logo elektroda
logo elektroda
X
logo elektroda
REKLAMA
REKLAMA
Adblock/uBlockOrigin/AdGuard mogą powodować znikanie niektórych postów z powodu nowej reguły.

Programowy Uart, a może 2 x sprzętowy? Co wybrać?

klops_mops 03 Kwi 2010 19:00 2127 11
REKLAMA
  • #1 7916722
    klops_mops
    Poziom 17  
    Witam,

    zmagam się z takim założeniem:
    - Urządzenie A wysyła po Uarcie (9600) dane co ok. 1s, danych jest dość dużo, bo ok 2x200 bajtów, transmisja jest buforowana - nie mogę sobie pozwolić na utratę danych.
    - Urządzenie B wysyła (115200, mogę zmniejszyć do 5600, jeśli to stanowiłoby kłopot) dane w bliżej nie określonym czasie, np. co 4 sekundy, 1 minutę, 10 minut, paczki nie są duże - od 10 do 230 bajtów. Odebrane dane muszę bezwzględnie odebrać! Czyli przydał by się jakiś bufor wejściowy.

    Problem: Jak rozwiązać tę transmisję, by wszystko pewnie działało?

    Moja propozycja rozwiązania: Myślałem by urządzenie A podpiąć na sprzętowy uart, a urządzenie B na programowy, lecz z tego co się orientuję tam nie mam możliwość buforowania transmisji. Zastanawiałem się również nad zastosowaniem uC z dwoma sprzętowymi uartami, i odpowiednio dużą ilością pamięci SRAM przeznaczonej na bufor.

    Proszę o pomoc w wyborze rozwiązania, może polecicie mi jeszcze inne rozwiązanie?

    Dodam jeszcze, że każde paczki danych zakończone są standardowo <CR><LF>, i niestety nie ma żadnego znaku początku ramki. Program poza odbiorem danych będzie je (odpowiednio sprasowane) wyświetlał na LCD oraz wysyłał dalej po którymś z uartów (albo urządzenia A, albo urządzenia B), dane te będą "mocno okrojone" do ok. 50 bajtow.

    Za każdą informację serdecznie dziękuję, pozdrawiam.
  • REKLAMA
  • #2 7916762
    tadzik85
    Poziom 38  
    Najlepiej 2 sprzętowe UARTy. A bufory robi się bardzo prosto. A początek nadawania można wykryć bez problemu. 1 bajt (przerwanie) po odebraniu znacznika końca lub po oczyszczeniu bufora.
  • REKLAMA
  • #3 7917235
    klops_mops
    Poziom 17  
    Dzięki za odp.
    W takim razie wykorzystam jakiegoś AVR'a z 2xUART, właśnie - tylko jakiego?
    Myślałem nad Atmega161, lecz mogę jej podłączyć kwarc max 8MHz, Atmega128 jest zbyt droga i w ogóle zbyt "potężna" do tego zastosowania, no ale wtedy mógłbym się pokusić o dołożenie obsługi kart SD...
    Do odbioru bardziej myślałem o wykorzystaniu

    w Bascomie.
  • #4 7917381
    august_a
    Poziom 21  
    cena za ATmega128 to ok 20zł na parametry które posiada to nie jest zła cena.
    Ale podobną cenę ma at91sam764 itd... A ATmedze dużo brakuje do tych procków.
    Tylko wtedy zapomnij o bascomie.
  • #5 7917468
    klops_mops
    Poziom 17  
    Wiem, w ogóle będę musiał zapomnieć o Bascomie, to już chyba ostatni projekt, gdzie soft jest pisany w tym języku. Od dawna przymierzam się do czegoś innego, ale jakoś nie mogę się wziąć za siebie i przysiąść do tego - polubiłem Bascom ;P

    No ale cóż Bascom już nie rozwija... ;( To kupię Atmege128... :) Dzięki za rady
  • #6 7917540
    excray
    Poziom 41  
    To już chyba lepiej dać dwa tanie AVRy. Jeden odpowiada za jeden port + wszystkie pozostałe czynności a drugi za odbiór drugiego UART + ew. inna drobnica a odebrane dane przesyła pierwszemu po tym jak się on o to zapyta.
  • REKLAMA
  • #7 7917667
    rpal
    Poziom 27  
    ATMega162 kolega potrzebuje, 2 UART-y 16 KB Flash, 1 KB 16MHz zegar no i cena koło 7,5 PLN wszysto w nim jest co trzeba, JTAG też. Szkoda czasu i pamięci na programową obsługę rs232 mozna prościej, szybciej i wydajniej.
  • #8 7917795
    revolt
    Poziom 34  
    A atmega64?
  • REKLAMA
  • #9 7917796
    Konto nie istnieje
    Poziom 1  
  • #10 7917832
    klops_mops
    Poziom 17  
    revolt napisał:
    A atmega64?

    Racja, ona tez ma 2xUart

    Atmega162 - najtaniej znalazłem 10zł brutto, w TQFP44. A do testów przydała by się w DIP, potem może być już SMD w układzie.
  • #11 7918673
    rpal
    Poziom 27  
    Maritex albo TME, dla obudowy TQFP można zawsze użyć przejściówki DIP ma ograniczoną ilość wyprowadzeń jednak do użycia 2xrs232 jest wszystko co trzeba.
  • #12 7931224
    Maciekqbn
    Poziom 15  
    Zgadzam się z kolega rpal.
    Zdarza mi się popełniać konstrukcje w których wykorzystuję 2 x UART, najczęściej właśnie na ATmega162. Spokojnie można zrobić oprogramowanie nawet szybkich transmisji (rzędu 460kbps i więcej, zależnie od zastosowanej częstotliwości zegara), bez ryzyka utraty danych.

    Odbiór robisz na przerwaniach, w procedurze obsługującej przerwanie wrzucasz odebrane dane do bufora okrężnego (czyli odbiór odbywa się 'w tle') a w programie tylko analizujesz bufor, np. coś takiego dla przerwania URXC:

    Usart0rx:
     Bufor_rx0(wsk_z0) = Udr
     Incr Wsk_z0
     If Wsk_z0 > 32 Then Wsk_z0 = 1                             'zawijanie bufora
    Return
    

    Identycznie dla drugiego UART (przerwanie URXC1, dane czytasz z UDR1) oczywiście do osobnego bufora.

    W Twoim przypadku musisz naturalnie zwiększyć długość bufora odpowiednio od odbieranej ilości znaków w jednej transmisji (najlepiej dać bufor o kilka bajtów dłuższy, jeśli może zajść sytuacja, że zaczną przychodzić nowe dane zanim zdążyłeś przeanalizować poprzednia transmisję).


    Do wyciągania danych z bufora możesz użyć czegoś w tym stylu:

    Sub Analiza_Bufora
     Skanuj_buf:
     If Wsk_o0 = Wsk_z0 Then Goto Bufor_end
    
     If Bufor_rx0(wsk_o0) = Adr_cz Then                         'mamy dane z czujnika
      Incr Wsk_o0
      If Wsk_o0 > 32 Then Wsk_o0 = 1
      If Wsk_o0 = Wsk_z0 Then Goto Bufor_end
    
     'tutaj analiza kolejnych komórek bufora 
    
     If Wsk_o0 = Wsk_z0 Then Goto Bufor_end
     Incr Wsk_o0
     If Wsk_o0 > 32 Then Wsk_o0 = 1
     Goto Skanuj_buf
     Bufor_end:
    End Sub
    



    Nadawanie możesz zrobić tez na przerwaniach lub łatwiej w pętli wywołując procedurę wysyłającą pakiet danych. Dane do wysłania umieszczone w bufor_tx(n), ich ilość określona w zmiennej Dlugosc:

    Sub Send_data                                              
     For n = 1 To Dlugosc
      Usart_transmit_buf:
      sbis UCSR0A,UDRE
      rjmp USART_Transmit_buf
      Udr = Bufor_tx(n)
     Next
     Usart_transmit_buf_e:
     sbis UCSR0A,UDRE
     rjmp USART_Transmit_buf_e
    End Sub
REKLAMA