Reklama

USART u AVR 1. Díl – Teoretický popis

Úvod

Jednotka USART zpřístupňuje u mikrokontrolérů AVR celou třídu nejrozšířenějších komunikačních protokolů (R232, RS485…). Zvu vás na ochutnávku jejích možností. Podíváme se na základy, zprovozníme několik variant komunikací PC – mikrokontrolér a ukážeme si jak mohou komunikovat mikrokontroléry mezi sebou. Vše ukážu přirozeně na funkčních příkladech.

 

USART můžete použít pro komunikaci se širokou paletou průmyslových zařízení, mezi něž patří například drivery motorů nebo laboratorní zdroje. Pomocí jednotky USART jste schopni komunikovat protokoly RS232, RS422 nebo RS485. Dále vám tato jednotka umožní velice snadnou komunikaci s počítačem pomocí převodníků USB-UART. Díky tomu budete moci dávat mikrokontroléru pokyny, případně z něj stahovat nebo “uploadovat” libovolná data. Arduino dokonce využívá bootloaderu, který pomocí USARTu nahrává program do čipu. V neposlední řadě vám USART poslouží ke komunikaci s RFID čtečkami, s GSM moduly a obecně se širokou paletou modulů pro bezdrátový přenos (včetně bluetooth). Často se USART používá pro tunelovou komunikaci skrze náročnější rozhraní (jako třeba ethernet) a někdy dokonce narazíte i na kamerky s UART rozhraním. A mimo to všechno můžete ještě USART použít i pro komunikaci mezi mikrokontroléry. Už z tohoto přehledu je jasné, že použití USARTu patří k základním schopnostem programátora embedded systémů.

 

Celý miniseriál tvoří vlastně komentované příklady. U každého z nich si ukážeme ovládání příslušné části modulu USART. Věřím, že se díky tomuto stylu “neztratíte” v relativně velkém množství informací. Začátečníkům doporučuji postupovat příklad po příkladu od začátku a nejlépe si většinu z nich vyzkoušet a nějak rozvinout. V každém dalším příkladu budu postupně přidávat další funkcionalitu. Zkušenějším radím, aby rovnou přeskočili ke kapitole, která je zajímá a případně přejali příklad jako šablonu a pracovali s ní dle potřeb. Nejprve ve stručnosti popíšu teoretické základy. Popis nebude vyčerpávající, takže kdo bude chtít něčemu rozumět do detailu, bude muset otevřít datasheet. Pár poznámek věnujeme tomu jak připravit spojení mikrokontrolér – PC a dále už se budeme věnovat jen vzorovým příkladům.

V následujících dílech tohoto seriálu si ukážeme tyto příklady:

  • USART – Jednoduché odesílání
  • USART – Jednoduchý příjem
  • USART – Implementace printf
  • USART – Příjem znakových pokynů s přerušením
  • USART – Příjem textovych pokynů s přerušením
  • USART – Příjem s argumenty
  • USART – Odesílání s přerušením
  • USART – Komunikace procesor – procesor
  • USART – MPCM (Multi-processor Communication Mode)
  • USART – Synchronní režim
Stručná teorie

Než se dostaneme k výbavě Atmelu, měli bychom si v rychlosti projít komunikační protokol. Pokud jste úplní začátečníci, doporučuji “googlit” UART nebo RS232. Tento protokol budeme s drobnými odlišnostmi používat. Ke komunikaci slouží dvě linky – Rx a Tx. RS232 obsahuje ještě další linky RTS,CTS,DTR, které slouží k řízení toku dat. Ty nás nebudou zajímat. Na každém mikrokontroléru je vývod označený Rx – to je vstupní pin jednotky UART. Vývod označený Tx je výstupní pin jednotky UART. Každý mikrokontrolér má tedy samostatný přijímač a samostatný vysílač. Propojení dvou mikrokontrolérů vždy vypadá tak, že Tx jednoho mikrokontroléru připojíte do Rx druhého mikrokontroléru. Když spojíte dva Tx, je to špatně (dva výstupy proti sobě), když dva Rx, tak je to také špatně – dva vstupy pro ti sobě. Komunikace může probíhat plně duplexně. To znamená, že oba spojené mikrokontroléry mohou kdykoli začít vysílat zprávu jeden druhému (i zároveň). Oproti RS232 budeme používat logické úrovně 0 a 5 V (respektive 0 a Ucc, pokud budete provozovat mikrokontrolérna jiném napětí). Datová linka je v neutrálním stavu držena výstupem (Tx) v log. 1. Pokud je vše v pořádku a nevysíláte, měli byste na Tx pinu naměřit napětí Ucc. Velice zjednodušeně vypadá komunikace v asynchronním režimu takto: Přijímač stále sleduje linku (svůj RX pin). Jakmile se na ní objeví log. 0 (tzv. “start bit”), spustí “stopky” a v pravidelných okamžicích (třeba každých 104 us) si přečte logickou úroveň na lince a uloží si její hodnotu. Jakmile zaznamená 8 hodnot, zastaví stopky a příjem zprávy je hotov. Vysílač i přijímač musí oba předem vědět v jakých okamžicích stav linky číst, jak bude zpráva dlouhá (nemusí to být vždy 8 bitů) a podobně (viz protokol RS232). Časování se neudává v sekundách ale v baudech za sekundu (tzv “baudrate”), což není žádná složitá jednotka a můžete se na ni dívat jako na bity za sekundu. Nejlépe to pochopíte z ukázek různých zpráv. Několik zpráv v tom nejobyčejnějším formátu můžete vidět na následujícím obrázku.

Obr. 1:- Ukázky několika zpráv. Konfigurace 9600Bd/s, 1 stop bit, žádná parita. start bit je označený jako S a stop bit jako T. Všimněte si že Start bit je vždy v nule, Stop bit vždy v jedničce. Také si všimněte, že ve zprávě se LSB odesílá jako první (data tedy musíte číst zprava).

Obr. 1:- Ukázky několika zpráv. Konfigurace 9600Bd/s, 1 stop bit, žádná parita. start bit je označený jako S a stop bit jako T. Všimněte si, že Start bit je vždy v nule, Stop bit vždy v jedničce. Také si všimněte, že ve zprávě se LSB odesílá jako první (data tedy musíte číst zprava).

Na Obr. 1 vidíte příklad několika zpráv. V první zprávě (bílá) odesíláme hodnotu 0x00, tedy samé nuly. V další zprávě pak postupně hodnoty 1, 2, 3 a 4. Díky tomu můžete pěkně vidět, že řazení zprávy je “odzadu”. Jako první se tedy vysílá LSB – nejméně důležitý bit zprávy. V poslední zprávě (azurová) je hodnota 0xFF tedy samé jedničky. Ve všech zprávách je krásně vidět Start bit (označený “S”), který slouží k synchronizaci. Přijímač na sestupné hraně na začátku Start bitu provede synchronizaci (tedy pozná, kde zpráva začíná). Stop bit (označený “T”) slouží k tomu, aby každá zpráva měla jasný konec a aby se linka vrátila do jedničky. Z jedničky totiž musí začínat start bit další zprávy – to je patrné na dalším obrázku. Na Obr. 2. je několik zpráv s různou konfigurací. První dvě zprávy nesou hodnotu 0x05 (tedy 0b101), zbytek zpráv pak 0x09 (0b1001). Bílý průběh zobrazuje 5bitovou zprávu, 1 stop bit a bez parity. Zelený průběh zobrazuje 6bitovou zprávu, 1 stop bit, bez parity. Modrý průběh je asi nejklasičtější uspořádání, 8 datových bitů, jeden stop bit a žádná parita. Na červeném průběhu je konfigurace 8 datových bitů,1 stop bit a paritní bit (označený “P”). Parita je sudá, takže v tomto případě musí být paritní bit nulový. Oranžový průběh zobrazuje dvě zprávy za sebou ve stejné konfiguraci jako modrý průběh, tedy 8 datových bitů, jeden stop bit a žádná parita. Je na něm pěkně vidět, k čemu slouží stop bit. Kdyby ve zprávě stop bit nebyl, tak by navazoval Start bit nové zprávy rovnou za poslední datový bit předešlé zprávy (který je momentálně 0). Přijímač by tak neměl sestupnou hranu, na kterou se může synchronizovat a nebyl by schopen rozpoznat začátek nové zprávy. Na posledním průběhu je jen pro zajímavost konfigurace 8 datových bitů, dva stop bity a žádná parita. Opět jsou to dvě zprávy těsně za sebou, protože jinak byste dvojici stop bitů nemohli přímo vidět :)

Obr. 2:- Ukázky různé konfigurace zpráv (9600Bd/s). 
bílá - 5bit, Žádná parita, 1 stop bit, data 0x05 
zelená - 6bit, Žádná parita, 1 stop bit, data 0x05 
modrá - 8bit, Žádná parita, 1 stop bit, data 0x09 
červená - 8bit, Sudá parita, 1 stop bit, data 0x09 (dvě zprávy) 
azurová - 8bit, Žádná parita, 2 stop bit, data 0x09 (dvě zprávy)

Obr. 2:- Ukázky různé konfigurace zpráv (9600Bd/s).
bílá – 5bit, Žádná parita, 1 stop bit, data 0x05
zelená – 6bit, Žádná parita, 1 stop bit, data 0x05
modrá – 8bit, Žádná parita, 1 stop bit, data 0x09
červená – 8bit, Sudá parita, 1 stop bit, data 0x09 (dvě zprávy)
azurová – 8bit, Žádná parita, 2 stop bit, data 0x09 (dvě zprávy)

Obr. 3:- při datové rychlosti 9600Bd/s by měl jeden bit odpovídat 1/9600 = 104us. Měříme délku start bitu a vychází přibližně 112us. Neměříme bohužel nejpřesněji (při přesnějším měření by ale nebyla vidět celá zpráva)

Obr. 3: Při datové rychlosti 9600Bd/s by měl jeden bit odpovídat 1/9600 = 104us. Měříme délku start bitu a vychází přibližně 112us. Neměříme bohužel nejpřesněji (při přesnějším měření by ale nebyla vidět celá zpráva)
Na čem se bude pracovat

Ve většině vašich aplikací budete chtít UART použít pro komunikaci mezi mikrokontrolérem a PC. Předpokládám, že dávno nemáte na PC sériový port (COM Port). Pokud náhodou máte a chcete ho použít, stačí vám změnit logické úrovně z mikrokontroléru na logické úrovně RS232. K tomuto účelu se vyrábí integrované obvody a nebo celé moduly (oboje za pár korun, stačí “googlit” pojem RS232-TTL). Velmi často založené na obvodu MAX232 nebo podobných. Z Číny k tomuto účelu dobře poslouží například toto. Jestliže ale na PC nemáte sériový port (a to je typičtější) můžete využít virtuální sériový port (VCP). Existují integrované obvody, které s vnějším světem komunikují pomocí UART (RS232 s 5V log. úrovněmi) a s PC komunikují prostřednictvím USB. V PC se pak zase chovají jako sériový port (proto virtuální). Jediné co potřebujete je vybavit PC příslušným ovladačem pro daný integrovaný obvod. Mezi nejrozšířenější patří produkty firmy FTDI (FT232R a podobné), ale k sehnání jsou i moduly jiných výrobců. Osobně mám otestované CP2102, PL2303 a CH340G. Při nákupu FTDI modulů je obezřetnost na místě. FTDI své čipy chrání. Koupíte-li neoriginální FTDI čip (nebo modul osazený neoriginálním čipem), máte velkou šanci, že prostě nebude s aktuálními ovladači na PC pracovat. Nebudu zabíhat do detailů, ale tak to prostě je. Takže pokud chcete sáhnout po FTDI, budete si muset nejspíš připlatit a koupit si modul z renomovanějších míst než z Číny. Kromě toho je internet plný vykuků, kteří vám klidně budou tvrdit, že modul osazený čipem PL2303 obsahuje FT232RL a podobné hlouposti, což vám přirozeně ztrpčí život, protože si nainstalujete špatné ovladače a nepoběží vám to. Kromě toho vás slušně natáhnou, protože PL2303 stojí v Číně okolo 10 – 20 korun a zdejší prodejce vám ho nacení klidně na 200, tak se nenechte napálit:-) Obecně je toto téma zvlášť bohaté u “Arduino” výrobků. Spousta výrobců těží z toho, že se začátečníci neorientují v problematice. Opatří prodávaný předmět popiskem “pro Arduino” a přirazí si k ceně pár stovek procent. Většina modulů bude pracovat s 5V. I když obvody umí v drtivé většině případů pracovat i s nižším napětím, hardwarová konfigurace modulu to nebude umožňovat. Pokud tedy budete chtít nižší provozní napětí (třeba kvůli čidlům) poohlížejte se po modulu, který umí třeba 3.3 V. A opět pozor na Ebay (čímž vás nechci odradit od nákupu). Prodejci na Ebay (a nejen tam) píší do záhlaví různé nesmysly. Chtějí totiž, aby se jejich produkt objevoval ve výsledcích vyhledávání co nejčastěji. Takže, když bude v hlavičce produktu napsáno 3.3 V, nejspíš to znamená, že má modul navíc výstup ze 3.3V regulátoru. Pokud má opravdu podporovat 3.3 V komunikaci, hledejte na něm nějaký jumper pro přepnutí 5 V nebo 3.3 V.

Programové vybavení PC

Prvně budete na PC pro svůj modul potřebovat ovladač. V Linuxu se mi všechny tři předešlé moduly chytili hned bez dodávání jakéhokoli dalšího ovladače. Na Windows jsem je musel doinstalovat. A i kdyby ne je to triviální a dobře zdokumentovaná záležitost. Pro PL2303 například ZDE a ZDE, pro CP2102 ZDE, ZDE nebo ZDE a pro FTDI ZDE. Dál se vám ke komunikaci bude hodit nějaký terminálový program. Z Linuxu je možné trochu krkolomným způsobem posílat na port data přímo z terminálu, ale kvůli přehlednosti si stejně seženete nějaký terminálový program. Windowsovský Hyperterminal kvůli nepřehlednosti moc nedoporučuji. Zaměřte se raději na Realterm, Termite, Coolterm nebo třeba Putty. Putty není sice nejpřehlednější, ale jako jedinou jsme ji přesvědčili, aby běžela na pořádných datových rychlostech (12 Mbd). Já osobně preferuji program Realterm. Některé terminálové programy umí krom ručního posílání zpráv také posílat a přijímat celé soubory. Takže pak můžete do mikrokontroléru nahrávat různě objemná data, případně z něj stahovat s celkem rozumným komfortem výsledky měření a podobně aniž byste museli umět programovat PC. Chcete-li podrobnější návod, přečtěte si na tomto webu k tomu určený článek.

Nastavení mikrokontroléru

Návod a všechny příklady by měly být bez úprav přenositelné mezi ATmega8, ATmega16, ATmega32 a ATmega64 (včetně verzí s příponou “A”). S drobnou úpravou bitu URSEL by měly být přenositelné na ATtiny2313. S přejmenováním registrů pak na ATmega48, 88, 168, 328 a spoustu dalších. Testoval jsem je na ATmega8A a ATmega16A.

Jednotka USART může ovládat tři piny Rx, Tx a XCK ( PD0, PD1 a PB0 na ATmega16) a může pracovat v synchronním a asynchronním režimu. V synchronním režimu může pracovat jako “Master” (generuje clock na pinu XCK) a nebo jako “Slave” (přijímá clock z pinu XCK). Pokud nastavíte XCK pin jako vstup (v registru DDR), bude pracovat jako “Slave”, pokud nastavíte pin XCK jako výstup, bude pracovat jako “Master”. Synchronní režim se zapíná nastavením bitu UMSEL v registru UCSRC. My se ale zatím synchronním režimem zabývat nebudeme, protože ho použité moduly neumí. Jednotka USART také slouží k nastavení datové rychlosti (Baudrate), což je ústřední veličina. Omezíme se ale pouze na povrchní informace jak baudrate nastavit. K tomu slouží registr UBRR, který se skládá z horní ( UBRRH) a dolní ( UBRRL) části. Do nich můžete zapsat maximálně 12ti bitovou hodnotu (0 – 4095). Ta slouží jako “dělička” clocku procesoru a generuje časovací signál. Koho zajímají detaily, doporučuji si pročíst celou kapitolu USART v datasheetu. Klíčová pro vás bude tabulka č.1 kde máte potřebné rovnice pro správné nastavení baudrate. V asynchronním režimu je možné pomocí bitu U2X v registru UCSRA nastavit tzv. “Double speed”. V tabulce máte proto uvedeny vztahy i pro situaci, kdy je “double speed” režim zapnutý. Aby vám výrobce ulehčil práci, tak shrnul nastavení UBRR do tabulek v sekci 19.12 (v datasheetu). Ve většině případů vám bude stačit mrknout do tabulky a opsat číslo :)

Velice pěknou utilitkou k těmto účelům najdete ZDE. V případě potřeby si nahoře můžete zaklikat různé varianty zobrazení tabulek. Můžete vyplnit frekvence na jakých váš mikrokontrolér pracuje a datové rychlosti pro něž chcete vypočítat hodnoty UBRR. Protože dělení clocku probíhá celočíselně, jsou některé možnosti nedosažitelné (z šesti dělením celým číslem pět prostě neuděláte). Je proto potřeba sledovat, jaká je odchylka reálného baudrate od požadovaného. To je zde znázorněno barevně a je dobré chybu udržovat nízkou dejme tomu pod 1 %. Co je a co není kritická chyba, rozebírá datasheet v sekci 19.8.3 “Asynchronous Operational Range”. Vzhledem k tomu, že budete provozovat mikrokontrolér typicky s interním RC oscilátorem (který sám o sobě zavádí další chybu), je velmi vhodné volit ty varianty kde je odchylka Baudrate pod 0.2 %. Když budete dobře vědět co děláte, tak si můžete dovolit i větší chybu. Pro začátek je to ale nevhodné, protože vám jen přibude prostor pro vznik problémů. Jak pak poznáte, jestli problém vznikl chybně napsaným programem, špatnou datovou rychlostí nebo špatným ovládáním terminálu ?

Detailní popis registrů a bitů, kterými se USART nastavuje, najdete v jiném článku na tomto webu. Nebudu tedy nosit dříví do lesa a psát již napsané. Projděte si jej, prosím. Jak pomocí těchto registrů USART konfigurovat, si budeme ukazovat na příkladech.

 
Autor: Michal Dudka
 

Následující a předchozí příspěvek v kategorii:

 

 
Tajned facebook
 

Za případné chyby v textu, ve zdrojovém kódě, nebo ve schématickém zapojení se omlouváme.
AUTOŘI NEBEROU ŽÁDNOU ODPOVĚDNOST ZA PŘÍPADNÉ ÚJMY NA ZDRAVÍ ČI MAJETKU.