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

[atmega8][C]dziwne zachowanie i problem z util/delay.h

bartekb3 08 Lip 2008 22:31 7539 32
  • #1 5325201
    bartekb3
    Poziom 10  
    Przede wszystkim chciałem wszystkim powiedzieć serdeczne WITAM:P

    Tak sie złożyło, że ostatnio zainteresowalem sie programowaniem mikrokontrolerów, troche poczytałem no i wziąłem sie za pisanie pierwszych programów... i tu mam problem z biblioteka delay.h (tak wiem - bylo walkowane nie raz- czytałem odpowiedzi na moje pytanie nie znalazłem)

    Oto kod programu (bardzo ambitnego:D):
    #include <avr/io.h>        
    #define F_CPU 8000000
    #include <util/delay.h>  
    
    #define SET(port,bit) (port |= _BV(bit))
    #define RESET(port,bit) (port &=~_BV(bit))
    #define SWITCH(port,bit) (port ^=_BV(bit))
    
    void Inicjalizacja(void)
    {
    DDRB = 0xFF; // Ustawiamy port B jako wyjścia
    PORTB = 0xFF; // Ustawiamy wyprowadzenia portu B w stan wysoki
    
    
    }
    
    int main(void)
    {
    Inicjalizacja();
    unsigned int i=0;
    while(1) // Rozpoczęcie pętli
    {
    
    PORTB = 0x00;
    for(i=0;i<10000;i++) {
    _delay_ms(30);
    }
    
    PORTB = 0xff;
    for(i=0;i<10000;i++) {
    _delay_ms(30);
    }
    
    
    } // Powrót do początku pętli
    }


    o co chodzi? otóż nie rozumiem w ogóle zachowania funkcji _delay_ms()...
    obojetnie jaka wartosc ms /ilosc przebiegow petli for bym nie wpisal diody i tak migaja z taka sama czestotliwoscia....
    a co najsmieszniejsze jak wrzucilem kod w VMLAB'a i tam jest ok:D
    ma ktoś jakiś pomysł dlaczego tak sie dzieje??

    a i jeszcze jedno pytanie niekumatego... dlaczego program z delay.h trzeba kompilować z optymalizacją??

    Pozdrawiam:D
  • #2 5325217
    adamusx
    Poziom 27  
    Zadeklaruj zmienną i jako volatile unsigned int. .
    Może pomoże :)
  • #3 5325253
    bartekb3
    Poziom 10  
    dalej to samo ;/

    a jeszcze jedno: jak przestawilem sobie atmege na 1MHz ustawilem F_CPU 1000000 i dalem _delay_ms(200) to w ogóle wariowal tzn tak jakby sie na tym delay'u zawieszal:P

    aaaa już doszedłem... musialem wylaczyc watchdog timer'a... ale tu pytanie : dlaczego z wlaczonym nie działa?
  • #5 5325304
    bartekb3
    Poziom 10  
    nie zrozumiałeś... tamto delay_ms nie bylo w petli:P

    a o maksymalnym opoznieniu czytalem:D

    mimo wszystko dzieki:P
  • #7 5326345
    Dr.Vee
    VIP Zasłużony dla elektroda
    Witam,

    bartekb3 napisał:

    a i jeszcze jedno pytanie niekumatego... dlaczego program z delay.h trzeba kompilować z optymalizacją??


    Funkcje _delay używają arytmetyki zmiennoprzecinkowej. W przypadku gdy używasz optymalizacji i w wywołaniach funkcji wartości argumentów są znane w czasie kompilacji (np. są stałe), wtedy kompilator jest w stanie określić liczbę "przebiegów" pętli opóźniającej. Jeśli kompilator nie może, to będzie to liczył AVR w trakcie wykonania programu, również korzystając z liczb zmiennoprzecinkowych (floating point). A to oznacza, że kod wynikowy nagle zajmuje dużo więcej miejsca.

    Pozdrawiam,
    Dr.Vee
  • #8 5328634
    bartekb3
    Poziom 10  
    Dzieki za zainterseowanie i wytłumaczenie:)

    W takim wypadku mam kolejne pytanie ,nie zwiazane z tematem ,ale napisze tutaj zeby nie zasmiecac forum kolejnymi tematami...

    Mianowicie, znacie jakieś stronki skad można pobrać gotowe biblioteki obsługujące np klawiature at wyswietlacze led multipleksowo, diode ir itd?
  • #12 5331566
    bartekb3
    Poziom 10  
    ok dzieki wielkie:P

    i ostatnie moje pytanie, mianowicie planuje sobie w przyszłości zrobić robota moze jakis model -w sumie nie do konca wiem co to bedzie ale jedno ze ma być zdalnie sterowane, czy są jakieś gotowe układy RC?? znalazlem na forum projekt bezprzewodowej klawiatury ktora korzystała z RCT-433-AS ... czy cos takiego nadalo by sie do robota?? ewentualnie jakie inne układy byście polecili?

    apropos istnieją jakies bazy danych układów scalony?? gdzie możnaby własnie znalezc pogrupowane tematycznie scalaki??
  • #14 5332173
    bartekb3
    Poziom 10  
    mi sie chyba pytania nie skończą... otóż kolejny problem: dlaczego nie moge obsługiwać lcd przez PORTC? na D i B moge a na C nie... czytalem zeby wylaczyc jtag ale atmega 8 nie ma jtag'a... wiec??

    i kolejne, troche dziwne... otoz gdy kompiluje w avr-gcc jakis programik z zewnetrzna biblioteka to wywala mi undefined reference to `nazwa funkcji' -wydaje mi sie ze cos z linkerem nie tak ale co dziwne wczesniej wszystko chodzilo bez recznego dolaczania a ostatnio taki komunikat wywala... macie jakis pomysl dlaczego??
  • #15 5332326
    Balu
    Poziom 38  
    1) musi działać - sprawdź połączenia
    2) pewnie coś z linkerem, jak powiesz, jak dołączasz rzeczy, czy robisz sam makefile etc może będzie prościej...a na tą chwilę powiem Ci, ze to coś...z linkerem :D
    Łukasz
  • #16 5332826
    bartekb3
    Poziom 10  
    #  avr-gcc -mmcu=atmega8 skrokowy.c -O1 -o skrokowy

    wywala:
    
    /tmp/ccoYgIw3.o: In function `main':
    skrokowy.c:(.text+0x1a): undefined reference to `lcd_init'
    skrokowy.c:(.text+0x1c): undefined reference to `lcd_clrscr'
    skrokowy.c:(.text+0x36): undefined reference to `lcd_clrscr'
    skrokowy.c:(.text+0x3a): undefined reference to `lcd_putc'
    

    a cos takiego wczesniej działało bez problemu...

    teraz musze wpisywac:

    
    #  avr-gcc -mmcu=atmega8 lcd.c -c -o lcd.o
    #  avr-gcc -mmcu=atmega8 skrokowy.c lcd.o -O1 -o skrokowy
    

    i dopiero daje efekt...

    z tym podlaczaniem lcd do portu C to sprawdzalem 5razy i nie mam pojecia co mu nie pasuje... bo port dziala normalnie mozna nim sterowac itd....
  • #18 5333353
    bartekb3
    Poziom 10  
    zadnego makefile'a nie robie... a dolaczam normalnie tzn
    #include <avr/io.h>
    # define F_CPU 8000000
    #include <util/delay.h>
    #include "lcd.h"
    # define SET(port,bit) (port |= _BV(bit))
    # define RESET(port,bit) (port &=~_BV(bit))
    # define SWITCH(port,bit) (port ^=_BV(bit))
    
    
    int main(void)
    {
    DDRC= 0x0f;
    PORTC=0x00;
    DDRD= 0x00;
    PORTD=0xff;
    lcd_init(LCD_DISP_ON); 
    lcd_clrscr();
    unsigned int i,x;
    
    while(1) // Rozpoczęcie pętli
    {
    PORTC=0x00;
    SET(PORTC,x);
    lcd_clrscr();
    lcd_putc((char)x);
    for( i=0;i<10;i++) {
    _delay_ms(20);
    }
    x++;
    if(x==4) x=0; 
    } // Powrót do początku pętli
    }
  • #19 5333618
    Dr.Vee
    VIP Zasłużony dla elektroda
    Po pierwsze, formatuj kod poprawnie, używając wcięć, łatwiej sie czyta.

    Po drugie, wartość zmiennej "unsigned x" jest użyta przed inicjalizacją. W C tylko zmienne globalne są automatycznie inicjalizowane zerem. Dobrym zwyczajem jest inicjalizacja zmiennej przy deklaracji, czyli
    unsigned x = 0; 

    Użycie opcji -Wall przy kompilacji z łatwością to wyłapuje.

    Po trzecie, skąd biblioteka do lcd ma "wiedzieć", że Ty używasz portu C do komunikacji? Z Twojego kodu to nie wynika.

    Po czwarte - kompilacja wielu plików źródłowych (bez użycia bibliotek) jest możliwa na dwa sposoby:

    avr-gcc -c plik1.c -o plik1.o
    avr-gcc -c plik2.c -o plik2.o
    avr-gcc plik1.o plik2.o -o plik_wynikowy


    lub

    avr-gcc plik1.c plik2.c -o plik_wynikowy


    Po piąte, zacznij używac make, opłaci Ci się :)

    Pozdrawiam,
    Dr.Vee
  • #20 5338270
    bartekb3
    Poziom 10  
    skoro tak mówisz to sie zainteresuje tym makefile'm...

    sluchaj a mógłbyś podać przykład jakiegoś modułu rc? bo szukam to rm rfm i nie moge znalezc...

    Z góry dzięki
  • #22 5339365
    bartekb3
    Poziom 10  
    hmmm... ciekawą rzecz zauważyłem...
    pisze program, który wykorzystuje LCD kompiluje wgrywam i wszystko ladnie chodzi...
    wyl;aczam plytke... wlaczam za jakis czas- program dalej chodzi a lcd nic nie wyświetla... dlaczego?
  • #24 5339787
    bartekb3
    Poziom 10  
    chyba rzeczywiście coś z tymi opóźnieniami było... bo zmieniłem bibliotekę na korzystającą z util/delay.h i teraz wszystko śmiga...

    hehe właśnie przeczytałem datsheet'a od atmegi8 i już wiem dlaczego mi lcd na porcie C nie chciał działać... ponieważ 6 pin jest używany jako reset... :D

    Proszę w przyszłości używać wielkich liter tam gdzie powinny być(początek zdania) i poprawić poprzednie posty.
    [zumek]
  • #25 6735563
    tro.ol
    Poziom 11  
    Dorzuczając się tu.

    Chodzi mi o jak nakrótsze opoznienie (delay) jaki można uzyskać w Atmega16.

    Skoro np mam 1MHz to najkrocej powinno być 1us.

    Jak ją otrzymac? prosiłbym o kod.
  • #28 6736800
    Brutus_gsm
    Poziom 25  
    Najkrótsze opoźnienie jakie można uzyskać, to jeden takt procesora a to jest bardzo mało ;> Można to zrobić poprzez intrukcję assembler'a NOP ;)
  • #29 6749934
    tro.ol
    Poziom 11  
    Czyli instrukcja NOP dla procesora z kwarcem 1MHz, to będzie 1us, nieprawdaz?

    Bo 1MHz=10^-6s, to wychodzi właśnie 1us.

    dobrze rozumuje?
  • #30 6749950
    Brutus_gsm
    Poziom 25  
    tro.ol napisał:
    dobrze rozumuje?

    Tak. Procesor wykonuje milion operacji na sekundę, czyli wykonanie jednej zajmuje mu 1us.
REKLAMA