Stap 4: .org assembler richtlijnen
We weten al wat de .nolist, .list, .include en .def assembler richtlijnen van onze vorige tutorials doen, dus laten we eerst eens een kijkje op de 4 lijnen van code die na die komen:
.org 0x0000 jmp Reset .org 0x0020 jmp overflow_handler
De verklaring van de .org vertelt de assembler waar in "Programmageheugen" om te zetten van de volgende instructie. Als uw programma wordt uitgevoerd, bevat de "Program Counter" (abreviated als PC) het adres van de huidige regel wordt uitgevoerd. Dus in dit geval wanneer de PC bij 0x0000 is het ziet de opdracht "jmp Reset" die woonachtig zijn in die locatie in het geheugen. De reden waarom we wil zetten jmp Reset in die locatie is omdat wanneer het programma begint, of de chip wordt teruggesteld, de PC start uitvoeren van code op deze plek. Dus, zoals we zien kunnen, we hebben net verteld om onmiddellijk "springen" naar de sectie met het label "Reset". Waarom hebben we dat doen? Dat betekent dat de laatste twee regels hierboven zijn gewoon worden overgeslagen! Waarom?
Nou, dat is waar de dingen interessant krijgen. Nu zult u moeten openstellen van een PDF-viewer met het volledige gegevensblad van ATmega328p die ik op de eerste pagina van deze tutorial aangewezen (dat is waarom het is punt 4 van de "u zal moeten" sectie). Als uw scherm te klein is, of hebt u manier teveel vensters geopend al (zoals het geval met mij) zou kunnen je doen wat ik doe, en zet het op een Ereader, of uw Androïde telefoon. U gebruikt het hele tijd als u van plan over het schrijven assemblagecode. Het koele ding is dat alle microcontollers in zeer vergelijkbare wijze en zo worden georganiseerd zodra je wennen aan het lezen van gegevensbladen en codering van hen u het bijna triviaal vindt te doen hetzelfde voor een verschillende microcontroller. Zo leren we eigenlijk het gebruik van alle microcontrollers in een zin en niet alleen de atmega328p.
Oke, ga naar pagina 18 in het gegevensblad en neem een kijkje op figuur 8-2.
Dit is hoe het programmageheugen in de microcontroller is ingesteld. U kunt zien dat het begint met adres 0x0000 en is onderverdeeld in twee secties; een toepassing flash en een boot flash sectie. Als u kort ingaan op 277 tabel pagina 27-14 u zult zien dat de toepassing flash sectie de locaties van 0x0000 tot 0x37FF neemt en de flash sectie van boot de resterende locaties van 0x3800 naar 0x3FFF neemt.
Oefening 1: hoeveel locaties zijn er in het programmageheugen? Dwz 3FFF converteren naar een decimaal getal en er 1 bij optellen omdat we beginnen met tellen bij 0. Aangezien elke locatie in het geheugen is 16 bits (of 2 bytes) wijd wat is het totale aantal bytes van het geheugen? Nu dit omzetten in kilobytes, herinneren zijn er 2 ^ 10 = 1024 bytes in een kilobyte. De flash sectie van de boot gaat van 0x3800 naar 0x37FF, hoeveel kilobytes is dit? Hoeveel kilobytes geheugen blijven voor ons om te gebruiken voor het opslaan van ons programma? Met andere woorden, hoe groot onze programma kunnen zijn? Tot slot, hoe veel regels code kunnen we hebben?
Oke, nu we weten alles over de organisatie van het programma flash geheugen, laten we blijven met onze bespreking van de verklaringen van de .org. We zien dat de eerste geheugenlocatie 0x0000 bevat onze instructie om te springen naar onze sectie met we het label Reset. Nu zien we wat de verklaring van de ".org 0x0020" doet. Het zegt dat we willen de instructie op de volgende regel worden geplaatst op de locatie in het geheugen 0x0020. De instructie die we hebben geplaatst is er een sprong naar een sectie in onze code die we hebben met het label "overflow_handler"... nu waarom de heck wij eisen zou dat deze sprong aan geheugenlocatie 0x0020 worden geplaatst? Als u wilt weten, we Ga naar pagina 65 in het gegevensblad en neem een kijkje op tabel 12-6.
Tabel 12-6 is een tabel van "Reset en Interrupt vectoren," en het toont precies waar de PC zal gaan wanneer zij ontvangt een "interrupt". Bijvoorbeeld, als je kijkt naar Vector nummer 1. De "bron" van de interrupt is "RESET" die is gedefinieerd als "externe Pin, Power-on Reset, Brown-out Reset en Watchdog systeem reset" betekenis, als om het even welk van die dingen met onze microcontroller gebeuren, start de PC uitvoeren van ons programma op locatie in het geheugen programma 0x0000. Hoe zit het met onze .org richtlijn dan? Nou, we een opdracht geplaatst op locatie in het geheugen 0x0020 en als je op de tafel kijkt ziet u dat als een Timer/Counter0 overflow gebeurt (afkomstig uit TIMER0 OVF) het zal uitvoeren wat is op locatie 0x0020. Dus wanneer dat gebeurt, de PC zal gaan naar de plek we met het label "overflow_handler". Cool toch? U zult zien in een minuut waarom we deden dit, maar eerst laten we eindigen deze stap van de tutorial met een terzijde.
Als we willen maken van onze code meer keurig en netjes we echt door de 4 lijnen die wij momenteel bespreken de volgende vervangen moeten (zie pagina 66):
.org 0x0000 rjmp Reset ; PC = 0x0000 reti ; PC = 0x0002 reti ; PC = 0x0004 reti ; PC = 0x0006 reti ; PC = 0x0008 reti ; PC = 0x000A ... reti ; PC = 0x001E jmp overflow_handler : PC = 0x0020 reti : PC = 0x0022 ... reti ; PC = 0x0030 reti ; PC = 0x0032
Zodat als een bepaalde interrupt optreedt het zal gewoon "reti" wat betekent "terugkeer van interrupt" en niets anders gebeurt. Maar als we nooit "Enable" deze verschillende interrupts, dan zij niet zullen worden gebruikt en kunnen we programmacode in deze plekken. In onze huidige "blink.asm"-programma gaan we alleen om de timer0 overflow interrupt (en natuurlijk de reset-interrupt die altijd is ingeschakeld) en dus wij niet de moeite met de anderen.
Hoe we "Schakel" de timer0 overflow interrupt dan? ... dat is het onderwerp van onze volgende stap in deze tutorial.