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

[ATMega16] C - Odebranie bajtu z PC na mikrokontrolerze

Altarir 08 Sie 2012 23:32 1145 7
REKLAMA
  • #1 11189580
    Altarir
    Poziom 11  
    Siedzę nad tym już z 3 godziny i wlaśnie skończyły mi sie pomysły:

    Piszę program, który ma wysyłać i odbierać dane przez UART. Wysyłanie danych z mikrokontrolera do PC idzie bezproblemowo, AccessPort ładnie wyświetla to co wysyła mikrokontroler. Problem pojawia się przy odebraniu bajtu z PC. Napisany program po prostu przestaje działać. W AccessPort wpisuje wartość i daje Auto Send co 500ms (próbowałem też z innymi odstępami czasu, jak i bez auto send).

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


    Obsługi LCD jestem pewien, wszystko wyświetla poprawnie: Gdy linijkę
    Kod: C / C++
    Zaloguj się, aby zobaczyć kod

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

    To na LCD mam wyświetloną zmienną test, czyli problem leży w odbieraniu bajtu

    Funkcja USART_ReceiveByte(); też wydaje sie dobrze napisana - tak samo jest w kilku przykładach znalezionych w internecie. A mimo to gdzieś jest jakiś błąd.

    W sumie korzystam AccessPort pierwszy raz w życiu, więc może popełniam jakiś błąd przy jego obsłudze? No ale z drugiej strony, jak inaczej niż Send/AutoSend można by w nim wysłać cokolwiek? ;) A liczniki na pasku u dołu programu pokazują, że coś z komputera jest wysyłane


    Z góry dziękuję za pomoc
  • REKLAMA
  • #2 11189678
    LordBlick
    VIP Zasłużony dla elektroda
    Altarir napisał:
    problem leży w odbieraniu bajtu
    Masz całkowita rację, używasz kodu blokującego (_delay_ms()), który powoduje, ze raczej się nie wstrzelisz w tą chwilę, kiedy wysyłany jest z PC upragniony bajt. Mozesz ew. użyć przerwania ISR(USART_RXC_vect)
    Altarir napisał:
    Kod: text
    Zaloguj się, aby zobaczyć kod
    A to, w/g sztuki, jest do przesunięcia do ustawień projektu w IDE lub do Makefile.
  • REKLAMA
  • Pomocny post
    #3 11189746
    szulat
    Poziom 23  
    LordBlick napisał:
    Altarir napisał:
    problem leży w odbieraniu bajtu
    Masz całkowita rację, używasz kodu blokującego (_delay_ms()), który powoduje, ze raczej się nie wstrzelisz w tą chwilę, kiedy wysyłany jest z PC upragniony bajt.

    Zgadza się, ma rację, ale ty, szanowny lordzie ;) racji nie masz, bo przecież pokazana funkcja USART_ReceiveByte czeka do skutku aż bajt zostanie odebrany, więc delay w niczym nie przeszkodzi.

    W tym kodzie widze dwie potencjalne przyczyny niedziałania:

    - włączone jest przerwanie (bit RXCIE) ale nie ma handlera przerwania, czyli po odebraniu znaku wywołuje się defaultowy handler restartujący procesor

    - nie ustawiono odpowiedniego formatu znaku w uarcie (liczba bitów, bity startu/stopu) więc znak się w ogóle nie odbiera i program czeka w ReceiveByte w nieskończoność
  • Pomocny post
    #4 11189760
    LordBlick
    VIP Zasłużony dla elektroda
    szulat napisał:
    przecież pokazana funkcja USART_ReceiveByte czeka do skutku aż bajt zostanie odebrany, więc delay w niczym nie przeszkodzi.
    Tym niemniej jest szansa na zgubienie danych.
  • #5 11189777
    szulat
    Poziom 23  
    LordBlick napisał:
    Tym niemniej jest szansa na zgubienie danych.

    Masz rację, dlatego twoja rada też jest bardzo przydatna i wskazuje sposób rozwiązania problemu, który objawiłby się wkrótce po rozwiązaniu problemu pierwszego :)
  • REKLAMA
  • #6 11190766
    Altarir
    Poziom 11  
    Po pierwsze, dziekuję za dotychczasowe sugestie :)

    Wyrzucenie delay nic nie zmienia. Nawet jeśli pętla wygląda tak:

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


    to nadal efekt jest taki sam jak poprzednio.

    Natomiast, gdy użyłem ISR(USART_RXC_vect), to wszystko działa poprawnie. Kod wtedy wygląda następująco:

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


    Czyli wyglada na to, że format danych (liczba bitów, parzystość, bit start/stop) wysyłanych z PC jest poprawny.

    Teoretycznie wiec efekt mam osiągnięty (odbieram dane z PC) ale nadal nie daje mi spokoju kwestia niedziałającego USART_ReceiveByte().

    szulat napisał:
    - włączone jest przerwanie (bit RXCIE) ale nie ma handlera przerwania, czyli po odebraniu znaku wywołuje się defaultowy handler restartujący procesor


    to raczej nie jest restart proceesora. Gdyby procesor się restartował, to powinien chyba zacząć cały program od początku, czyli wyświetlić wartość początkową zmiennej test:

    chodzi o ten fragment kodu z pierwszego posta:

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


    A on po prostu zatrzymuje się.

    Inna sprawa: nie bardzo rozumiem, jak miałby wyglądać ten handler. Jeśli używam handlera ISR(USART_RXC_vect) to funkcja USART_ReceiveByte() przestaje być potrzebna. Chyba, że się pogubiłem. Mógłbyś napisać to nieco bardziej łopatologicznie? ;)
  • Pomocny post
    #7 11190829
    Konto nie istnieje
    Poziom 1  
  • REKLAMA
  • #8 11194382
    Altarir
    Poziom 11  
    OK, dziękuje wszystkim za pomoc. Sprawa jest wyjaśniona. Mimo wszystko zdecydowałem, że pozostanę przy przerwaniu - działa bardzo dobrze.
REKLAMA