Hallo,
ich beschäftige mich zur Zeit mit der Decodierung des DCF-77 Signals. Um ein besseres Verständniss dafür zu bekommen habe ich mir mal einen Beispielcode heruntergeladen um darin die einzelnen Schritte nachvollziehen zu können.
Soweit habe ich auch den Weg der Decodierung verstanden.
Wo ich leider noch nicht dahintergekommen bin, ist das der Beispielcode die richtige Uhrzeit und das Datum anzeigt. Aber auch ab und an dann plötzlich z.B. statt: 16:55:30 Sa 06.04.13 dann 02:45:50 Do 06.09.26 anzeigt. Nach ein paar Minuten dann stimmt die Anzeige wieder.
Hier mal den Code den ich dafür hergenommen habe:
Code:
$regfile = "m32def.dat"
$crystal = 8000000
Signal Alias Pind.7
Config Signal = Input
'Portd.5 = 1
On Timer0 Kurzzeit
On Timer1 Sekundentakt
Config Timer0 = Timer , Prescale = 1024
Enable Timer0
Config Timer1 = Timer , Prescale = 1024
Enable Timer1
Enable Interrupts
Config Lcdbus = 4
Config Lcd = 16 * 2
Config Lcdpin = Pin , Db4 = Porta.2 , Db5 = Porta.3 , Db6 = Porta.4 , Db7 = Porta.5 , E = Porta.1 , Rs = Porta.0
Cls
Cursor Off
Dim I As Byte
Dim A As Byte
Dim B As Byte
Dim C As Byte
Dim Sep As String * 1
Dim H As String * 8
Dim H1 As String * 8
Dim H2 As String * 8
Dim Fehler As Byte
Dim Paritaet As Single: 'Der Wert der auf Paritaet getest wird
Dim Pbit As Byte: 'Das Ergbnis des Paritaetstest
' 0: gerade, 1:ungerade
Dim Preload0 As Word
Dim Preload1 As Word
Dim Bitnummer As Byte
Dim Einbit As Byte
Dim Zaehler As Word
Dim Azaehler As Word
Dim Z(10) As Word: ' Zehn Signalzeiten zur Ermittlung der Vergleichszeit V.
Dim V As Word: ' V= 1,5 * kürzeste Zeit
Dim Sekunden As Byte
Dim Minuten As Byte
Dim Stunden As Byte
Dim Wtag As Byte
Dim Wota(7) As String * 2
Dim Tag As Byte
Dim Monat As Byte
Dim Jahr As Byte
Dim Psekunden As Byte
Dim Pminuten As Byte
Dim Pstunden As Byte
Dim Pwtag As Byte
Dim Ptag As Byte
Dim Pmonat As Byte
Dim Pjahr As Byte
'-----------------------------------------------------------------------------
'Hauptprogramm
Gosub Init
Do
Gosub Stellen
Loop
'-----------------------------------------------------------------------------
Init:
Wota(1) = "Mo"
Wota(2) = "Di"
Wota(3) = "Mi"
Wota(4) = "Do"
Wota(5) = "Fr"
Wota(6) = "Sa"
Wota(7) = "So"
Wtag = 1
Preload1 = 57724 : 'Timer1,1 Sekunde
Preload0 = 178: 'Timer0,1/100 Sekunde
Timer1 = Preload1
While V < 1
For I = 1 To 10
Do
Loop Until Signal = 1
Timer0 = Preload0
Zaehler = 0
Do
Loop Until Signal = 0
Z(i) = Zaehler
Next I
For I = 1 To 10
If Z(i) < Z(1) Then
Swap Z(1) , Z(i)
End If
Next I
V = Z(1) / 2
V = V + Z(1)
Wend
Return
'-----------------------------------------------------------------------------
Stellen:
Gosub Synchro
If Fehler > 0 Then Goto Stellende
Gosub Holebit
If Fehler > 0 Then Goto Stellende
Gosub Synchro
If Fehler > 0 Then Goto Stellende
If Pstunden > 23 Then Fehler = 1
If Pminuten > 59 Then Fehler = 1
If Pwtag < 1 Then Fehler = 1
If Pwtag > 7 Then Fehler = 1
If Ptag < 1 Then Fehler = 1
If Ptag > 31 Then Fehler = 1
If Pmonat < 1 Then Fehler = 1
If Pmonat > 12 Then Fehler = 1
If Fehler > 0 Then Goto Stellende
Stunden = Pstunden
Minuten = Pminuten
Sekunden = 0
Wtag = Pwtag
Tag = Ptag
Monat = Pmonat
Jahr = Pjahr
Stellende:
Return
'-----------------------------------------------------------------------------
Synchro:
'Minutensyncronisation abwarten
Fehler = 0
Do
Zaehler = 0
Timer0 = Preload0
While Signal = 0
If Zaehler > 1000 Then
Fehler = 1: 'kein Empfang
Exit While
Else
Fehler = 0
End If
Wend
Loop Until Zaehler > 130
Return
'-----------------------------------------------------------------------------
Holebit:
'Das Zeittelegramm einlesen
For Bitnummer = 0 To 58
Do
Loop Until Signal = 1
Azaehler = Zaehler
Timer0 = Preload0
Zaehler = 0
Do
Loop Until Signal = 0
Azaehler = Zaehler
' If Azaehler < 11 Then
If Azaehler < V Then
'Low
Einbit = 0
Else
'High
Einbit = 1
End If
Select Case Bitnummer
'Test auf LCD-Display
Case Is = 21
Paritaet = Einbit
Pminuten = Einbit
Case Is = 22
Paritaet = Paritaet + Einbit
Einbit = 2 * Einbit
Pminuten = Pminuten + Einbit
Case Is = 23
Paritaet = Paritaet + Einbit
Einbit = 4 * Einbit
Pminuten = Pminuten + Einbit
Case Is = 24
Paritaet = Paritaet + Einbit
Einbit = 8 * Einbit
Pminuten = Pminuten + Einbit
Case Is = 25
Paritaet = Paritaet + Einbit
Einbit = 10 * Einbit
Pminuten = Pminuten + Einbit
Case Is = 26
Paritaet = Paritaet + Einbit
Einbit = 20 * Einbit
Pminuten = Pminuten + Einbit
Case Is = 27
Paritaet = Paritaet + Einbit
Einbit = 40 * Einbit
Pminuten = Pminuten + Einbit
Case Is = 28
Gosub Ptest : 'Paritaetsprüfung
If Fehler = 1 Then
Fehler = 2
End If
Case Is = 29
Paritaet = Einbit
Pstunden = Einbit
Case Is = 30
Paritaet = Paritaet + Einbit
Einbit = 2 * Einbit
Pstunden = Pstunden + Einbit
Case Is = 31
Paritaet = Paritaet + Einbit
Einbit = 4 * Einbit
Pstunden = Pstunden + Einbit
Case Is = 32
Paritaet = Paritaet + Einbit
Einbit = 8 * Einbit
Pstunden = Pstunden + Einbit
Case Is = 33
Paritaet = Paritaet + Einbit
Einbit = 10 * Einbit
Pstunden = Pstunden + Einbit
Case Is = 34
Paritaet = Paritaet + Einbit
Einbit = 20 * Einbit
Pstunden = Pstunden + Einbit
Case Is = 35
Gosub Ptest : 'Paritaetsprüfung
If Fehler = 1 Then
Fehler = 3
End If
Case Is = 36
Paritaet = Einbit
Ptag = Einbit
Case Is = 37
Paritaet = Paritaet + Einbit
Einbit = 2 * Einbit
Ptag = Ptag + Einbit
Case Is = 38
Paritaet = Paritaet + Einbit
Einbit = 4 * Einbit
Ptag = Ptag + Einbit
Case Is = 39
Paritaet = Paritaet + Einbit
Einbit = 8 * Einbit
Ptag = Ptag + Einbit
Case Is = 40
Paritaet = Paritaet + Einbit
Einbit = 10 * Einbit
Ptag = Ptag + Einbit
Case Is = 41
Paritaet = Paritaet + Einbit
Einbit = 20 * Einbit
Ptag = Ptag + Einbit
Case Is = 42
Paritaet = Paritaet + Einbit
Pwtag = Einbit
Case Is = 43
Paritaet = Paritaet + Einbit
Einbit = 2 * Einbit
Pwtag = Pwtag + Einbit
Case Is = 44
Paritaet = Paritaet + Einbit
Einbit = 4 * Einbit
Pwtag = Pwtag + Einbit
Case Is = 45
Paritaet = Paritaet + Einbit
Pmonat = Einbit
Case Is = 46
Paritaet = Paritaet + Einbit
Einbit = 2 * Einbit
Pmonat = Pmonat + Einbit
Case Is = 47
Paritaet = Paritaet + Einbit
Einbit = 4 * Einbit
Pmonat = Pmonat + Einbit
Case Is = 48
Paritaet = Paritaet + Einbit
Einbit = 8 * Einbit
Pmonat = Pmonat + Einbit
Case Is = 49
Paritaet = Paritaet + Einbit
Einbit = 10 * Einbit
Pmonat = Pmonat + Einbit
Case Is = 50
Paritaet = Paritaet + Einbit
Pjahr = Einbit
Case Is = 51
Paritaet = Paritaet + Einbit
Einbit = 2 * Einbit
Pjahr = Pjahr + Einbit
Case Is = 52
Paritaet = Paritaet + Einbit
Einbit = 4 * Einbit
Pjahr = Pjahr + Einbit
Case Is = 53
Paritaet = Paritaet + Einbit
Einbit = 8 * Einbit
Pjahr = Pjahr + Einbit
Case Is = 54
Paritaet = Paritaet + Einbit
Einbit = 10 * Einbit
Pjahr = Pjahr + Einbit
Case Is = 55
Paritaet = Paritaet + Einbit
Einbit = 20 * Einbit
Pjahr = Pjahr + Einbit
Case Is = 56
Paritaet = Paritaet + Einbit
Einbit = 40 * Einbit
Pjahr = Pjahr + Einbit
Case Is = 57
Paritaet = Paritaet + Einbit
Einbit = 80 * Einbit
Pjahr = Pjahr + Einbit
Case Is = 58
Gosub Ptest : 'Paritaetsprüfung
If Fehler = 1 Then
Fehler = 4
End If
End Select
Next Bitnummer
Return
'-----------------------------------------------------------------------------
Ptest:
'Paritaetstest
Paritaet = Paritaet / 2
Paritaet = Frac(paritaet)
If Paritaet = 0 Then
Pbit = 0: 'gerade Parität
Else
Pbit = 1 : 'Ungerade Parität
End If
If Einbit = Pbit Then
nop
Else
Fehler = 1
End If
Return
'-------------------------------------------------------------
Form:
H = Str(a)
H = "0" + H
H1 = Right(h , 2)
H1 = H1 + Sep
H2 = H1
H = Str(b)
H = "0" + H
H1 = Right(h , 2)
H1 = H2 + H1
H1 = H1 + Sep
H2 = H1
H = Str(c)
H = "0" + H
H1 = Right(h , 2)
H1 = H2 + H1
H = H1
Return
'-------------------------------------------------------------
Sekundentakt:
Timer1 = Preload1
Incr Sekunden
If Sekunden > 59 Then
Sekunden = 0
Incr Minuten
If Minuten > 59 Then
Minuten = 0
Incr Stunden
If Stunden > 23 Then
Stunden = 0
Incr Tag
If Tag > 31 Then
Tag = 0
Incr Monat
If Monat > 12 Then
Monat = 0
Incr Jahr
If Jahr > 99 Then
Jahr = 0
End If
End If
End If
End If
End If
End If
Cls
A = Stunden : B = Minuten : C = Sekunden : Sep = ":"
Gosub Form
Locate 1 , 5
Lcd H
A = Tag : B = Monat : C = Jahr : Sep = "."
Gosub Form
Locate 2 , 9
Lcd H
Locate 2 , 1
Lcd Wota(wtag)
Return
'-----------------------------------------------------------------------------
Kurzzeit:
Timer0 = Preload0
Incr Zaehler
Return
'-----------------------------------------------------------------------------
End
Wäre schön wenn mir da Jemand weiterhelfen könnte. Auch habe ich noch keinen so richtigen Ansatz um in diesen Code noch eine RTC (DS1307) einzubinden m von dieser die Uhrzeit anzeigen zu lassen. Oder ist da besser wenn man die Softclock (geht ziemlich ungenau) immer wieder aus dem RTC syncronisiert? Oder kann man per Interrupt (Sekundentakt aus der RTC) die RTC Sekündlich auslesen und die Infos auf dem LCD anzeigen.
Zu einem späteren Zeitpunkt dann, wenn das Alles per LCD korrekt und zuverlässig funktioniert, soll das Ganze dann auf Dot-Matrix/7-Segment Anzeigen ausgegeben werden.
Die Schaltung für die LED-Anzeigen steht schon und wurde auch schon testweise mit statischen Anzeigen in Betrieb genommen.
Lesezeichen