Hårdvara XOR för utgångsstift på AVR-mikrokontroller

Visste du att många AVR-chips har en typ av högvaru-exklusivt eller (xor) alternativ när det gäller de logiska nivåerna av utgångsstiften? Om du tittar i databladet (bilden ovan är en skärmdump från en ATTINY13 datablad) hittar du en sektion om växling av stiftet. Det visar sig att om du ställer in en port som en utgång, kommer att skriva logik ett till motsvarande PIN-register att växla de logiska nivåerna på det. Det här är väldigt lätt att försumma om du skriver i C, men jag har jobbat med att lära mig lite assembler språk och fann att detta är mycket användbart. Fortsätt läsa efter pausen och jag ska berätta hur jag hände på den här informationen och vad det är bra för.

Så först, låt oss prata om varför det spelar ingen roll mycket om du skriver i c-koden. Vanligtvis om du vill växla några utepinnar skriver du bara ett en-liner som Xor är med en bitmask:

1
PORTB ^ = 0xFF;

Det här är lite C-shorthand (lär dig mycket mer om det från min handledningsserie) som utför XOR på nuvarande utgångsnivåer och skriver resultatet tillbaka till porten. Men samma sak kan göras i hårdvara genom att skriva bitmasken till PINB-registret:

1
Pinb = 0xff;

Du bryr dig inte riktigt, för det är bara en rad kod. I själva verket är det förmodligen enklare att Xor Portb eftersom det är mycket mer meningsfullt konceptuellt. Men kompilatorn kan sluta använda mycket fler cykler än om du hade skrivit till PIN-registeret.

Jag hände över den här funktionen eftersom jag blinkade några lysdioder som ett sätt att lära sig assembler. Jag hade denna jumble av kod i en avbrottstjänstrutin:

1
2
3
4
LDI MYREG, 0xFF
I IntraG, PORTB
Eor IntraG, MYREG
ut Portb, IntraG

Den laddar en bitmask i ett register, laster i den aktuella logiken från PORTB till ett annat register, utför en XOR av de två och skriver resultatet tillbaka till PORTB. Detta tar fyra cykler och kräver två register. Växling bitar är en sådan rudimentär operation jag var förvånad att det inte var ett kommando till Xor Bits direkt så jag började söka runt. Jag kom över den här korta artikeln över på AVR-freaks som clued mig in i bitväxeln. Nu kunde jag minska min samlingskod enligt följande:

1
2
LDI IntraG2, 0xFF; temporaritetsanvändning intrreg2 som en bit mask
ut Pinb, IntraG2; Skrivning till Pinb Effectivley gör en exklusiv eller på Portb

Detta resulterar i samma växlingseffekt, men tar bara två cykler och kräver användning av endast ett register.

Vad jag hittade många intressanta är att oavsett hur mycket jag använder AVR-chips, det är aldrig brist på överraskningar som väntar på att hitta i databladet.

Leave a Reply

Your email address will not be published. Required fields are marked *

Related Post