K U R S Mikrokontrolery z rdzeniem ARM, część 17 Interfejsy szeregowe: UART W zwiÄ…zku z tymi trudnoÅ›ciami W każdym systemie mikroprocesorowym zachodzi potrzeba wymiany w dzisiejszych czasach daje siÄ™ za- informacji z otoczeniem na przykÅ‚ad z innymi komputerami, uważyć duże zainteresowanie magi- czy urzÄ…dzeniami peryferyjnymi podÅ‚Ä…czanymi do systemu. stralami szeregowymi (na przykÅ‚ad Najbardziej naturalnym sposobem przesyÅ‚ania danych sÄ… magistrale w komputerach PC równolegÅ‚Ä… ma- gistrala dyskowa ATA zostaÅ‚a zastÄ…- równolegÅ‚e, w których dane przesyÅ‚ane sÄ… jednoczeÅ›nie w porcjach piona przez wydajniejszÄ… magistra- odpowiadajÄ…cych dÅ‚ugoÅ›ci sÅ‚owa maszynowego mikroprocesora. le szeregowÄ… Serial ATA), w któ- Jednak taki sposób przesyÅ‚ania danych jest kÅ‚opotliwy ze wzglÄ™du rych dane przesyÅ‚ane sÄ… bit po bicie za pomocÄ… kilku przewodów. na dużą liczbÄ™ poÅ‚Ä…czeÅ„, gdzie już nawet w przypadku prostego Najprostsze mikrokontrolery, takie 8 bitowego systemu mikroprocesorowego musimy podÅ‚Ä…czyć 8 jak 8051 posiadajÄ… interfejs szere- linii danych, 16 linii adresowych i kilkanaÅ›cie linii sterujÄ…cych. gowy UART, sÅ‚użący do komuni- W przypadku poÅ‚Ä…czenia równolegÅ‚ego z innymi urzÄ…dzeniami kacji z zewnÄ™trznymi urzÄ…dzeniami, na przykÅ‚ad innymi komputerami. zewnÄ™trznymi na przykÅ‚ad dwoma systemami mikroprocesorowymi Mikrokontrolery LPC21xx posiada- znajdujÄ…cymi siÄ™ na przeciwnych koÅ„cach pomieszczenia wiÄ…zaÅ‚oby jÄ… na swoim pokÅ‚adzie dwa inter- siÄ™ z koniecznoÅ›ciÄ… użycia drogich wielożyÅ‚owych przewodów. fejsy transmisji szeregowej UART sÅ‚użące najczęściej do komunikacji z innymi systemami mikroproceso- którym przesyÅ‚ane sÄ… poszczególne strony programowej nie sÄ… kom- rowymi, dwa interfejsy szeregowe bity danych, poczÄ…wszy od bitu patybilne z żadnymi standardami. SPI wykorzystywane do komunika- najmniej znaczÄ…cego do najbardziej Twórcy mikrokontrolerów LPC213x/ cji z pojemnymi urzÄ…dzeniami pa- znaczÄ…cego, a na koniec przesyÅ‚a- 214x poszli trochÄ™ innÄ… drogÄ… miÄ™ci masowych (karty MMC) czy ny jest jeden lub dwa bity stopu i zamiast wymyÅ›lać kolejny nowy innych urzÄ…dzeÅ„, w których wyma- (1). Liczba bitów danych w znaku wspaniaÅ‚y interfejs szeregowy, siÄ™- gane jest przesyÅ‚anie dużej iloÅ›ci może być zmienna i wynosi od 5 gnÄ™li po doskonale sprawdzone danych, dwa interfejsy I2C wyko- do 8, jednak najczęściej przesy- rozwiÄ…zanie i we wnÄ™trzu mikro- rzystywane do komunikacji z wol- Å‚a siÄ™ jeden bajt danych. Ponad- kontrolera zaimplementowali dwa niejszymi urzÄ…dzeniami peryferyj- to na koÅ„cu, przed bitem stopu, UARTY zgodne programowo ze nymi takimi jak pamiÄ™ci EEPROM, może być wysÅ‚any dodatkowy bit standardem przemysÅ‚owym 16550. pomiarowe przetworniki A/C itp. sÅ‚użący do kontroli parzystoÅ›ci. Do charakterystycznych cech tego Dodatkowo w mikrokontrolerach Sposób i szybkość przesyÅ‚ania jed- ukÅ‚adu możemy zaliczyć: 16 bi- LPC214x wbudowano interfejs uni- nego znaku musi być jednakowo towÄ… nadawczo odbiorczÄ… kolejkÄ™ wersalnej magistrali szeregowej zdefiniowany w nadajniku i od- FIFO, zapewniajÄ…cÄ… odpowiednie (USB) wykorzystywanej do komu- biorniku. W przypadku transmisji buforowanie znaków oraz wbudo- nikacji z komputerami PC. Z uwagi z komputerami, jako standardowe wany mechanizm sprzÄ™towej lub na duży stopieÅ„ skomplikowania przyjmuje siÄ™ nastÄ™pujÄ…ce prÄ™dko- programowej kontroli przepÅ‚ywu. programowego magistrali USB, spo- Å›ci transmisji (1200, 2400, 4800, Dodatkowo drugi UART mikrokon- soby programowania kontrolera za- 9600, 19200, 57600, 115200 b/ trolerów LPC21x4/21x6/21x8 posia- wartego w: LPC214x zostanÄ… omó- s). PrÄ™dkość transmisji wyznacza da standardowe linie modemowe wione w oddzielnym cyklu poÅ›wie- siÄ™ poprzez podziaÅ‚ czÄ™stotliwo- (RTS/CTS) obsÅ‚ugiwane caÅ‚kowi- conym temu zagadnieniu. Å›ci taktujÄ…cej ukÅ‚ady peryferyjne cie w sposób sprzÄ™towy. W tab. 4 danego mikrokontrolera w dzielni- przedstawiono zbiór linii interfejsu Porty szeregowe UART ku. Nawet proste mikrokontrolery UART0 i UART1 mikrokontrolera: Dla przypomnienia UART (Uni- 8 bitowe, takie jak 80C2051 czy Linie zaznaczone kolorem sza- versal Asynchronous Receiver Trans- wiÄ™kszość AVR ów posiadajÄ… wbu- rym wystÄ™pujÄ… tylko w drugim mitter) jest kontrolerem szeregowej dowane sprzÄ™towe kontro- transmisji asynchronicznej w której lery transmisji szeregowej, dane przesyÅ‚ane sÄ… bit po bicie umożliwiajÄ…ce duplek- w sposób asynchroniczny (rys. 34), sowÄ… transmisjÄ™ danych czyli poszczególne bity informacji bez udziaÅ‚u mikrokontro- przesyÅ‚ane sÄ… w Å›ciÅ›le okreÅ›lonych lera. SÄ… one zazwyczaj odstÄ™pach czasu. autorskimi rozwiÄ…zaniami Transmisja znaku rozpoczyna producentów danego mi- Rys. 34. Jedna z możliwych ramek przesyÅ‚anych siÄ™ od wysÅ‚ania bitu startu (0), po krokontrolera, dlatego od asynchronicznie za pomocÄ… UART a Elektronika Praktyczna 4/2007 105 K U R S BRE- PAR_ PAR_ STOP_ WORD_ Tab. 4. Linie interfejsów UART0 i UART1 w mikrokontrolerach LPC21xx DLAB AK SEL EN SEL SEL SygnaÅ‚ Linia Linia Opis 7 6 5 4 3 2 1 0 (UART0) (UART1) RXD P0.1 P0.9 Linia po której odbierane sÄ… dane RS232 Rys. 36. Rejestr U1LCR (0xE001000C) TXD P0.0 P0.8 Linia po której nadawane sÄ… dane RS232 U0LCR (0xE000C00C) CTS P0.11 Stan niski na tej linii informuje, że modem jest gotowy do odbio- ru danych nadawanych po linii TXD BREAK ustawienie tego bitu DCD P0.14 Stan niski na tej linii informuje, że modem pomyÅ›lnie nawiÄ…zaÅ‚ powoduje natychmiastowe ustawie- poÅ‚Ä…czenie i dane ze zdalnym hostem mogÄ… być wymieniane. nie linii TXD w stan 0, co skutku- DSR P0.12 Stan niski na tej linii informuje o gotowoÅ›ci modemu do nawiąża- je natychmiastowym przerwaniem nia poÅ‚Ä…czenia. transmisji. DTR P0.13 Stan niski informuje, że UART jest gotowy do nawiÄ…zania poÅ‚Ä…cze- DLAB ustawienie tego bitu nia z modemem. umożliwia dostÄ™p do rejestrów RI P0.15 Stan niski na tej linii informuje, że modem odbiera sygnaÅ‚ dzwo- dzielnika taktujÄ…cego sterownik nienia. transmisji szeregowej. RTS P0.10 Stan niski na tej linii informuje, że UART chce przesÅ‚ać dane do Najczęściej rejestr ten bÄ™dzie- modemu my konfigurować w taki sposób, aby przesyÅ‚ać 8 bitów danych, bez kontrolerze (UART1) w bardziej 5 V napiÄ™cia zasilajÄ…cego. Z punktu kontroli parzystoÅ›ci i z jednym bi- rozbudowanych mikrokontrolerach widzenia mikrokontrolera nie stano- tem stopu. W prostych UART ach 2134/2136/2139/2144/2146/2148. wi to problemu, gdyż jego wejÅ›cia mikrokontrolerów 8 bitowych naj- Nie stanowi to jednak problemu, tolerujÄ… napiÄ™cie 5 V, jednak wy- częściej nie wystÄ™puje bufor zna- gdyż w 99% przypadków wykorzy- maga to stosowania dodatkowego ków i w przypadku, gdy procesor stywać bÄ™dziemy tylko linie RXD zasilacza. W przypadku gdy zależy nie odczyta z rejestru zawartoÅ›ci i TXD. SygnaÅ‚y elektryczne wycho- nam na stosowaniu jednego napiÄ™- znaku zanim zostanie odebrany dzÄ…ce z mikrokontrolera majÄ… war- cia zasilajÄ…cego należy użyć ukÅ‚adu kolejny znak, zostanie on bez- toÅ›ci 0 i 3 V, natomiast w standar- MAX3232, który jest przystosowa- powrotnie stracony. Aby zapobiec dzie RS232 wymagane jest napiÄ™- ny do zasilania napiÄ™ciem 3,3 V. utracie danych w ukÅ‚adzie 16550 cie Ä…12V, dlatego konieczne jest Podczas konfigurowania UART ów wprowadzono bufor (kolejkÄ™ FIFO) podÅ‚Ä…czenie konwertera poziomów należy pamiÄ™tać, aby wybrać odpo- o dÅ‚ugoÅ›ci 16 znaków. Do sterowa- napięć standardu RS232, chociaż- wiedniÄ… funkcjÄ™ alternatywnÄ… portu nia dziaÅ‚aniem kolejki FIFO sÅ‚uży by takiego, jak przedstawiono na za pomocÄ… rejestrów PINSEL. Do rejestr FCR (FIFO Control Register) rys. 35. konfiguracji parametrów transmisji rys. 37. Jeden ukÅ‚ad MAX232 posiada takich jak liczba bitów danych, EN Ustawienie tego bitu po- dwa kanaÅ‚y wejÅ›ciowe i dwa ka- liczba bitów stopu oraz przesyÅ‚a- woduje wÅ‚Ä…czenie kolejki FIFO naÅ‚y wyjÅ›ciowe, a wiÄ™c za pomocÄ… nie bitu kontroli parzystoÅ›ci sÅ‚uży RX_RST Ustawienie tego bitu jednego ukÅ‚adu możemy podÅ‚Ä…czyć rejestr U0LCR (UART0) lub U1LCR powoduje skasowanie wszystkich dwa porty szeregowe. WadÄ… tego (UART1) w skrócie LCR (Line Con- znaków znajdujÄ…cych siÄ™ w kolejce rozwiÄ…zania jest to, że do prawi- trol Register), którego zawartość odbiornika. dÅ‚owej pracy ukÅ‚ad ten wymaga przedstawiono na rys. 36. TX_RST Ustawienie tego bitu WORD_SEL umoż- powoduje skasowanie wszystkich liwia ustawienie dÅ‚ugoÅ›ci znaków znajdujÄ…cych siÄ™ w kolejce znaku od 5 bitów dla nadajnika. 00b do 8 bitów dla 11b RX_LEVEL OkreÅ›la po ilu STOP_SEL ustawie- znakach znajdujÄ…cych siÄ™ w kolejce nie tego bitu powoduje, odbiornika zostanie wygenerowanie że nadawane bÄ™dÄ… dwa przerwanie: bitu stopu, natomiast 00b przerwanie zostanie zgÅ‚o- wyzerowanie tego bitu szone po każdym odebranym zna- spowoduje nadawanie ku. jednego bitu stopu. 01b przerwanie zostanie zgÅ‚o- PAR_EN ustawie- szone po 4 odebranych znakach. nie tego bitu powoduje 10b przerwanie zostanie zgÅ‚o- sprawdzanie i generowa- szone po 8 odebranych znakach. nie bitu parzystoÅ›ci. 11b przerwanie zostanie zgÅ‚o- PAR_SEL bity te szone po 14 odebranych znakach. okreÅ›lajÄ… rodzaj bitu ge- DodatkowÄ… zaletÄ… wprowadzenia nerowanego parzystoÅ›ci: bufora jest możliwość skonfiguro- 00b nieparzysta wania ukÅ‚adu tak, aby nie zgÅ‚a- liczba bitów w znaku RX_LEVEL TX_RST RX_RST EN 01b parzysta liczba 7 6 5 4 3 2 1 0 bitów w znaku Rys. 35. Schemat elektryczny prostego konwertera 10b zawsze 1 Rys. 37. Rejestr U1FCR (0xE0010008) napięć TTL LV< >RS232 11b zawsze 0 U0FCR (0xE000C008) Elektronika Praktyczna 4/2007 106 Pclk Bd żÿ K U R S 16 żÿ (16 żÿ DLL żÿ DLM ) DLL niem dodatkowego rejestru możemy (Line Status Register) sÅ‚uży spraw- 7 6 5 4 3 2 1 0 wyznaczyć wedÅ‚ug wzoru: dzenia statusu ukÅ‚adu i umożliwia Rys. 38. Rejestr U1DLL (0xE0010000) okreÅ›lenie wyżej Pclk U0DLL (0xE000C000) Bd żÿ wspomnianych sta- DIVADDVAL nów, oraz okreÅ›lenie 16 żÿ (16 żÿ DLL żÿ DLM ) żÿ (1 żÿ ) DLM MULVAL bÅ‚Ä™dów w transmisji. 7 6 5 4 3 2 1 0 Rejestr ten nie wystÄ™puje w ory- RDR Stan wysoki oznacza, Rys. 39. Rejestr U1DLM (0xE0010004) ginalnym ukÅ‚adzie 16550, ani że rejestr RBR zawiera prawidÅ‚o- U0DLM (0xE000C004) w mikrokontrolerach LPC213x, jed- wÄ… danÄ…. W momencie odczytania nak oprogramowanie napisane dla wszystkich danych z kolejki FIFO szaÅ‚ on przerwania wraz z każdym LPC213x bÄ™dzie dziaÅ‚ać prawidÅ‚o- zostaje on automatycznie wyzero- nadchodzÄ…cym znakiem, ale dopie- wo w ukÅ‚adach LPC214x, ponieważ wany. ro po odebraniu okreÅ›lonej liczby domyÅ›lnie rejestr FDR jest ustawio- OE (Overrun Error) Bit ten znaków. Uważnemu Czytelnikowi ny tak, by nie wpÅ‚ywaÅ‚ na prÄ™d- jest ustawiany, gdy kolejka FIFO nasuwa siÄ™ pewnie wÄ…tpliwość co kość transmisji ustawionÄ… za po- odbiornika zostaje przepeÅ‚niona siÄ™ stanie, gdy odebrane zostanie mocÄ… rejestrów DLL:DLM. i odebrany znak zostaÅ‚ utracony, mniej znaków niż liczba, która Jeżeli chcemy wysÅ‚ać jakieÅ› wyzerowanie tego bitu nastÄ™pu- powoduje wygenerowanie przerwa- dane przez port szeregowy, mu- je w momencie odczytania rejestru nia? Mianowicie po czasie równym simy je wpisać na koniec kolejki LSR. 3& 4 znaków zostanie wygenerowa- FIFO zapisujÄ…c THR, który stanowi PE (Parity Error) Bit ten jest ne przerwanie od przeterminowania wierzchoÅ‚ek kolejki (rys. 41). ustawiany w przypadku gdy wÅ‚Ä…- (timeout). Do okreÅ›lenia prÄ™dko- czona jest kontrola parzystoÅ›ci THR Å›ci transmisji portów szeregowych i stwierdzono odebranie bÅ‚Ä™dnego 7 6 5 4 3 2 1 0 sÅ‚użą rejestry DLL (rys. 38) oraz znaku. Odczytanie rejestru LSR po- DLM (rys. 39). Rys. 41. Rejestr U1THR (0xE0010000) woduje wyzerowanie tego bitu. PrÄ™dkość transmisji szeregowej U0THR (0xE000C000) FE (Framing Error) Bit ten możemy wyznaczyć wedÅ‚ug nastÄ™- jest ustawiany w przypadku odebra- pujÄ…cego wzoru: Po zapisaniu tego rejestru dane nia bÅ‚Ä™dnego bitu stopu, a zerowa- trafiajÄ… do kolejki FIFO i sukcesyw- ny jest automatycznie w momencie Pclk Bd żÿ nie zostajÄ… wysyÅ‚ane poprzez port odczytania rejestru LSR. 16 żÿ (16 żÿ DLL żÿ DLM ) szeregowy za pomocÄ… linii TX. Od- BI (Break Interrupt) Bit ten gdzie: Bd prÄ™dkość transmi- czytu danych odebranych poprzez jest ustawiany w momencie gdy sji, P czÄ™stotliwość taktowania liniÄ™ RX portu szeregowego może- wszystkie odebrane bity posiadajÄ… clk ukÅ‚adów peryferyjnych. my dokonać odczytujÄ…c zawartość stan 0 . Wyzerowanie tego bitu Należy zwrócić uwagÄ™, że do- rejestru RBR, który zawiera najstar- nastÄ™puje w wyniku odczytania re- Pclk stÄ™p do rejestrów DLL i DLM jest szy znak odebrany poprzez port jestru LSR. Bd żÿ możliwy tylko w przypadku gdy żÿbit żÿ DIVADDVAL znajdujÄ…cy siÄ™ w kolejce THRE Ustawienie tego bitu szeregowy 16 żÿ (16 żÿ DLL żÿ DLM ) (1 ) DLAB w rejestrze LCR jest ustawio- FIFO (rys. 42). oznacza, że rejestr nadajnika THR MULVAL ny. Uzyskanie dokÅ‚adnych standar- jest pusty i możemy do niego wpi- RBR dowych prÄ™dkoÅ›ci transmisji: 9600, sać danÄ… do nadania. 7 6 5 4 3 2 1 0 19200, 115200 itp. jest możliwe TEMT Bit ten jest ustawiany, tylko w przypadku użycia rezonato- Rys. 42. Rejestr U1RBR (0xE0010000) gdy wszystkie dane znajdujÄ…ce siÄ™ ra kwarcowego o czÄ™stotliwoÅ›ci ta- U0RBR (0xE000C000) w kolejce FIFO zostaÅ‚y wysÅ‚ane. kiej, by dzieliÅ‚a siÄ™ ona bez reszty RXFE Ustawienie tego bitu przez standardowe prÄ™dkoÅ›ci trans- Jak można Å‚atwo zauważyć, reje- oznacza wystÄ…pienie jakiegoÅ› bÅ‚Ä™du misji (np. 11,0592 MHz). Czasami stry RBR i THR majÄ… taki sam ad- transmisji odbiornika, okreÅ›lenie nie jest to zbyt wygodne rozwiÄ…- res bazowy a rozróżnienie nastÄ™puje o jaki bÅ‚Ä…d chodzi jest możliwe zanie i chcielibyÅ›my mieć możli- za pomocÄ… sygnaÅ‚u zapisu/odczytu. poprzez zbadanie innych bitów. wość użycia rezonatora o dowol- Oprócz tego, adresy tych rejestrów Bit ten jest zerowany w momencie nej czÄ™stotliwoÅ›ci. Konstruktorzy pokrywajÄ… siÄ™ z rejestrami DLL odczytania rejestru LSR. Philipsa zauważyli ten problem i DLM wyznaczajÄ…cymi prÄ™dkość PoznaliÅ›my już wszystkie reje- i w najnowszych mikrokontrolerach transmisji, a wyboru rejestrów RBR/ stry niezbÄ™dne do napisania pro- LPC214x wprowadzili rejestr (FDR) THR dokonujemy poprzez wyzero- cedur sÅ‚użących do transmisji sze- umożliwiajÄ…cy uzyskanie w zasa- wanie bitu DLAB w rejestrze LCR. regowej, dlatego teraz napiszemy dzie dowolnej prÄ™dkoÅ›ci transmisji Sam dostÄ™p do rejestrów umoż- program (ep8a.zip) (list. 8), który z użyciem rezonatora kwarcowego liwiajÄ…cych wysyÅ‚anie i odbieranie bÄ™dzie pobieraÅ‚ znaki z termina- o dowolnej czÄ™stotliwoÅ›ci. danych nie umożliwia poprawnego la i wyÅ›wietlaÅ‚ je na wyÅ›wietlaczu W mikrokontrolerach LPC214x przesyÅ‚ania danych, ponieważ nie LCD zestawu ZL6ARM. prÄ™dkość transmisji z uwzglÄ™dnie- znamy statusu ukÅ‚adu portu sze- regowego i nie możemy okreÅ›lić MULVAL DIVADDVAL RXFE TEMT THRE BI FE PE OE RDR czy rejestr RBR zawiera odebrane 7 6 5 4 3 2 1 0 7 6 5 4 3 2 1 0 dane, albo czy kolejka FIFO nadaj- Rys. 40. Rejestr U1FDR (0xE0010028) nika jest pusta i możemy przesyÅ‚ać Rys. 43. Rejestr U1LSR (0xE0010014) U0FDR (0xE000C028) do niej kolejne znaki. Rejestr LSR U0LSR (0xE000C014) Elektronika Praktyczna 4/2007 107 K U R S Procedura Uart0Init inicjalizuje List. 8. PrzykÅ‚adowy program demonstrujÄ…cy dziaÅ‚anie UART a #include lpc213x.h pierwszy port szeregowy mikrokon- #include CLcdDisp.h trolera, z prÄ™dkoÅ›ciÄ… transmisji prze- //Ustawienia kontrolera VIC kazywanÄ… jako parametr. PrÄ™dkość #define TXD0_P00_SEL (1<<0) #define RXD0_P01_SEL (1<<2) tÄ™ można wyznaczyć za pomocÄ… //Czetotliwosc PCLK #define PCLK 60000000 makra UART_BAUD, które okreÅ›la //Wyznaczenie predkosci #define UART_BAUD(baud) (unsigned short)(PCLK/(baud*16.0) + 0.5) wartość podzielnika DLL i DLM. #define U0LCR_8Bit_Data 3 W procedurze najpierw ustawiane #define U0LCR_1Bit_Stop 0 #define U0LCR_No_Parity 0 sÄ… funkcje alternatywne dla linii #define U0FCR_14Char_Fifo (3<<6) RXD0 i TXD0, ustawiana jest prÄ™d- /* Inicjalizacja Uart0 */ static void Uart0Init(unsigned short BaudRate) kość oraz tryb transmisji na 8 bi- { tów danych, 1 bit stopu, bez kon- //Wybor RXD i TXD jako funkcja alternatywna PINSEL0 |= TXD0_P00_SEL | RXD0_P01_SEL; troli parzystoÅ›ci. NastÄ™pnie wÅ‚Ä…cza- //Ustawianie predkosci transmisji U0LCR = U0LCR_Divisor_Latch_Access_Bit; ny jest bufor FIFO, który zabezpie- //Ustaw predkosci transmisji U0DLL = (unsigned char)BaudRate; cza nas przed utratÄ… danych. Pro- U0DLM = (unsigned char)(BaudRate>>8); //Ustawienie 8,n,1 cedura Uart0Puts wysyÅ‚a poprzez U0LCR = U0LCR_8Bit_Data | U0LCR_1Bit_Stop | U0LCR_No_Parity; port szeregowy poszczególne znaki //Wlacz fifo U0FCR = U0FCR_FIFO_Enable | U0FCR_14Char_Fifo; Å‚aÅ„cucha tekstowego, aż do napo- //Wylacz przerwania i kasuj flagi przerwan U0IER = 0; tkania znaku koÅ„ca Å‚aÅ„cucha (\0). U0IIR = 0; //Wszystkie znaczniki odebrania znaku Przed wpisaniem znaku do rejestru U0LSR = 0; } THR, w pÄ™tli while oczekujemy na zwolnienie miejsca w kolejce FIFO, //Nadawanie znaku static void Uart0Puts(const char *str) co nastÄ™puje w momencie, gdy bit { //Wysylaj kolejne znaki THRE w rejestrze U0LSR przyjmu- while(*str) { je wartość 1. Funkcja Uart0Gets, //Czekaj az bedzie mozna zapisac do bufora nadajnika while(!(U0LSR & U0LSR_THRE)); pobiera Å‚aÅ„cuch tekstowy z portu //Wyslij znak i przejdz do nast znaku szeregowego, ponieważ dane wpi- U0THR = *str++; } sywać bÄ™dziemy z terminala, koniec } Å‚aÅ„cucha możemy okreÅ›lić w mo- //Odbior znaku mencie, gdy odbierzemy znak (\r). static void Uart0Gets(char *str) Procedura sprawdza stan bitu RDA { char c; w rejestrze U0LSR, którego usta- do { wienie informuje o odebraniu zna- //Czekaj na znak while(!(U0LSR & U0LSR_RDR)); ku, nastÄ™pnie przepisuje ten znak //Odbierz znak c = U0RBR; z rejestru U0RDR do bufora i ocze- //Zapisz znak do bufora kuje na zwolnienie miejsca w bu- *str++ = c; //Czekaj na nadajnik forze nadajnika, po czym przesy- while(!(U0LSR & U0LSR_THRE)); //Nadaj zwrotnie znak Å‚a ten znak z powrotem poprzez U0THR = c; } port szeregowy. Dzieje siÄ™ tak do while(c != \r ); *(str 1) = 0; momentu napotkania znaku koÅ„ca } linii (\r). PrzesyÅ‚anie odebranego znaku z powrotem do portu szere- //Obiekt wyswietlacza LCD CLcdDisp cout; gowego umożliwia zobaczenie tego //Bufor odebranych znakow char buf[256]; co piszemy na terminalu. W funk- /* Funkcja glowna main */ cji głównej main() inicjalizujemy int main(void) port szeregowy z prÄ™dkoÅ›ciÄ… 9600, { Uart0Init(UART_BAUD(9600)); inicjalizujemy wyÅ›wietlacz LCD, Uart0Puts( Mikrokontrolery z rdzeniem ARM cz VIII\r\n ); Uart0Puts( Uart bez systemu przerwan\r\n ); a nastÄ™pnie wypisujemy napis po- Uart0Puts( Wpisz cos i nacisnij Enter\r\n ); while(1) witalny na terminalu. PÄ™tla głów- { na programu odczytuje liniÄ™ tekstu //Pobierz linie Uart0Gets(buf); z terminala, i sprawdza pierwszy //Czy pierwszy znak to 1 if(buf[0] == 1 ) znak Å‚aÅ„cucha, który może zawie- { //Tak wypisz na lcd wiersz 1 rać numer linii, w której mamy cout << pos(1,1) << (buf+1); } wyÅ›wietlić tekst. Jeżeli stwierdzono, //Czy pierwszy znak to 2 że pierwszy znak Å‚aÅ„cucha zawiera else if(buf[0] == 2 ) { liczbÄ™ 1 lub 2, wówczas kolejne //Tak wypisz na lcd wiersz 2 cout << pos(1,2) << (buf+1); znaki wyÅ›wietlane sÄ… w pierwszej } //ani 1 ani 2 lub drugiej linii wyÅ›wietlacza LCD, else { natomiast w przeciwnym przypad- //Jezeli ani 1 ani 2 to wypisz w 1 wierszu ku tekst odebrany z portu szerego- cout << pos(1,1) << buf; } wego jest domyÅ›lnie wypisywany //Wypisz potwierdzenie Uart0Puts( \r\nOK\r\n ); w pierwszej linii. } return 0; Lucjan Bryndza, EP } lucjan.bryndza@ep.com.pl Elektronika Praktyczna 4/2007 108