if(S1TIME == 35){ S1TIME = 15; } ?

PIC, AVR, Arduino, Raspberry Pi, Basic Stamp, PLC mm.
PopUnoNkoK
Inlägg: 789
Blev medlem: 10 december 2007, 12:40:08
Ort: Piteå

if(S1TIME == 35){ S1TIME = 15; } ?

Inlägg av PopUnoNkoK »

Detta är kod jag skrivit själv och jag vill kolla om det är så här man skriver eller om det finns något enklare sätt.

Kod: Markera allt

		bcf			STATUS, 2
        incf  		S1TIME,1        ; Ökar på S1 tiden
		movlw		.35				;värdet att jämföra med
		subwf		S1TIME, 0		;Ta värdet i F och subtrahera med W
		btfss		STATUS, 2		;Kolla i Z biten i Status REG om svaret blev "noll".
		goto		loop			;Om inte, fortsätt att öka
		movlw		.15				;Annars, återställ S1 tiden till ändläge 1
		movwf		S1TIME			;
Hade jag skrivit det i ActionScript (Vilket är Adobe Flash språk) skulle det sett ut så här.

Kod: Markera allt

if(S1TIME == 35){ 
S1TIME = 15; 
}
Det blir två frågor:

1. Är ASM koden helt OK eller finns det bättre sätt?

2. Hur lik är ActionScriptkoden här över Ckoden som används i Picprogrammering?

MVH Peter F
sodjan
EF Sponsor
Inlägg: 43251
Blev medlem: 10 maj 2005, 16:29:20
Ort: Söderköping

Re: if(S1TIME == 35){ S1TIME = 15; } ?

Inlägg av sodjan »

Koden är nog OK, förrutom att det blir tydligare om du skriver symboler
istället för numeriska namn på bitar i olika register. men behöver då inte
kolla databladet för att kontrollera att du verkligen använder Z-biten (t.ex).
Och "W" och "F" kan jag aldrig hålla redan vilket som är 0/1...

Jag föredrar också d'35' framför .35 eftersom alla andra radix skrivs på samma
sätt (h'xx', a'B', b'01010101' o.s.v).

Kod: Markera allt

   bcf     STATUS, Z
   incf    S1TIME, F       ; Ökar på S1 tiden
   movlw   d'35'           ; värdet att jämföra med
   subwf   S1TIME, W       ; Ta värdet i F och subtrahera med W
   btfss   STATUS, Z       ; Kolla i Z biten i Status REG om svaret blev "noll". 
Sen så är kommentarerna inte så bra, de säger ju bara exakt vad instruktionen
gör och det står ju i databladet! Något i stil med detta är bättre :

Kod: Markera allt

   bcf     STATUS, Z
   incf    S1TIME, F       ; Ökar tiden för switch 1 (eller vad det nu var)
   movlw   d'35'           ; Uppnått max-tid ?
   subwf   S1TIME, W       ; -"-
   btfss   STATUS, Z       ; -"-
   goto    loop            ; Nej, fortsätt räkna...
   ......                  ; Ja, max-tid uppnåd...
Det är lite enklare att underhålla om du inte har en massa hårdkodade
värden utspridda i koden. Det kan ju dessutom finnas fler ställen där samma
värde ska användas och då är det väldigt lätt att missa ett av dom.
Så det är lite smidigare om du gör så här :

Kod: Markera allt

   ; Någonstans i början av koden...
max-S1-tid  EQU   d'35'
   ;
   ;
   bcf     STATUS, Z
   incf    S1TIME, F       ; Ökar tiden för switch 1 (eller vad det nu var)
   movlw   max-S1-tid      ; Uppnått max-tid ?
   subwf   S1TIME, W       ; -"-
   btfss   STATUS, Z       ; -"-
   goto    loop            ; Nej, fortsätt räkna...
   ......                  ; Ja, max-tid uppnåd...
Det är lite enklare att underhålla om du inte har en massa hårdkodade
värden utspridda i koden. Det kan ju dessutom finnas fler ställen där samma
värde ska användas och då är det väldigt lätt att missa ett av dom.
PopUnoNkoK
Inlägg: 789
Blev medlem: 10 december 2007, 12:40:08
Ort: Piteå

Re: if(S1TIME == 35){ S1TIME = 15; } ?

Inlägg av PopUnoNkoK »

Mycket vettiga synpunkter Sodjan.

Symboler istället för numeriska namn är förstås smidigare, problemet är att jag inte har koll på vilka symboler man kan använda. Jag ska kolla igenom Inc filen för att skaffa mig en liten överblick om vad som finns tillgängligt. Sedan skrev jag denna koden med databladet i högsta hugg så det var då lätt att använda bit siffrorna. Men, i fortsättningen blir det Symboler så ofta som möjligt.

Vad det gäller tal i Decimalform så gillade jag att man kunde skriva .15 men det är klart att det blir mer enhetligt att använda samma "form" för alla. Binär älskar jag för den är så visuell, Hex avskyr jag fortfarande (ENBART för att jag inte har koll på den, alltså ser inte direkt vilket värde det motsvarar). Decimal funkar bra eftersom det är nåt "man bara kan".

Vad det gäller kommentarer så har jag alltid varit dålig på att skriva bra kommentarer (och använda bra variabelnamn). När det gäller ASM så har jag velat skriva vad Instruktionen gör eftersom det inte alltid är självklart för mig. Men dessa instruktioner i detta kodexempel börjar sitta så här kan man förtydliga annat.

Som sagt, tack för svar.

Ps1. Det är pulstiden för servo1 som denna kod avser Ds1.

Ps2. Hur gör du för att få så fint strukturerad kod i dina kodexempel? Hur ändrar man tabbarna i inläggseditorn? Ds2


MVH Peter F
sodjan
EF Sponsor
Inlägg: 43251
Blev medlem: 10 maj 2005, 16:29:20
Ort: Söderköping

Re: if(S1TIME == 35){ S1TIME = 15; } ?

Inlägg av sodjan »

> problemet är att jag inte har koll på vilka symboler man kan använda.

Generellt kan man säga att det finns symboler definierade för "allt".
Alla bitar i register där bitarna har olika betydelse (d.v.s inte bitarna
i register som t.ex TMR0) har egna "namn".

> så gillade jag att man kunde skriva .15

Vad är så speciellt med det ? Att du sparar två tecken ? Jag föredar personligen
starkt d'15' eftersom det har samma grundformat som alla andra format.

> Hex avskyr jag fortfarande (ENBART för att jag inte har koll på den, alltså ser inte direkt vilket värde det motsvarar).

Å andra sidan så är hex lätt att översätta till binärt i huvudet. Decimalt går nästan inte alls.
Med hexvärdet h'8F' så är det rellativt enkelt att se vilka bitar som är "1" resp "0". Och på
något sätt så säger h'FF' "alla bitar = 1" lite mer tydligt än d'255', i alla fall för mig... :-)

Men visst, om det enbart är värdet i sig som är viktigt (och inte så mycket själva "bitmönstret")
så fungerar decimalt ofta precis lika bra. Notera dock att när det i datablad för
olika prylar (LCD, EEPROM minnen o.s.v.) står angivet olika "kommandon" så är det praktiskt
taget alltid angivet i hex. Att i det läget "översätta" alla hex-kommandon decimalt är bara
rent korkat.

> Hur gör du för att få så fint strukturerad kod i dina kodexempel?

Menar du själva formatteringen eller hur det är uppdelat i olika "nivåer" (subrutiner) ?

När det gäller struktureringen så brukar jag börja designen "uppifrån". Alltså det
man gör i huvudet eller på ett papper. Vad vill jag göra ? Hur ska det göras ? Vilka
olika moment behövs för att göra det ? Sedan kodar jag "underifrån", alltså med de
lägsta funktionerna. "Skriv ett tecken till LCD" eller liknande. Testar den och går sedan
vidare "uppåt". "Skriv en sträng till LCD" eller något sådant. Då tycker jag att man både
får en bra struktur på det hela och samtidigt jobbar åt det ursprungliga målet
som formulerades i början av designfasen samtidigt som koden kommer att
bestå av mindre rutiner med "rena" gränssnitt mot överliggande kod. Det underlättar
även senare när man vill återanvända koden i nästa projekt.

> ...så har jag velat skriva vad Instruktionen gör eftersom det inte alltid är självklart för mig.

Jo, så kan det vara. Men efter ett tag blir kommentarer i stil med detta lite fånig :

INCF VAR1 ; Öka VAR1 med ett

Det står ju faktiskt i databladet... :-)
v-g
EF Sponsor
Inlägg: 7875
Blev medlem: 25 november 2005, 23:47:53
Ort: Kramforce

Re: if(S1TIME == 35){ S1TIME = 15; } ?

Inlägg av v-g »

En sak som herrn ovanför också lärt mig är att köra med är #DEFINE

Tex:

Kod: Markera allt

   #DEFINE Blue_LED PORTB, 1   ; My Blue LED pin
   #DEFINE My_Button PORTA, 1   ; The button pin
Denna kod:

Kod: Markera allt

   BSF Blue_LED
   BSF Blue_LED
   BTFSC My_Button
   BTFSS My_Button
osv
blir då väldigt lättförståelig och kommentarer är nästan överflödiga ;)


Ibland händer det ju (ofelbart) att du måste flytta LEDen till en annan port/pinne. Genom ovanstående så behöver du då bara ändra på ETT ställe i koden och sen kompilera om, jämför detta med att leta efter alla PORTA/B och ersätta med rätt port/pinne. Enkelt sagt så är kompilatorn 100 gånger mer träffsäker och snabbare än vad man själv är ;)

Har däremot ett stort problem med att skriva relevanta kommentarer, ofta tar dessa längre tid än själva koden :D
sodjan
EF Sponsor
Inlägg: 43251
Blev medlem: 10 maj 2005, 16:29:20
Ort: Söderköping

Re: if(S1TIME == 35){ S1TIME = 15; } ?

Inlägg av sodjan »

JA, det finns många sätt att få sin assembler kod att bli med "3GL-look-alike"... :-)

EQU av konstanter istället för att ha dom "ute i koden".
DEFINE av t.ex pinner som i v-g's exempel.
Använda MACRO för att skapa sina egna "pseudo-instruktioner" för rutinoperationer.
Använda "assmebly-time calculations" för att underlätta t.ex inställning av baudrate
vid olika kristallfrekvenser.
Och sen hela DEFINE/IFDEF/ENDIF apparaten för att styra hur koden byggs.

Man kan få ett helt program att nästan inte ha några PIC-instruktioner alls... :-)
arte
Inlägg: 317
Blev medlem: 13 januari 2006, 01:18:50

Re: if(S1TIME == 35){ S1TIME = 15; } ?

Inlägg av arte »

PopUnoNkoK skrev:Detta är kod jag skrivit själv och jag vill kolla om det är så här man skriver eller om det finns något enklare sätt.

2. Hur lik är ActionScriptkoden här över Ckoden som används i Picprogrammering?

MVH Peter F
ActionScript och C är väldigt lik. Vissa typiska C saker som structar,pekare m.fl finns inte i AS3.

C är ju inte object orienterat heller. Men kan du AS3 så kan du skriva ganska många C program.
sodjan
EF Sponsor
Inlägg: 43251
Blev medlem: 10 maj 2005, 16:29:20
Ort: Söderköping

Re: if(S1TIME == 35){ S1TIME = 15; } ?

Inlägg av sodjan »

Sen så har väl ActionScript inte så mycket med PIC-programmering att göra,
så jämförelsen är kanske inte speciellt rellevant. Att "programmera en PIC"
handlar om mycket mer än en viss syntax på språket.
Skriv svar