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

Attiny26 - przerwania Timer 0 w C, problem z pętlą główną i ostrzeżeniami

mas24 14 Paź 2014 07:57 1161 5
  • #1 14039713
    mas24
    Poziom 16  
    Witam,

    Jestem początkującym w C (AVR GCC). Przez całe lata programowałem w Bascomie, i przyszedł czas na przesiadkę.

    Na warsztat wziąłem Attiny26 i chciałem zaprogramować jakiś programik z przerwaniami (od Timer 0). Niestety, jak ustawię przerwania, to nie chce wykonywać nic w pętli głównej. W dodatku kompilator pisze ostrzeżenie, ze zastosowany uchwyt SIGNAL jest przestarzały, ale jedyny, który działa. Nie znalazłem w notce, czy Attiny26 ma tryb CTC, tak chętnie używany w innych mikrokontrolerach. Programik ma generować sygnał prostokątny na pinie PB1, ze skokowo przełączanymi, określonymi częstotliwościami.

    Poniżej kod opisywanego programu. W pętli głównej nie działa obsługa przycisków.
    Kod: C / C++
    Zaloguj się, aby zobaczyć kod
  • #2 14039731
    Sparrowhawk
    Poziom 22  
    No właśnie nie stosuje się już SIGNAL, więc powinieneś używać ISR (...). A nie działa zapewne dlatego, że brakuje volatile
    Kod: C / C++
    Zaloguj się, aby zobaczyć kod
    przed deklaracją zmiennej dx.

    A zamiast twojego SIGNAL(...) powinno być:
    Kod: C / C++
    Zaloguj się, aby zobaczyć kod

    Do sprawdzenia jakich nazw przerwań należy użyć dla danej rodziny mikrokontrolerów firmy Atmel warto zajrzeć tutaj: AVR Interrupts
  • #3 14039974
    mas24
    Poziom 16  
    Teraz zadziałało :)

    Zasugerowałem się nazwą przerwania z noty katalogowej Attiny26, tam jest tylko "TIM0_OVF0", a SIGNAL wziąłem z jakiegoś przykładu z netu. Dopiero tabelka na stronie, którą podałeś pokazała, co należy wpisać w ISR.

    Oczywiście dodanie słówka "VOLATILE" także pomogło, tak więc program już działa i mogę przystąpić do kalibracji częstotliwości (ustalenie wartości dx).

    Dzięki :)

    Mam jeszcze pytanko, co do C:
    Jak mam 16-bitową zmienną, jak skopiować 8 najstarszych bitów i wstawić do 8-bitowego rejestru? Wiem, że przez przesuwanie, ale mi to nie bardzo wychodzi.
    Robię tak:
    Kod: C / C++
    Zaloguj się, aby zobaczyć kod

    temp jest 16-bitowa i zawiera jakieś dane, ale mnie interesuje, by 8 najstarszych bitów upchnąć do rejestru OCR1A. 8 najmłodszych jest niepotrzebne.
  • #4 14040436
    M. S.
    Poziom 34  
    Kod: C / C++
    Zaloguj się, aby zobaczyć kod


    Moim zdaniem 8 najstarszych bitów wysyłasz w kosmos.

    Może tak będzie lepiej:

    Kod: C / C++
    Zaloguj się, aby zobaczyć kod
  • #5 14040569
    vonar
    Poziom 28  
    mas24 napisał:
    temp jest 16-bitowa i zawiera jakieś dane, ale mnie interesuje, by 8 najstarszych bitów upchnąć do rejestru OCR1A. 8 najmłodszych jest niepotrzebne.
    Po prostu:
    Kod: C / C++
    Zaloguj się, aby zobaczyć kod

    Przy okazji – zmienną X wykorzystujesz tylko w procedurze obsługi przerwania. Warto w związku z tym zamienić ją z globalnej na lokalną statyczną.
  • #6 14042676
    mas24
    Poziom 16  
    OK, pomogła ostatnia porada z przesuwaniem bitów.
    Co do X, to pozostawię go tam, gdzie jest, gdyż będzie on użyty zarówno w przerwaniach, jak i w pętli głównej "while(1)"

    Dzięki Kolegom za pomoc :)
REKLAMA