AVR mikrokontrollerek programozása. Hogyan kezdjük el az AVR programozását? Ajánlások. MK interfész programozási módban

Nem egyszer vagy kétszer mondtam, hogy az MK tanulmányozását az assemblerrel kell kezdeni. Az oldalon egy egész tanfolyamot szenteltek ennek (bár nem túl konzisztens, de fokozatosan átfésülöm a megfelelő megjelenésre). Igen, nehéz, az eredmény nem az első napon lesz, de megtanulod megérteni, mi történik a vezérlőben. Tudni fogja, hogyan működik, és nem másolja mások forrásait, mint egy majom, és megpróbálja megérteni, miért állt le hirtelen. Ráadásul a C sokkal könnyebben vacakol a redneck kóddal, amely a legalkalmatlanabb pillanatban fog kijönni.

Erről egy kicsit bővebben később lesz szó. Néha a kifejezéseket felcserélhetően használják, de ennek az oktatóanyagnak a középpontjában mindig a mikrokontrollerek állnak. Minden asztali számítógépen, laptopon vagy táblagépen egy tucat vagy több mikrokontroller lehet csendesen futtatni a beépített funkcióit, és ezekkel az eszközökkel sokan észre sem veszik, hogy a programot futtató apró számítógéphez csatlakoznak. De van és van, és ezeket a programokat meg kell írni, ezért a világnak beágyazott programozásra van szüksége.

Sajnos mindenki azonnali eredményt akar. Ezért úgy döntöttem, hogy a másik utat választom - készítek egy bemutatót C-ről, de a fehérnemű bemutatásával. Egy jó beágyazó programozó mindig szorosan tartja a vasdarabot a tepertőnél, megakadályozva, hogy engedély nélkül egyetlen lépést is tegyen. Tehát mi lesz először a C kód, aztán mit szült a fordító és hogyan működik mindez a valóságban :)

A legtöbb asztali vagy nagyszámítógéppel ellentétben a beágyazott programok valami hasznosat tesznek, és a beágyazott programozó számára végtelenül menők a dolgok, amelyek a dolgokat csinálnak. Erre a kérdésre nincs tökéletes válasz, mivel minden válasznak vannak kivételei. Céljaink szempontjából azonban kijelentjük, hogy a beágyazott rendszer olyan rendszer, amely egy vagy több mikroszámítógépet használ, speciális speciális programokat futtat, és speciális hardverhez csatlakozik speciális funkciók végrehajtása érdekében.

Ez összehasonlítható egy általános célú számítógéppel, például egy asztali számítógéppel vagy laptoppal, amelyet nem arra terveztek, hogy csak egy speciális programot fusson egyetlen speciális hardverkészlettel. Ez nem tökéletes meghatározás, de ez egy kezdet.

Másrészt a C erőssége a kódhordozhatóság. Ha persze mindent helyesen írni. A munkaalgoritmusok és vasmegvalósításaik szétválasztása a projekt különböző részeire. Ezután az algoritmus másik MK-ra való átviteléhez elegendő csak az interfész réteget átírni, ahol a hardverhez való összes hozzáférés meg van írva, és az összes működő kódot úgy hagyni, ahogy van. És persze az olvashatóság. A Sish forráskódját egy pillantásra könnyebb megérteni (bár .. például nem érdekel, hogy mit pöccintsek - legalább si, legalább asm :)), de ismét, ha minden helyesen van megírva. Ezekre a pontokra is figyelni fogok.

Néhány példa a beágyazott rendszerekre. Éneklő fali hal. A fenti listában van néhány dolog, amire érdemes odafigyelni. Míg sok beágyazott rendszer meglehetősen hagyományos felhasználói I/O-eszközöket használ, mások nem. Ezenkívül sok beágyazott rendszer közvetlenül kölcsönhatásba lép az emberekkel, míg mások nem.

Miben más a beágyazott programozás?

A beágyazott programoknak szorosan együtt kell működniük a speciális komponensekkel és az ezt alkotó egyedi áramkörökkel Hardver. Ellentétben a teljes funkcionalitású operációs rendszer tetején történő programozással, ahol a hardverrészletek a lehető legnagyobb mértékben el vannak távolítva a programozó észrevételeitől és vezérlésétől, a legtöbb beágyazott program közvetlenül a hardveren és a hardveren működik. Tehát egy beágyazott programozónak jól kell ismernie a hardvert, legalább az írás terén szoftver amely megfelelően kommunikál ezzel a berendezéssel és vezérli.

Kísérleti vasdarabként, amelyre az összes példa oroszlánrésze kerül, az én hibakereső táblám lesz.

Az első C program az AVR-hez

Fordítóprogram kiválasztása és környezet telepítése
Számos különböző C fordító létezik az AVR-hez:
Először is ezt IAR AVR C- szinte egyértelműen az AVR legjobb fordítójaként ismerik el, tk. maga a vezérlő az Atmel és az IAR szakemberei szoros együttműködésében jött létre. De mindenért fizetni kell. És ez a fordító nem csak drága kereskedelmi szoftver, hanem olyan rengeteg beállítással is rendelkezik, hogy csak keményen kell dolgozni, hogy lefordítsák benne. Igazából nem volt barátságom vele, a projekt a linkelési szakaszban történt furcsa hibák miatt elrohadt (később rájöttem, hogy egy ferde repedés volt).

Ez a tudás gyakran kiterjed a kulcsfontosságú hardverkomponensek meghatározására, és a kisebb szervezetekben néha a hardver tervezése és elrendezése is szerepet játszik. A beágyazott programozónak jól kell ismernie a hibakereső hardvereket, például a multimétereket, oszcilloszkópokat, logikai analizátorokat és hasonlókat.

Egy másik különbség a számítógépekhez képest Általános rendeltetésű az, hogy a legtöbb beágyazott rendszer meglehetősen korlátozott a korábbihoz képest. A beágyazott rendszerekben használt mikroszámítógépek programmemóriája néhány ezertől több százezer bájtig terjedhet, nem pedig egy asztali gép gigabájtja, és általában kevesebb adatmemóriával rendelkeznek, mint a programmemóriával.

Második megy WinAVR GCC egy hatékony optimalizáló fordító. Teljesen nyílt forráskódú, cross-platform, általában az élet minden öröme. Tökéletesen integrálódik az AVR Stúdióba is, lehetővé téve a hibakeresést ott, ami pokolian kényelmes. Általában azt választottam.

Szintén van CodeVision AVR C nagyon népszerű fordítóprogram. Egyszerűsége miatt vált népszerűvé. munkaprogram néhány perc alatt beszerezheti – ehhez nagyban hozzájárul az indítókód varázsló, amely lebélyegzi az esetleges uart inicializálásának szabványait. Hogy őszinte legyek, valahogy gyanakodva bánok vele - egyszer szét kellett szednem egy programot, amit ez a fordító írt, valami zabkása és nem kód derült ki. Rettenetes mennyiségű felesleges gesztus és művelet, ami meglehetősen nagy mennyiségű kódot és lassú teljesítményt eredményezett. Lehetséges azonban, hogy hiba volt az eredeti firmware-író ​​DNS-ében. Ráadásul pénzt akar. Nem annyira, mint az IAR, de észrevehető. Demó módban pedig legfeljebb 2 kb kódot tesz lehetővé.
Persze van repedés, de ha lopsz, akkor egymillió, IAR értelmében :)

Mi a különbség a mikroszámítógép, a mikroprocesszor és a mikrokontroller között?

Így minden mikrokontroller mikroszámítógép, de nem minden mikroszámítógép használ mikrokontrollert. A kisebb beágyazott rendszerek leggyakrabban mikrovezérlőket használnak, nem pedig mikroprocesszorokat, mivel a mikrokontrollerek a legkompaktabb kialakítást és a legalacsonyabb hardverköltséget biztosítják. Másrészt a nagyobb beágyazott rendszerek egy vagy több mikroprocesszort is használhatnak, ha nem található megfelelő sebességű és funkcionalitású mikrovezérlő.

Van még Image Craft AVR Cés MicroC a mikroelektronikától. Egyiket sem kellett használni, de... SWG nagyon sok dicséret micropascal, azt mondják, borzasztóan kényelmes programozási környezet és könyvtárak. Szerintem a MicroC nem lesz rosszabb, de fizetős is.

Mint mondtam, én választottam WinAVR három okból: ingyenes, integrálható az AVR Stúdióba, és csak egy csomó kész kódot írnak rá minden alkalomra.

Lehetőség van arra is, hogy egy komplex beágyazott rendszerbe mikroprocesszorokat és mikrokontrollereket is beépítsünk. Az egyetlen valódi szabály az, hogy bármilyen eszközt használjunk, amely megfelelő a feladathoz, tekintettel a költségvetésre, a rendelkezésre állásra, az időre, az eszközökre stb.

Azt is meg kell jegyezni, hogy a legtöbb mikrokontrollerrel lehetőség van külső memória és perifériák hozzáadására, ha az alaplapi mix nem gondoskodik minden rendszerszükségletről. Mikor van értelme hozzátenni külső eszközök, szemben azzal, hogy nagyobb, a szükséges erőforrásokkal rendelkező mikrokontrollert választunk, ezt egyedi tervezési alapon kell meghozni.

Tehát töltse le a WinAVR-t az AVR Studio segítségével. Ezután először a stúdiót telepítik, majd felülről a WinAVR felgördül, és plug-in formájában a stúdióhoz tapad. Erősen javaslom, hogy a WinAVR-t egy rövid útvonalra tegyük, például a C:\WinAVR-hez, így sok problémát elkerülhetünk az elérési utakkal.

Projekt létrehozása
Szóval, a stúdió be van állítva, a C be van csavarva, ideje megpróbálni programozni valamit. Kezdjük az egyszerűvel, a legegyszerűbbel. Futtassa a stúdiót, válasszon ki egy új projektet az AVR GCC fordítójaként, és adja meg a projekt nevét.

Például egy eszköz rendelkezhet egy teljes utasításkészlettel, amely képes 8 bites adatokon működni, valamint több olyan utasítással is, amelyek 16 bites adatokon működnek. Ezt az eszközt 8 bites kialakításnak kell tekinteni, még akkor is, ha a marketing osztály mást mond, és 16 bites chipnek nevezi. A mennyiséget tekintve a 8 bites mikrokontrollerek jelentik a beágyazott piac legnagyobb szegmensét. Sok alkalmazásnak egyszerűen nincs szüksége több energiára, és soha nem is lesz. A 16 bites eszközök erősebbek, de tömörítésük a legalacsonyabb 8 bites és a felső kategóriás 32 bites eszközök között történik. A 32 bites eszközök a legbonyolultabb vagy csúcskategóriás kialakítások kivételével a fedélzeti spektrum legfelső végén találhatók, de az árak csökkennek.

A munkaterület egy üres *.c fájllal nyílik meg.

Most már nem árt beállítani az útvonalak megjelenítését a stúdió könyvjelzői között. Ehhez lépjen a következő helyre:
Menü Eszközök - Beállítások - Általános - Fájllapok, és válassza a "Csak fájlnév" lehetőséget a legördülő listából. Ellenkező esetben lehetetlen lesz dolgozni - a lapon lesz teljes útvonal fájlt, és nem lesz több két-három lapnál a képernyőn.

Milyen mikrokontroller-családokat használnak ezekben az oktatóanyagokban?

Hogy egy kis áttekintést adjunk különféle lehetőségeket rendelkezésre álló mikrokontrollerek, ez az oktatóanyag egy 8 bites család és egy 32 bites család köré épül. Ezt a két családot azért választottuk ki, hogy meglehetősen tág képet adjunk a mikrokontrollerek világában fellelhető eszközökről és megközelítésekről.

Mi kell még ezekhez az oktatóanyagokhoz?

Ha a tesztberendezésekről van szó, a DMM-ek nagyon olcsók, és nincs mentség arra, hogy ne legyen ilyen. Egy másik felszerelés, amellyel minden beágyazott mérnöknek rendelkeznie kell, egy tisztességes oszcilloszkóp. Ne essen pánikba, nincs szükség hangerőre ezekhez az oktatóanyagokhoz.

Projekt beállítása
Általában klasszikusnak tekinthető egy make fájl létrehozása, amelyben minden függőséget leírnak. És ez valószínűleg helyes. De nekem, aki teljesen integrált IDE-kben nőttem fel, mint pl uVision vagy AVR Stúdió ez a megközelítés mélyen idegen. Ezért a magam módján fogom csinálni, a stúdió minden eszközével.

Kattintson a fogaskerék gombra.

Hogyan működik a beépített program?

Ha azonban beszerez egyet ezek közül, többet tanulhat meg, és jó sok időt takaríthat meg a tranzakció során. Itt az ideje, hogy beszéljünk egy kicsit a különböző programozási nyelvekről, amelyek segítségével beágyazott szoftvereket írhatunk. Más nyelvekre ugyanez nem vonatkozik. Mielőtt a beépített programokról beszélnénk, ez jó hely, Adni rövid áttekintés hogyan indul el és fut a beágyazott program. Néha ez a memóriahely közvetlenül tartalmazza a kódot; például a resetből való kilépéskor a program végrehajtása a program címén kezdődik.



Ezek a projekt beállításai, vagy inkább a make fájl automatikus létrehozásának beállításai. Az első oldalon csak azt a frekvenciát kell megadnia, amelyen az MK működni fog. Ez a biztosítékbitektől függ, ezért feltételezzük, hogy a frekvencia 8000000Hz.
Ügyeljen az optimalizálási vonalra is. Most van -Os a méretoptimalizálás. Hagyja egyenlőre, aztán megpróbálhatja eljátszani ezt a paramétert. -O0 egyáltalán nem optimalizálás.

Az első esetben meg kell győződnie arról, hogy a program a megadott autoload címen van betöltve, a második esetben pedig ott tölti be a programját, ahol a programmemória a vezérlő címterében volt, és győződjön meg arról, hogy ezután betölti az indítási címet a visszaállítási címvektorba.

Kérjük, vegye figyelembe, hogy az indítási mód kiválasztása nem Önön múlik, hanem beépül a választott mikroszkóp projektjébe. Amikor a telepített program futni kezd, általában elegendő inicializálás és karbantartás szükséges a program indítása előtt. Az inicializálás nagy részét az átlagos asztali programozó soha nem látja, mivel azt a számítógép indítókódja és operációs rendszere kezeli. De egy beágyazott rendszerben ugyanolyan valószínű, hogy nincs operációs rendszer, és minden rendszerindító kódot és egyéb indítókódot kifejezetten meg kell adni.

A következő lépés az utak beállítása. Mindenekelőtt adja hozzá a projektje könyvtárát - ott harmadik féltől származó könyvtárakat helyez el. A ".\" elérési út megjelenik a listában

A make fájl generálódik, megtekintheti a projekt alapértelmezett mappájában, csak nézze meg, mi van ott.



Ez minden most. Kattintson az OK gombra mindenhol, és lépjen a forráshoz.

Programozási nyelv és fejlesztői környezet kiválasztása a programozáshoz

Előfordulhat, hogy néhány nagyon fontos hardvert először inicializálni kell, például a memóriaelérési időket és a címleképezéseket vezérlő hardvert, valamint a rendszeróra hardvert. Előfordulhat, hogy bizonyos szoftver inicializálásra van szükség, például be kell állítani a veremmutatót, és esetleg át kell másolni az adatokat a nem felejtő memóriából a felejtő memóriába, ahol azok elérhetők és esetleg módosíthatók. Ezt követően általában megkezdődik a hardver inicializálásának újabb köre, a rendszer által igényelt perifériák beállítása és a kezdeti kimeneti állapotok beállítása.

A probléma megfogalmazása
Az üres lap csábító valami ravasz ötlet megtestesítésére, hiszen a dióda banális villogása már nem jön be. Azonnal ragadjuk meg a bikát a szarvánál, és hozzuk létre a kapcsolatot a számítógéppel – ez az első dolgom.

Ez így fog működni:
Amikor egy egység megérkezik a COM portra (0x31 kód), bekapcsoljuk a diódát, ha pedig nulla érkezik (0x30 kód), akkor eloltjuk. Sőt, minden megszakításokon fog megtörténni, a háttérfeladat pedig egy másik dióda villogása lesz. Egyszerű és értelmes.

Milyen mikrokontrollerek vannak?

Végül a szoftver inicializálásának újabb köre következhet be. Ez az inicializálás általában két részre oszlik, ahol az első hardver- és szoftverinicializálási lépéseket gyakran az úgynevezett startkódban, a későbbi hardver- és szoftverlépéseket pedig a felhasználói programban hajtják végre. Egy összeszerelő programban az összes inicializálási lépés egyformán látható lehet a felhasználói kódban, bár az első lépések még ebben az esetben is lehetnek egy külön indító forrásfájlban.

A séma összeállítása
Csatlakoztatnunk kell az USB-USART átalakító modult a mikrokontroller USART érintkezőihez. Ehhez veszünk egy két vezetékből álló jumpert, és keresztben helyezzük a csapokra. Vagyis a vezérlő Rx-ét a konverter Tx-ével, a konverter Tx-ét pedig a vezérlő Rx-ével kötjük össze.

Kiderül, hogy végül ez a séma:



Nem tartom a maradék kimenetek csatlakoztatását, tápegységet, reset-et, az alap

Megjegyzés a mintaprogramokról

Az oktatóanyag minden része tartalmaz néhány rövid példát. A példák a legegyszerűbb fogalmakkal kezdődnek, és minden további programhoz hozzáadnak néhány fogalmat. Ez lesz a sorozat következő leckéjének témája. Tutorial, de más módon. Remélem, ez hasznos lesz az Ön számára.

Ugyanakkor a 4 bites mód is elég gyors és pontos ahhoz, hogy a legtöbb igényünket kielégítse, ráadásul mindössze 7 tűt igényel. Ezért 4 bites módban fogunk dolgozni. Ehhez használja a következő diagramot. Tekintse meg a fenti tűkonfigurációt.

Írjuk a kódot

Azonnal leszögezem, hogy magának a C nyelvnek a leírásában nem mélyedek el. Ehhez egyszerűen kolosszális mennyiségű anyag áll rendelkezésre, a klasszikus "C programozási nyelvtől" a K&R-től a különféle kézikönyvekig.

Egy ilyen módszert találtam a rejtekemben, egyszer tanultam is ezt a nyelvet a segítségével. Minden rövid, világos és lényegre törő. Fokozatosan beírom és a webhelyemre húzom.

Ez egy fantasztikus könyvtár előre definiált kódokkal, így egy kicsit lazíthatunk rajta anélkül, hogy a kódolási részen törnénk a fejünket. Így lehetőséget kapunk a könyvtári függvények használatára ahelyett, hogy a programozás mélységeibe mennénk. Ez a módszer sokkal hatékonyabb, hatékonyabb és időt takarít meg. Ezen a ponton ne aggódjon a könyvtár megírása miatt.

Most két fájlt találhat a projektben. Könyvtár beállításához kövesse az alábbi lépéseket. Most ügyeljen arra, hogy nagyon lassan görgessen, különben lemarad néhány fontos részletről. Kiválaszthatja, hogy egy porton menjenek át, vagy különböző portokon legyenek elosztva. Most, ha tovább görget, megtalálja a könyvtárban definiált összes funkció listáját a leírásukkal együtt.

  • Győződjön meg arról, hogy helyes-e, különben a késleltetési időzítések meghiúsulnak.
  • Alatta van a legjobb rész.
  • Válassza ki őket a névjegyek elérhetősége szerint.
  • Leírásukat a pályázatukhoz mellékeljük.
Most, hogy végignézte a különféle elérhető funkciókat, írjunk hozzá néhány mintakódot.

Igaz, hogy még nem minden fejezet került át oda, de szerintem nem sokáig.

Nem valószínű, hogy jobban leírom, ezért a képzési kurzusból a Cish bonyolultságának részletes magyarázata helyett egyszerűen közvetlen hivatkozásokat adok a kézikönyv egyes oldalaira.

Könyvtárak hozzáadása.
Először is hozzátesszük szükséges könyvtárakés címek definíciókkal. Végül is a C univerzális nyelv, és el kell magyarázni, hogy AVR-rel dolgozunk, ezért írja be a sort a forráskódba:

1 #beleértve

Ez a fájl a mappában található WinAVRés tartalmazza a vezérlő összes regiszterének és portjának leírását. És ott minden trükkös, egy konkrét vezérlőre hivatkozva, amelyet a fordító továbbít készítsenek fájl a paraméterben MCUés e változó alapján egy fejlécfájl csatlakozik a projekthez, amely tartalmazza az adott vezérlő összes portjának és regiszterének címét. Hogyan! Enélkül is megteheti, de akkor nem használhat olyan szimbolikus regiszterneveket, mint a SREG vagy az UDR, és emlékeznie kell mindegyik címére, például "0xC1", és ezen töri a fejét.

Ugyanaz a csapat #beleértve<имя файла> lehetővé teszi bármely szövegfájl tartalmának hozzáadását a projekthez, például egy funkcióleírást tartalmazó fájlt vagy egy másik kódrészletet. És hogy a direktíva megtalálhassa ezt a fájlt, megadtuk a projektünk elérési útját (a WinAVR könyvtár alapértelmezés szerint ott van regisztrálva).

fő funkció.
A C program a függvényekről szól. Tetszőleges sorrendben egymásba ágyazhatók és hívhatók különböző utak. Minden funkciónak három kötelező paramétere van:

  • Visszatérési érték pl. bűn(x) x szinuszának értékét adja vissza. Mint a matematikában, röviden.
  • Az átvitt paraméterek, ugyanaz az x.
  • Funkciótest.

Minden átadott és visszaadott értéknek valamilyen típusúnak kell lennie, az adatoktól függően.

Minden C programnak tartalmaznia kell egy függvényt fő- mint belépési pont a főprogramhoz, különben egyáltalán nem C :). A main jelenléte valaki más millió fájl forrásában megértheti, hogy ez a program fő része, ahonnan minden kezdődik. Itt állítjuk be:

1 2 3 4 5 int main(void ) ( return 0 ; )

Minden, először a legegyszerűbb programírva, nem számít, hogy nem csinál semmit, most kezdtük.

Lássuk, mit csináltunk.
int az az adattípus, amelyet a fő függvény visszaad.

Természetesen a mikrokontrollerben fő- elvileg semmit nem lehet visszaadni, és elméletileg annak is kell lennie void main(void), de a GCC eredetileg a PC-n van kihegyezve és ott a program vissza tudja adni az értéket operációs rendszer befejezésekor. Ezért a GCC be void main(void) a Figyelmeztetésre esküszik.

Ez nem hiba, működni fog, de nem szeretem a figyelmeztetéseket.

üres ebben az esetben ilyen típusú adatokat adunk át a függvénynek fő- kívülről, a költőtől sem tud elfogadni semmit üres- üres. A csonkot akkor használjuk, ha semmit sem kell átadni vagy visszaadni.

Itt vannak ezek { } A curly brackets egy programblokk, jelen esetben a függvény törzse fő-, a kód ott lesz.

Visszatérés- ez a visszatérési érték, amit a főfüggvény ad a befejezéskor, mivel van egy int, vagyis egy szám, akkor egy számot kell visszaadnunk. Bár ennek még mindig nincs értelme, mert. a mikrokontrolleren a main-ról csak sehova sem tudunk menni. nullát adok vissza. Nefig számára. A fordító pedig általában okos és nem generál kódot erre az esetre.
Bár ha perverz, akkor attól fő- mehetsz az MK-hoz - például kieshetsz a bootloader részbe és végrehajthatod, de itt már alacsony szintű firmware-választásra lesz szükséged az átmeneti címek javításához. Az alábbiakban látni fogja és megérti, hogyan kell csinálni. Minek? Ez most egy másik kérdés, az esetek 99.999%-ában erre nincs is szükség :)

Kész, lépj tovább. Adjunk hozzá változót, nincs is rá igazán szükségünk és nem is kellene változókat bevezetni nélküle, de tanuljuk. Ha változókat adunk hozzá a függvénytörzsben, akkor azok lokálisak, és csak ebben a függvényben léteznek. Amikor kilép a funkcióból, ezek a változók törlődnek, és a RAM-memória fontosabb igényekhez kerül. .

1 2 3 4 5 6 int main(void) (előjel nélküli karakter; return 0; )

aláírás nélküli aláíratlant jelent. A helyzet az, hogy a bináris ábrázolásban a legjelentősebb bit az előjelhez van rendelve, ami azt jelenti, hogy a +127/-128 szám belefér egy bájtba (char), de ha az előjelet eldobjuk, akkor 0-tól 255. Általában nincs szükség a jelre. Szóval azt aláírás nélküli.
én csak egy változónév. Nem több.

Most inicializálnunk kell a portokat és UART. Természetesen felveheti és csatlakoztathatja a könyvtárat, és meghívhat valamilyen UartInit-et (9600); de akkor nem fogod tudni, mi történt valójában.

Ezt csináljuk:

1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 int main(void ) ( unsigned char i; #define XTAL 8000000L #define baudrate 9600L #define bauddivider (XTAL/(16*baudrate)-1)#define HI(x) ((x)>>8) #define LO(x) ((x)& 0xFF) UBRRL = LO(baudosztó) ; UBRRH = HI(baudosztó) ; UCSRA = 0; UCSRB=1<< RXEN| 1 << TXEN| 1 << RXCIE| 0 << TXCIE; UCSRC = 1 << URSEL| 1 << UCSZ0| 1 << UCSZ1; }

Ijedős? Valójában csak öt utolsó sor van a valódi kódban. Minden, ami #define ez egy előfeldolgozó makrónyelv. Majdnem ugyanazok a csúcsok, mint az Assemblerben, de a szintaxis némileg más.

Ezek megkönnyítik a szükséges együtthatók kiszámításának rutinműveleteit. Az első sorban azt mondjuk, hogy ahelyett XTAL nyugodtan helyettesítheti 8000000, ill L- típusjelzés, azt mondják long a processzor órajele. Azonos átviteli sebesség- az UART-on keresztüli adatátvitel gyakorisága.

baudosztó már bonyolultabb, helyette az előző kettő képletével számított kifejezés lesz behelyettesítve.
Jól és LOés SZIA ebből az eredményből az alacsony és a magas bájt lesz kivéve, mert nyilván nem fér bele egy bájtba. NÁL NÉL SZIA x eltolódik (a makró bemeneti paramétere) nyolcszor jobbra, ennek következtében csak a magas bájt marad meg belőle. És be LO bitenkénti ÉS-t csinálunk a 00FF számmal, így csak az alacsony bájt marad meg.

Tehát minden, ami történt, olyan #define nyugodtan kidobhatja, és kiszámolhatja a szükséges számokat a számológépen, és azonnal beírhatja az UBBRL = ... sorokba. és UBBRH=…..

Tud. De! Csináld ezt SZIGORÚAN LEHETETLEN!

Ez így is, úgy is működni fog, de lesz ún mágikus számok- a semmiből vett értékek, és nem világos, hogy miért, és ha pár év múlva megnyit egy ilyen projektet, akkor rohadt nehéz lesz megérteni, hogy mik ezek az értékek. És most, ha meg akarja változtatni a sebességet, vagy megváltoztatni a kvarc frekvenciáját, és mindent újra kell számolnia, és így megváltoztatott néhány számot a kódban, és ennyi. Általánosságban elmondható, hogy ha nem akarod, hogy rossz kódolónak tartsanak, akkor készítsd el a kódot úgy, hogy könnyen olvasható, érthető és könnyen módosítható legyen.

Akkor minden egyszerű:
Mindezek az "UBRLL és Co" az UART adó konfigurációs regiszterei, amelyekkel kommunikálni fogunk a világgal. És most hozzárendeltük a szükséges értékeket, beállítva őket a kívánt sebességre és a kívánt üzemmódra.

Rekord megtekintése 1< A következőket jelenti: vegyen 1-et és tegye a helyére RXEN egy bájtban. RXEN ez a regiszter 4. bitje UCSRB, így 1< a 00010000 bináris számot alkotja, TXEN a 3. bit, és 1< 00001000. Egyetlen "|" ez bitesen van VAGY, tehát 00010000 | 00001000 = 00011000. Ugyanígy a fennmaradó szükséges konfigurációs bitek beállítása és hozzáadása a közös kupachoz. Ennek eredményeként az összegyűjtött szám beírásra kerül az UCSRB-be. Részletesebben le van írva az MK adatlapján az USART részben. Tehát ne zavarja el a figyelmét a technikai részletek.

Kész, ideje megnézni, mi történik. Kattintson a fordításra, és indítsa el az emulációt (Ctrl+F7).

Hibakeresés
Mindenféle folyamatjelző sáv futott át, a stúdió megváltozott, és egy sárga nyíl jelent meg a fő funkció bejárata közelében. Itt van jelenleg a processzor, és a szimuláció szünetel.

A helyzet az, hogy eredetileg az UBRRL = LO(bauddivider) sorban volt; Hiszen ami a define-ban van, az nem kód, hanem egyszerűen csak előzetes számítások, így a szimulátor kicsit unalmas. De most rájött, hogy az első utasítás teljesült, és ha felmászik egy fára I/O nézet, az USART részhez és ott nézd meg az UBBRL bájtot, látni fogod, hogy ott már van érték! 0x33.

Tegyen még egy lépést. Nézze meg, hogyan fog változni egy másik regiszter tartalma. Tehát menjen végig mindegyiken, ügyeljen arra, hogy az összes megadott bit be van állítva, ahogy mondtam, és egyszerre vannak beállítva a teljes bájtra. A dolgok nem mennek tovább, mint a Visszatérés - a programnak vége.

Nyítás
Most állítsa vissza a szimulációt nullára. Kattintson ide Visszaállítás (Shift+F5). Nyissa meg a szétszerelt listát, most látni fogja, mi történik valójában a vezérlőben. View -> Disassembler. És nem YYAAAA!!! Szerelő!!! SZÖRNYŰ!!! DE KELL. Hogy később, ha valami elromlik, ne hülyéskedjen a kódban, és ne tegyen fel bénább kérdéseket a fórumokon, hanem azonnal szálljon be a zsaruba, és nézze meg, hol van dugó. Nincs ott semmi szörnyű.

Először a sorozat topjai lesznek:

1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 +00000000: 940C002A JMP 0x0000002A Jump +00000002: 940C0034 JMP 0x00000034 Jump +00000004: 940C0034 JMP 0x00000034 Jump +00000006: 940C0034 JMP 0x00000034 Jump +00000008: 940C0034 JMP 0x00000034 Jump +0000000A: 940C0034 JMP 0x00000034 Jump +0000000C: 940C0034 JMP 0x00000034 Jump + 0000000E: 940C0034 JMP 0x00000034 Jump +00000010: 940C0034 JMP 0x00000034 Jump +00000012: 940C0034 JMP 0x00000034 Jump +00000014: 940C0034 JMP 0x00000034 Jump +00000016: 940C0034 JMP 0x00000034 Jump +00000018: 940C0034 JMP 0x00000034 Jump +0000001A: 940C0034 JMP 0x00000034 Jump +0000001C : 940C0034 JMP 0x00000034 Jump +0000001E: 940C0034 JMP 0x00000034 Jump +00000020: 940C0034 JMP 0x00000034 Jump +00000022: 940C0034 JMP 0x00000034 Jump +00000024: 940C0034 JMP 0x00000034 Jump +00000026: 940C0034 JMP 0x00000034 Jump +00000028: 940C0034 JMP 0x00000034 Jump

Ez a megszakítási vektor tábla. Később visszatérünk rá, egyelőre csak nézz és ne feledd, hogy ott van. Az első oszlop a flash cella címe, amelyben a parancs található, a második a parancs kódja, a harmadik parancs mnemonika, ugyanaz az assembler utasítás, a parancs harmadik operandusa. Ja, és az automatikus megjegyzés.
Tehát, ha megnézzük, akkor folyamatos átmenetek vannak. A JMP parancskód pedig négy bájtos, tartalmazza a visszafelé írt ugrási címet - az alacsony címnél az alsó bájtot és a 940C ugrási parancs kódját

Írja ezt a nullát a 0x3F címre. Ha megnézi az I / O nézet oszlopot, látni fogja, hogy a 0x3F cím a SREG regiszter címe - a vezérlő jelzőregisztere. Azok. visszaállítjuk a SREG-et, hogy a program nulla feltételek mellett futhasson.

Itt valójában átmenet van a fő funkcióra. És három parancs után a Main csak elkezdődik. És az átmenet a CALL-on keresztül megy végbe, a címet elmentve a verembe. Ugyanakkor két bájt RAM közepes, és csak 1024 van belőle. =) Nizachot! Valami azonban azt súgja, hogy a main as deklarációja inline int main(void) megoldja ezt a problémát, de még nem próbáltam. Ellenőrizheti magát.

Ez előre nem látható körülmények, például a fő funkcióból való kilépés esetén történik. A vezérlőt hardveres alaphelyzetbe állítással, vagy valószínűbb, hogy egy watchdogból történő visszaállítással ki lehet hozni egy ilyen hurokból. Nos, vagy ahogy fentebb mondtam, javítsuk ki ezeket a helyeket a hex editorban, és menjünk, ahova akarunk. Vegye figyelembe azt is, hogy kétféle JMP és RJMP ugrás létezik, az első egy közvetlen ugrás egy címre. Négy bájtot foglal el, és közvetlen ugrást végezhet a teljes memóriaterületen. A második típusú átmenet - RJMP - relatív. Parancsa két bájtot vesz igénybe, de az aktuális pozícióról (címről) 1024 lépést ugrik előre vagy hátra. A paraméterei pedig az aktuális ponttól való eltolást jelzik. Gyakrabban használt, tk. A vakuban a hely felét foglalja el, és ritkán van szükség hosszú átmenetekre.

1 +00000034: 940C0000 JMP 0x00000000 Ugrás

És ez egy ugrás a kód legelejére. Egyfajta újraindítás. Itt ellenőrizheti, hogy az összes vektor ugrik-e. Ebből a következtetésből - ha most engedélyezed a megszakításokat (alapértelmezetten le vannak tiltva), és van megszakításod, de nincs kezelő, akkor lesz szoftveres visszaállítás - a program a legelejére kerül.

fő funkció. Minden ugyanaz, nem is lehet leírni. Nézze csak a regiszterekben a már kiszámított számot beírja. Fordító előfeldolgozó sziklák!!! Tehát nincsenek "varázslatos" számok!

1 2 3 4 5 6 7 8 9 10 11 12 +00000036: E383 LDI R24,0x33 Azonnali betöltés +00000037: B989 OUT 0x09,R24 Ki a 15. I/O helyre: UBRRH = HI (baudosztó); +00000038: BC10 OUT 0x20,R1 Kimenet a 16. I/O helyre: UCSRA = 0; +00000039: B81B OUT 0x0B,R1 Kimenet a 17. I/O helyre: UCSRB = 1<

És íme a jamb:

1 2 3 +0000003E: E080 LDI R24,0x00 Azonnali betöltés +0000003F: E090 LDI R25,0x00 Azonnali betöltés +00000040: 9508 RET Szubrutin visszatérés

A kérdés az, hogy a fordító miért ad hozzá ilyen csúcsokat? Ez pedig nem más, mint a Return 0, akkor a függvényt int main-nak (void) definiáltuk, így még négy bájtot szartunk el, nem értem mit :) És ha a void main-t (void) csinálod, akkor csak a RET marad, de megjelenik egy figyelmeztetés, hogy ezek szerint a fő funkciónk nem ad vissza semmit. Általában azt csinálsz amit akarsz :)

Nehéz? Úgy tűnik, nem. Kattintson a lépésről lépésre történő végrehajtásra disassembler módban, és nézze meg, hogyan hajtja végre a processzor az egyes utasításokat, ami a regiszterekkel történik. Hogyan zajlik a mozgás a parancsokon és a végső hurokoláson keresztül?

Folytatás pár nap múlva...

Offtop:
Alekszej78 Csináltam egy bővítményt a firefoxhoz, amely megkönnyíti a navigációt a webhelyemen és a fórumon.
Beszélgetés és letöltés,

Mikrokontrollerek(a továbbiakban egyszerűen hívjuk őket MK) egyre népszerűbbek a rádióamatőrök körében. Segítségükkel szinte bármit összeszerelhet - indikátorokat, voltmérőket, háztartási készülékeket (védőeszközök, kapcsolókészülékek, hőmérők ...), fémdetektorokat, különféle játékokat, robotokat stb. a lista nagyon hosszú lehet...

Ezekben a cikkekben megpróbáljuk feltárni AVR mikrokontrollerek cégek ATMEL, tanuljon meg velük dolgozni, fontolja meg a firmware programokat, készítsen egyszerű és megbízható programozót, vegye figyelembe a firmware folyamatát és ami a legfontosabb, az esetlegesen felmerülő problémákat (és nem csak kezdőknek).

Az AVR család mikrovezérlőinek fő paraméterei

mikrokontroller

Flashmemória

RAM memória

EEPROM memória

I/O portok

u kínálat

Az MK AVR mega további paraméterei:

Üzemi hőmérséklet: -55…+125*С
Tárolási hőmérséklet: -65…+150*С
Feszültség a RESET lábon a GND-hez viszonyítva: max 13V
Maximális tápfeszültség: 6,0V
Maximális I/O vezetékáram: 40mA
Maximális áramerősség az elektromos vezetéken VCC és GND: 200mA

ATmega 8X Pinouts


Az ATmega48x, 88x, 168x modellek pinoutja





Pin-hozzárendelések a modellekhez

Pinout ATmega16, 32x modellekhez


Pin-hozzárendelések az ATtiny2313 modellekhez



A cikk végén, a mellékletben ott van adatlapokat egyes mikrokontrollerekhez

FUSE beállító bitek MK AVR

Emlékezik programozott biztosíték 0, nincs programozva– 1. Legyen óvatos a biztosítékok beállításakor, a hibásan beprogramozott biztosíték blokkolhatja a mikrovezérlőt. Ha nem biztos abban, hogy melyik biztosítékot kell programoznia, jobb, ha az MK-t először biztosítékok nélkül villogtatja.

A rádióamatőrök legnépszerűbb mikrokontrollerei a következők ATmega8, majd az ATmega48, 16, 32, ATtiny2313 és mások. A mikrokontrollereket TQFP csomagban és DIP-ben árulják, kezdőknek ajánlom DIP-ben vásárolni. Ha TQFP-t veszel, akkor problémásabb lesz a flashelés, adaptert kell venni vagy gyártani, és forrasztani a táblát. lábuk nagyon közel van egymáshoz. A mikrokontrollereket DIP kiszerelésben tanácsolom, speciális panelekre (aljzatokra) tedd, kényelmes és praktikus, nem kell forrasztani az MK-t, ha relashelni akarod, vagy más kivitelben használni.

Szinte minden modern MK-nak van Az ISP áramkörön belüli programozási képessége, azaz ha a mikrokontrollered az alaplapra van forrasztva, akkor a firmware cseréjéhez nem kell leforrasztanunk a tábláról.

6 érintkező használható a programozáshoz:

VISSZAÁLLÍTÁS- MK bemenet
VCC- Plusz táp, 3-5V, MK-tól függ
GND- Közös vezeték, mínusz teljesítmény.
MOSI- MK bemenet (információs jel MK-ban)
MISO- MK kimenet (információs jel az MK-tól)
SCK- MK bemenet (órajel MK-ban)

Néha az XTAL 1 és XTAL2 kimeneteket is használják, ezekhez a kimenetekhez ragaszkodik a kvarc, ha az MK külső generátorról fog működni, az ATmega 64 és 128 esetén a MOSI és a MISO kimeneteket nem használják az ISP programozáshoz, helyette a MOSI kimenetek a a PE0 láb, és a MISO a PE1. A mikrokontroller programozóhoz való csatlakoztatásakor a csatlakozó vezetékek a lehető legrövidebbek legyenek, és a programozótól az LPT portig tartó kábel sem lehet túl hosszú.

A mikrokontroller jelölése tartalmazhat érthetetlen betűket és számokat, például Atmega 8L 16PU, 8 16AU, 8A PU stb. Az L betű azt jelenti, hogy az MK alacsonyabb feszültségen működik, mint az L betű nélküli MK, általában 2,7 V . A kötőjel vagy a 16PU vagy 8AU szóköz utáni számok az MK-ban lévő oszcillátor belső frekvenciáját jelzik. Ha a biztosítékokat külső kvarcról van beállítva, akkor a kvarcot az adatlap szerinti maximumot meg nem haladó frekvenciára kell állítani, ez ATmega48/88/168 esetén 20MHz, egyéb atmega esetén 16MHz.

A mikrokontroller nevében az első számjegyek a FLASH ROM mennyiségét jelzik kilobájtban, például ATtiny15 - 1 Kb, ATtiny26 - 2 Kb, AT90S4414 - 4 Kb, Atmega8535 - 8 Kb, ATmega162 - 16 Kb, -AT3 Kb ATmega6450 - 64Kb, Atmega128 - 128Kb.

Néha vannak olyan sémák, ahol AT90S nevű mikrokontrollereket használnak ... ezek a mikrovezérlők régi modelljei, amelyek közül néhány modernre cserélhető, például:

AT90S4433 - ATmega8
AT90S8515 - ATmega8515
AT90S8535 - ATmega8535
AT90S2313 – ATtiny2313
ATmega163 - ATmega16
ATmega161 - ATmega162
ATmega323 - ATmega32
ATmega103 - ATmega64/128

Az ATmega 8 több tápcsatlakozóval rendelkezik, digitális - VCC, GND és analóg - AVCC, GND. Szabványos csatlakozásnál mindkét vezetékpár párhuzamosan van kötve, azaz. együtt. Az AVR mikrokontrollerek nem szeretik a nagyfeszültséget, ha a tápegység 6 voltnál nagyobb, akkor meghibásodhatnak. Általában kis teljesítményű 5 voltos feszültségszabályozót használok, KR142EN5 vagy 78L05. Ha a tápfeszültség túl alacsony, akkor az MK nem villog, a program káromkodni fog és hibákat ad (például -24 a PonyProgban).

Ezt be is fejezzük, miközben az interneten kiválaszthatod a neked tetsző áramkört és áttanulmányozhatod, egyúttal mehetsz és megvásárolhatod a kívánt mikrokontrollert. Ezután összeállítunk egy egyszerű és megbízható programozót, megismerkedünk a villogó programokkal és kipróbáljuk vaku MK.