Witajcie!
Robię bibliotekę mającą w zamyśle być modułem do I2C slave, z użyciem atmegi 128A.
Wyizolowałem najmniejszą możliwą część błędu który doświadczyłem, może ktoś z Was będzie miał pomysł co może być przyczyną.
Żebyśmy wiedzieli o czym dyskusja, kod programu:
Urządzenie to podpinam do drugiego mikrokontrolera, robiącego za I2C mastera - i mającego w założeniu wymieniać dane. W tym momencie układ będzie odpowiadał na każdy bajt wartosią 0xA2, ignorując wszystkie wysłane mu bajty.
Jak można zauważyć, z pozoru zbędne jest porównanie jako że ta zmienna bierze z to nigdy nie powinnien wykonać się kod tej instrukcji warunkowej.
Jednakże, po kilku/kilkunastu/więcej transferów na liniach I2C wartość zostaje zmieniona - i program wpada w if'a zawieszając procesor.
Co ciekawe, w programie jest zmienna 'counter'. Zakomentowanie jej inkrementowania w pętli while() powoduje że błąd znika.
Ten sam kod wgrany na ATmegę 644P działa poprawnie.
Assembler dla zainteresowanych:
TL;DR: dostęp do interesujących zmiennych jest atomowy.
Opcje kompilacji:
Testowałem również z -O2, asm podobny, zachowanie takie samo.
Próbowałem również za pomocą atmel studio 6.2 - wynik jest identyczny.
Na początku obsługa TWI była na przerwaniach - indentyczne zachowanie.
Przykład problemu:
Program wgrany na atmegę128a - na płytce easyAVR128. Podłączony do niego drugi procesor wysyła i odbiera z niego dane.
Po kilku transmisjach program wpada w tą pętle.
Zrzut z analizatora logicznego (Saleae 16-ch):
Dołączyłbym również plik z capturem danych z saleae - jednak jest to niedozwolone rozszerzenie załącznika. W zamian tego wrzuciłem na serwer: Klik - pobierz.
Macie jakiekolwiek pomysły co robię źle?
Dzięki z góry za pomoc!
Robię bibliotekę mającą w zamyśle być modułem do I2C slave, z użyciem atmegi 128A.
Wyizolowałem najmniejszą możliwą część błędu który doświadczyłem, może ktoś z Was będzie miał pomysł co może być przyczyną.
Żebyśmy wiedzieli o czym dyskusja, kod programu:
Kod: C / C++
Urządzenie to podpinam do drugiego mikrokontrolera, robiącego za I2C mastera - i mającego w założeniu wymieniać dane. W tym momencie układ będzie odpowiadał na każdy bajt wartosią 0xA2, ignorując wszystkie wysłane mu bajty.
Jak można zauważyć, z pozoru zbędne jest porównanie
Kod: C / C++
Kod: C / C++
Jednakże, po kilku/kilkunastu/więcej transferów na liniach I2C wartość zostaje zmieniona - i program wpada w if'a zawieszając procesor.
Co ciekawe, w programie jest zmienna 'counter'. Zakomentowanie jej inkrementowania w pętli while() powoduje że błąd znika.
Ten sam kod wgrany na ATmegę 644P działa poprawnie.
Assembler dla zainteresowanych:
TL;DR: dostęp do interesujących zmiennych jest atomowy.
Kod: AVR assembler
Opcje kompilacji:
avr-g++ -O0 -std=gnu++1y -Wall -Wextra -Winline -mmcu=atmega128aTestowałem również z -O2, asm podobny, zachowanie takie samo.
Próbowałem również za pomocą atmel studio 6.2 - wynik jest identyczny.
Na początku obsługa TWI była na przerwaniach - indentyczne zachowanie.
Przykład problemu:
Program wgrany na atmegę128a - na płytce easyAVR128. Podłączony do niego drugi procesor wysyła i odbiera z niego dane.
Po kilku transmisjach program wpada w tą pętle.
Zrzut z analizatora logicznego (Saleae 16-ch):
Dołączyłbym również plik z capturem danych z saleae - jednak jest to niedozwolone rozszerzenie załącznika. W zamian tego wrzuciłem na serwer: Klik - pobierz.
Macie jakiekolwiek pomysły co robię źle?
Dzięki z góry za pomoc!
