'Bascom Funkuhr DCF77-88-1

$regfile = "m88def.dat"
$crystal = 8000000

Signal Alias Pind.5
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 = Portb., Db5 = Portb., Db6 = Portb., Db7 = Portb., E = Portc., Rs = Portc.2
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
   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:

= Str(a)
= "0" + H
H1 = Right(, 2)
H1 = H1 + Sep
H2 = H1

= Str(b)
= "0" + H
H1 = Right(, 2)
H1 = H2 + H1
H1 = H1 + Sep
H2 = H1

= Str(c)
= "0" + H
H1 = Right(, 2)
H1 = H2 + H1
= 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