Elektroda.pl
Elektroda.pl
X
Proszę, dodaj wyjątek www.elektroda.pl do Adblock.
Dzięki temu, że oglądasz reklamy, wspierasz portal i użytkowników.

[mega162] [bascom] nie działa komunikacja z ds1820 i ds18b20

hv222 02 Wrz 2009 21:55 2295 3
  • #1 02 Wrz 2009 21:55
    hv222
    Poziom 15  

    Witam
    Na wstępie chciałbym zaznaczyć iż jestem początkującym programistą i dlatego proszę o wyrozumiałość.
    Robię termometr na lampach nixie, ale nie działa mi poprawnie komunikacja z ds18b20 i ds1820. Problem polega na tym, że na lampach pokazuje się wartość -00.1 tak jak by wyjście czujnika było zwarte bezpośrednio z + , a nie jest . Czujnik jest podpięty pod portb.0 i połączony poprzez rezystor 4.7k do zasilania układu - ok. 5V (próbowałem też podłączyć 1wire pod portd.7 i zmieniałem atmegę na inny egzemplarz ). Jeśli odłączę ten rezystor pomiędzy wyjściem a + to wynik na lampach wychodzi 0.00 i to niezależnie czy użyty jest ds18b20 czy ds1820 (oczywiście po zmianie przeliczania ).
    Atmega162 jest taktowana kwarcem 5MHz podpiętym przez kondensatory 30p do masy. Sterowanie lamp odbywa się przez tranzystory MPSA42. każda katoda lampy jest podłączona do osobnego pinu procesora.

    Czujniki które używam są sprawne (testuję je na płytce testowej bascom AVT 3500 z at90s2313) i działają bez problemu. Program do odczytu jest taki sam (z tą różnicą , że wynik jest prezentowany na lcd a nie na lampach nixie.

    Dodam jeszcze, że napięcie zasilające (dokładnie 4.95V) mega162 i ds1820 jest dobrze filtrowane (kondensator 330µ i 100n )

    oto kod programu na mega162 i nixie

    Code:

    $regfile = "m162def.dat"
    $crystal = 5000000

    Config Porta = Output
    Config Pinb.1 = Output
    Config Pinb.2 = Output
    Config Pinb.3 = Output
    Config Pinb.4 = Output
    Config Pinb.5 = Output
    Config Pinb.6 = Output
    Config Pinb.7 = Output

    Config Portc = Output
    Config Portd = Output
    Config Porte = Output


    Porta = 0
    Portc = 0
    Portd = 0
    Porte = 0
    Portb.1 = 0
    Portb.2 = 0
    Portb.3 = 0
    Portb.4 = 0
    Portb.5 = 0
    Portb.6 = 0
    Portb.7 = 0


    Dim Odczyt(2) As Byte , A As Byte , Disp1 As Byte , Disp2 As Byte , Disp3 As Byte , Disp4 As Byte , B As Integer
    Dim Licznik As Byte , T As Integer , T1 As Integer
     Dim D2 As Integer
    Dim D3 As Integer
    Dim D4 As Integer


    Dim Tmp1 As Integer
    Dim Tmp2 As Integer
    Dim Tmp3 As Integer

    ' disp1 = minus , disp2 = dziesiątki , disp3 = jedności , disp4 = po przecinku :)


     Config 1wire = Portb.0
    '*********************************************************
    '  program   

    Do

    '*********************************************************
    'odczyt z ds18b20/ds1820
       Config 1wire = Portb.0


     1wreset                                                    'reset
     1wwrite &HCC                                               'jedna kostka, więc wykorzystujemy rozkaz SKIP ROM




     1wwrite &H44                                               'dokonaj konwersji
                                                      'przeczekaj czas konwersji
     1wreset                                                    'reset
     1wwrite &HCC                                               'rozkaz adresowy SKIP ROM
     1wwrite &HBE                                               'rozkaz funkcyjny - polecenie odczytu DS18x20
     Odczyt(1) = 1wread(2)                                      'odczytaj dwa pierwsze bajty
     T = Odczyt(2)                                              'przepisz starszy bajt do zmiennej typu Integer
     Shift T , Left , 8                                         'przesuń ten bajt w lewo na wyższe pozycje
     T = T + Odczyt(1)                                          'przepisz - dodaj młodszy bajt
                                                                'teraz w zmiennej T typu Integer jest dziwna "ułamkowa" wartość temperatury
     ' T1 = T / 16        'dla ds18b20                                   
     T1 = T / 2           'dla ds1820





    '**********************************************************
    ' przeliczanie

        Waitms 50

      B = T1


    If B < 0 Then Disp1 = 1 Else Disp1 = 0                      ' sprawdzenie ujemności liczby jeśli jest
                                                                 ' ujemna to potem wyświetli się " - "
      D2 = B / 100                                              'przerobka temperatury
     Disp2 = Abs(d2)                                            'do postaci trawionej
     Tmp1 = D2 * 100                                            'przez lampy nixie
     Tmp2 = B - Tmp1
     D3 = Tmp2 / 10
     Disp3 = Abs(d3)
     Tmp1 = D3 * 10
     Tmp3 = Tmp2 - Tmp1
     D4 = Tmp2 - Tmp1
     Disp4 = Abs(d4)





       '*******************************************************
       
       Portd.6 = 1                                             
       'minus
       If Disp1 = 1 Then Portd.5 = 1 Else Portd.5 = 0
       If Disp1 = 0 Then Portd.5 = 0



       'po przecinku
       If Disp4 = 0 Then Portb.6 = 1 Else Portb.6 = 0
       If Disp4 = 1 Then Porta.2 = 1 Else Porta.2 = 0
       If Disp4 = 2 Then Porta.4 = 1 Else Porta.4 = 0
       If Disp4 = 3 Then Porta.1 = 1 Else Porta.1 = 0
       If Disp4 = 4 Then Porta.0 = 1 Else Porta.0 = 0
       If Disp4 = 5 Then Portb.5 = 1 Else Portb.5 = 0
       If Disp4 = 6 Then Portb.2 = 1 Else Portb.2 = 0
       If Disp4 = 7 Then Portb.1 = 1 Else Portb.1 = 0
       If Disp4 = 8 Then Portb.3 = 1 Else Portb.3 = 0
       If Disp4 = 9 Then Portb.4 = 1 Else Portb.4 = 0

       'jednoiści

       If Disp3 = 0 Then Portd.4 = 1 Else Portd.4 = 0
       If Disp3 = 1 Then Portc.0 = 1 Else Portc.0 = 0
       If Disp3 = 2 Then Portc.1 = 1 Else Portc.1 = 0
       If Disp3 = 3 Then Portc.2 = 1 Else Portc.2 = 0
       If Disp3 = 4 Then Portd.1 = 1 Else Portd.1 = 0
       If Disp3 = 5 Then Portd.0 = 1 Else Portd.0 = 0
       If Disp3 = 6 Then Portb.7 = 1 Else Portb.7 = 0
       If Disp3 = 7 Then Porta.3 = 1 Else Porta.3 = 0
       If Disp3 = 8 Then Portd.2 = 1 Else Portd.2 = 0
       If Disp3 = 9 Then Portd.3 = 1 Else Portd.3 = 0


       'dziesiątki

       If Disp2 = 0 Then Portc.3 = 1 Else Portc.3 = 0
       If Disp2 = 1 Then Porte.0 = 1 Else Porte.0 = 0
       If Disp2 = 2 Then Porte.1 = 1 Else Porte.1 = 0
       If Disp2 = 3 Then Porte.2 = 1 Else Porte.2 = 0
       If Disp2 = 4 Then Portc.7 = 1 Else Portc.7 = 0
       If Disp2 = 5 Then Portc.6 = 1 Else Portc.6 = 0
       If Disp2 = 6 Then Portc.5 = 1 Else Portc.5 = 0
       If Disp2 = 7 Then Porta.6 = 1 Else Porta.6 = 0
       If Disp2 = 8 Then Porta.5 = 1 Else Porta.5 = 0
       If Disp2 = 9 Then Portc.4 = 1 Else Portc.4 = 0



    Loop
    End



    a to kod na at90s2313 i lcd (płytka testowa AVT 3500)
    Code:

    $regfile = "2313def.dat"
    $crystal = 4000000


    'ldc 2*16 podłączony jest następująco :Enable do portb.3 , RS do portb.2 , DB7 do portb.7 , DB6 do portb.6 ,  DB5 do portb.5 i DB4 do portb.4

    Config 1wire = Portd.5
    Dim Odczyt(2) As Byte , , T As Integer , , X As Byte , Y As Byte , Z As Byte , T2 As Byte
     Dim A As Byte , Disp1 As Byte , Disp2 As Byte , Disp3 As Byte , Disp4 As Byte ,
     Dim B As Integer ,
    Dim Licznik As Byte , , T1 As Integer
     Dim D2 As Integer
    Dim D3 As Integer
    Dim D4 As Integer


    Dim Bd(9) As Byte
    Dim Tmp1 As Integer
    Dim Tmp2 As Integer
    Dim Tmp3 As Integer
    ' disp1 = minus , disp2 = dziesiątki , disp3 = jedności , disp4 = po przecinku :)
     Config 1wire = Portd.5


    '*********************************************************
    '  program   ,

    Do

    '*********************************************************
    '  obsługa ds1820
     1wreset                                                    'reset
     1wwrite &HCC                                               'jedna kostka, więc wykorzystujemy rozkaz SKIP ROM
     1wwrite &H44                                               'dokonaj konwersji
                                                      'przeczekaj czas konwersji
     1wreset                                                    'reset
     1wwrite &HCC                                               'rozkaz adresowy SKIP ROM
     1wwrite &HBE                                               'rozkaz funkcyjny - polecenie odczytu DS18x20
     Odczyt(1) = 1wread(2)                                      'odczytaj dwa pierwsze bajty
     T = Odczyt(2)                                              'przepisz starszy bajt do zmiennej typu Integer
     Shift T , Left , 8                                         'przesuń ten bajt w lewo na wyższe pozycje
     T = T + Odczyt(1)                                          'przepisz - dodaj młodszy bajt
    'teraz w zmiennej T typu Integer jest dziwna "ułamkowa" wartość temperatury
      T1 = T / 16                                               ' jak ds18b20                                     'wyraź w stopniach Celsjusza, wynik wpisz do zmiennej Single
     'T1 = T / 2                                                ' jak ds1820
     B = T1
    '**********************************************************
    ' przeliczanie





    If B < 0 Then Disp1 = 1 Else Disp1 = 0                      ' sprawdzenie ujemności liczby jeśli jest
       b = b * 10                                                          ' ujemna to potem wyświetli się " - "
      D2 = B / 100                                              'przerobka temperatury
     Disp2 = Abs(d2)                                            'do postaci trawionej
     Tmp1 = D2 * 100                                            'przez lampy nixie
     Tmp2 = B - Tmp1
     D3 = Tmp2 / 10
     Disp3 = Abs(d3)
     Tmp1 = D3 * 10
     Tmp3 = Tmp2 - Tmp1
     D4 = Tmp2 - Tmp1
     Disp4 = Abs(d4)
     Cls
     Lcd Disp1 ; " . " ; Disp2 ; " . " ; Disp3 ; " . " ; Disp4  'zmienne oddzielone kropką

         Wait 1
     Loop
     End                                                        'end program


    I program na płytkę testową działa mi bez problemu. Przeliczanie temperatury na mega162 też bo jak zamiast odczytu z czujnika wstawię np. coś takiego :
    Code:

    T1 = T1 + 1
    If T1 = 150 Then T1 = -150

    to taki "licznik" działa bez problemu.


    Za pomoc z góry dziękuję
    Pozdrawiam
    Michał

    0 3
  • #2 02 Wrz 2009 22:44
    mos18
    Poziom 15  

    Witam nie czekasz na obliczenie temperatury powinno być waitms 750 .
    Wstaw waitms 750 w miejsce gdzie masz 'przeczekaj czas konwersji

    0
  • #3 03 Wrz 2009 17:00
    hv222
    Poziom 15  

    Witam
    Faktycznie zapomniałem wstawić waitms 750 (przy wcześniejszych próbach było tylko mi przy pisaniu posta uciekło ) jednak teraz kiedy wstawiłem opóźnienie program w ogóle nie reaguje na obecność czujnika (nawet po zmniejszeniu rezystora do 1.2k) czyli mam wynik 00.0
    pozdrawiam
    Michał

    0