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

[Rozwiązano] ATMega32A - Komunikacja szeregowa, ustanowienie parametrów

Archi^Voo 04 Cze 2018 23:58 738 9
REKLAMA
  • #1 17258850
    Archi^Voo
    Poziom 10  
    Witam

    mam problem z inicjacją komunikacji szeregowej.
    Potrzebuję ustanowić połączenie 9600, słowo: 8 bitów, parity: even, bit stop: 1

    funkcją ustawiam jak niżej:
    Kod: C / C++
    Zaloguj się, aby zobaczyć kod


    wysyłam 0x00

    Kod: C / C++
    Zaloguj się, aby zobaczyć kod


    Kod: C / C++
    Zaloguj się, aby zobaczyć kod


    i zamiast 0x00 otrzymuję:

    ATMega32A - Komunikacja szeregowa, ustanowienie parametrów





    gdy ślę 0x01 otrzymuję:

    ATMega32A - Komunikacja szeregowa, ustanowienie parametrów


    Gdzie tkwi problem?

    Przy domyślnych ustawieniach rejestrów UCSRC i UCSRB przy wysłaniu 0x00 otrzymuję 0xE0 co wygląda na słowo 5 bitowe. Jednak 0x01 daje wtedy też E0. Dopiero 0x02 daje E2. Gdzie popełniam błąd?
  • REKLAMA
  • #3 17258996
    Mandeson
    Poziom 11  
    Kod: C / C++
    Zaloguj się, aby zobaczyć kod
    To to trzeba usunąć. Bit parzystości nie liczy się jako bit danych, a przesyłasz 8 bitów, nie 9.

    Poza tym to:
    Kod: C / C++
    Zaloguj się, aby zobaczyć kod
    włącza 2 bity stopu, a w programie wybrałeś tylko jeden.

    Podsumowując, funkcja do inicjalizacji powinna wyglądać tak:
    Kod: C / C++
    Zaloguj się, aby zobaczyć kod
  • REKLAMA
  • #4 17259053
    Archi^Voo
    Poziom 10  
    wywalenie
    Kod: C / C++
    Zaloguj się, aby zobaczyć kod

    nic nie zmienia

    teraz ustawienia mam jak niżej:
    Kod: C / C++
    Zaloguj się, aby zobaczyć kod


    wysyłam
    Kod: C / C++
    Zaloguj się, aby zobaczyć kod


    a w kompie otrzymuję
    00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 C0


    8 bitów otrzymuję tylko jeżeli nie ustawię nic, jednak nadal nie otrzymuję tego co wysłałem.

    Co ciekawe wysłanie 0xFD daje na odbiorze 00 00 FF 00 00 FF czyli w zależności od tego co wysyłam otrzymuję dane różnej długości. Może to kogoś naprowadzi.
  • REKLAMA
  • Pomocny post
    #5 17259176
    excray
    Poziom 41  
    Jeśli zapisujesz coś do UCSRC to zawsze bit URSEL musi być ustawiony. Poza tym niepotrzebnie obciążasz procesor obliczaniem zawartości rejestrów UBRRH i UBRRL. Jeśli zapisujesz coś do rejestru to zapisz to jednym rzutem, a nie rozbijasz to na naście linijek. Zapisy typu "UCSRC |= (0<<USBS);" nie mają sensu. Taka operacja nic nie zmienia: 0|0=0 a 1|0=1.
  • #6 17259353
    Archi^Voo
    Poziom 10  
    Cytat:
    Jeśli zapisujesz coś do rejestru to zapisz to jednym rzutem


    Święta prawda. To i ostatnie zdanie nasunęło mi trop, który przybliża mnie do rozwiązania. Teraz funkcja wygląda tak:

    Kod: C / C++
    Zaloguj się, aby zobaczyć kod


    i za każdym razem wysyła 8 bitów i otrzymuję 8 bitów - czyli progres.

    Lecz nadal nie otrzymuję tego co wysyłam dla 00 mam C0, dla FF mam DF, a dla 0F dostaję C7.
  • #7 17259388
    Mandeson
    Poziom 11  
    Zamień funkcję na TĄ, nic nie zmieniaj i zobacz co się dzieje:
    Kod: C / C++
    Zaloguj się, aby zobaczyć kod
  • REKLAMA
  • #8 17259415
    Archi^Voo
    Poziom 10  
    Mandeson napisał:
    Zamień funkcję na TĄ i zobacz co się dzieje:

    Kod: c [rozwiń] [zaznacz wszystko]

    void UART_init(unsigned int baud,bool RX,bool TX)
    {
    // ustawienie prędkości
    unsigned int ubrr;
    ubrr=(((F_CPU / (baud * 16UL))) - 1);
    UBRRH = (unsigned char)(ubrr>>8);
    UBRRL = (unsigned char)ubrr;
    // ustawienie rejestru na UCSRC
    UCSRC|= (1<<URSEL);
    // ustawienie bitów parzystości
    UCSRC |= (1<<UPM1);
    // ustawienie ilości bitów danych
    UCSRC |= (1<<UCSZ1) | (1<<UCSZ0);

    if(RX)
    {
    UCSRB |= (1<<RXEN);
    }
    if(TX)
    {
    UCSRB |= (1<<TXEN);
    }
    }


    komplety rozjazd: dla 0x00 otrzymuję 00 00 00 00 00 00 00 00 00 00 00 00 F0

    ustawienie:
    Kod: C / C++
    Zaloguj się, aby zobaczyć kod

    jest bliższe sukcesu - mam powtarzalną długość słowa - nie koniecznie dobrą, ale powtarzalną. Któryś bit jeszcze jest nie tak... Słowo zdaje się być krótsze. Przy wysłaniu tablicy 72 bitowej dostaję nie więcej niż 64 bity.
  • #9 17259470
    Mandeson
    Poziom 11  
    Jaką częstotliwością jest taktowany mikrokontroler?
    Prędkość UART'u 9600 nie działa na 1 MHz. Określony baud rate w AVR nie zadziała na wszystkich częstotliwościach (szczegóły w nocie katalogowej). 9600 może być na 8 MHz, przy czym URBR = 51, 16 MHz, przy czym URBR = 103, ale NIE MOŻE działać np. Na 1 MHz.
    Na 1 MHz da się obsługiwać 4800 bodów
  • #10 17259611
    Archi^Voo
    Poziom 10  
    Dziękuję wszystkim, teraz działa na ustawieniach:
    Kod: C / C++
    Zaloguj się, aby zobaczyć kod


    f procka to 11059200 Hz

    Wydaje mi się, że od początku miałem jakieś chore ustawienia domyślne i zmiana bitu nic nie dawała. Trzeba było po prostu zapisać cały indeks A B i C jw.

    ps. mam jeszcze problem z jedną pętlą ale to osobny temat. Pozdrawiam
REKLAMA