Czy mozna w jakis sposob utworzyc cos na wzor tablicy bitow, ktora niestety jest zabroniona w BASCOMie? Potrzebne mi to do zapisywania kolejno odebranych bitow sygnalu DCF.
Czy wolisz polską wersję strony elektroda?
Nie, dziękuję Przekieruj mnie tamDIM A as BYTE
DIM B as BYTE
A.B = 1
Config Timer0 = Timer , Prescale = 64
$regfile = "m16def.dat" 'dyrektywa dla mikrokontrolera ATmega16
$crystal = 8000000 'częstotliwość taktowania 8 MHz
Ddra = &B11110000 'PA.7-4 wyjscia wybierajace wyswietlacz, PA.3-2 wejscia przyciskow
Config Portc = Output 'port sterujacy wyswietlaczem
Config Portd.2 = Input
D1 Alias Porta.7 'linie wybierajace wyswietlacz
D2 Alias Porta.6
D3 Alias Porta.5
D4 Alias Porta.4
B1 Alias Pina.3 'przycisk 1 (aktywne 0)
B2 Alias Pina.2 'przycisk 2 (aktywne 0)
Dot Alias Portc.7 'linia ustawiajaca kropke
Dcf_in Alias Pind.2
Porta.3 = 1 'ustawienie rezystorow podciagajacych
Porta.2 = 1 'dla wejsc obslugujacych przyciski
Dim Hours As Byte
Dim Minutes As Byte
Dim Seconds As Byte
Dim 2ms_cntr As Word
Dim Synchronized As Bit 'czy wykryto szczeline synchronizacyjna
Dim Int0_bit As Bit 'pamietana poprzednia wartosc bitu int0
Int0_bit = Dcf_in
Config Int0 = Change
Config Timer2 = Timer , Prescale = 64
Config Timer1 = Timer , Prescale = 1024
Timer2 = 6
Start Timer2
On Int0 Interrupt_dcf
On Timer2 Interrupt_2ms
Enable Interrupts
Enable Int0
Enable Timer2
Do
Loop
End 'koniec programu
Interrupt_2ms:
Timer2 = Timer2 + 6
2ms_cntr = 2ms_cntr + 1
If 2ms_cntr = 500 Then
Gosub Incr_sec
2ms_cntr = 0
End If
Return
Interrupt_dcf:
Waitus 15
If Dcf_in <> Int0_bit Then
If Int0_bit = 0 Then
Stop Timer1
Int0_bit = 1
Else
Timer1 = 0
Start Timer1
Int0_bit = 0
End If
End If
Return
Incr_sec:
Seconds = Seconds + 1
If Seconds >= 60 Then
Seconds = 0
Gosub Incr_min
End If
Return
Incr_min:
Minutes = Minutes + 1
If Minutes >= 60 Then
Minutes = 0
Gosub Incr_hour
End If
Return
Incr_hour:
Hours = Hours + 1
If Hours >= 23 Then
Hours = 0
End If
Return
Incr_hour:
Hours = Hours + 1
If Hours >= 23 Then
Hours = 0
End If
Return
mass85 napisał:... BASCOM nie obsluguje tablic bitow...
Balu napisał:Incr_hour: Hours = Hours + 1 If Hours >= 23 Then Hours = 0 End If Return
Hours = 5
Dim Asd(hours) As Bit
Hours = 4
Asd(hours) = 1
Hours = 1
Asd(hours) = 1
If Dcf_array(1).index = 1 Then Display_values(1) = &B00000110
Else Display_values(1) = &B00111111If((dcf_in = 0) And(dcf_failure = 0) And(synchronized = 1)) Then 'wykryto poczatek przerwy miedzy impulsami
If(timer_val > 50ms And Timer_val < 150ms) Then 'odebrano bit 0
Dcf_array(1).bits_rcvd = 0
Bits_rcvd = Bits_rcvd + 1
Elseif(timer_val >= 150ms And Timer_val < 250ms) Then 'odebrano 1
Dcf_array(1).bits_rcvd = 1
Bits_rcvd = Bits_rcvd + 1
Else
Dcf_failure = 1
Synchronized = 0
End If
Else 'wykryto impuls
If(timer_val > 2000ms Or Timer_val < 600ms) Then 'niepoprawna przerwa miedzy impulsami
Set Dcf_failure
Bits_rcvd = 0
Reset Synchronized
Elseif(timer_val > 1500ms) Then 'mamy bit synchronizacyjny
Set Synchronized
If(bits_rcvd = 58 And Dcf_failure = 0) Then Gosub Change_time
Reset Dcf_failure
Bits_rcvd = 0
End If
End If
Error : 46 Line : 158 Assignment error [ELSE DISPLAY_VALUES(1): 0 &B00111111: 112] , in File : F:\STUDIA\DCF\PROGRAM\NONAME2.BAS
Error : 44 Line : 269 2 variables expected , in File : F:\STUDIA\DCF\PROGRAM\NONAME2.BAS
Error : 1 Line : 270 Unknown statement [IF(TIMER_VAL > 50MS AND TIMER_VAL < 150MS) THEN] , in File : F:\STUDIA\DCF\PROGRAM\NONAME2.BAS
Error : 323 Line : 273 Label too long [150MS AND TIMER_VAL < 250MS) THEN] , in File : F:\STUDIA\DCF\PROGRAM\NONAME2.BAS
Error : 46 Line : 273 Assignment error [ELSEIF(TIMER_VAL >): 0 150MS AND TIMER_VAL < 250MS) THEN: 0] , in File : F:\STUDIA\DCF\PROGRAM\NONAME2.BAS
Error : 1 Line : 284 Unknown statement [IF(TIMER_VAL > 2000MS OR TIMER_VAL < 600MS) THEN] , in File : F:\STUDIA\DCF\PROGRAM\NONAME2.BAS
Error : 1 Line : 288 Unknown statement [ELSEIF(TIMER_VAL > 1500MS) THEN] , in File : F:\STUDIA\DCF\PROGRAM\NONAME2.BAS
Error : 44 Line : 290 2 variables expected , in File : F:\STUDIA\DCF\PROGRAM\NONAME2.BAS
Error : 28 Line : 293 IF THEN expected , in File : F:\STUDIA\DCF\PROGRAM\NONAME2.BAS
Error : 7 Line : 293 IF THEN expected [END IF in source 293] , in File : F:\STUDIA\DCF\PROGRAM\NONAME2.BAS
Error : 28 Line : 295 IF THEN expected , in File : F:\STUDIA\DCF\PROGRAM\NONAME2.BAS
Error : 7 Line : 295 IF THEN expected [END IF in source 295] , in File : F:\STUDIA\DCF\PROGRAM\NONAME2.BAS
$regfile = "m16def.dat" 'dyrektywa dla mikrokontrolera ATmega16
$crystal = 8000000 'częstotliwość taktowania 8 MHz
Ddra = &B11110000 'PA.7-4 wyjscia wybierajace wyswietlacz, PA.3-2 wejscia przyciskow
Config Portc = Output 'port sterujacy wyswietlaczem
Config Portd.2 = Input
D1 Alias Porta.7 'linie wybierajace wyswietlacz
D2 Alias Porta.6
D3 Alias Porta.5
D4 Alias Porta.4
B1 Alias Pina.3 'przycisk 1 (aktywne 0)
B2 Alias Pina.2 'przycisk 2 (aktywne 0)
Porta.2 = 1
Porta.3 = 1
Dot Alias Portc.7 'linia ustawiajaca kropke
Dcf_in Alias Pind.2
Porta.3 = 1 'ustawienie rezystorow podciagajacych
Porta.2 = 1 'dla wejsc obslugujacych przyciski
Dim Hours As Byte
Dim Minutes As Byte
Dim Seconds As Byte
Dim 2ms_cntr As Word
Dim Display_nr As Byte
Dim Umode As Byte 'zmienna trybu
Dim Dcf_allowed As Bit 'czy mozna sie synchronizowac z DCF
Dim Display_values(4) As Byte 'tablica danych do wyswietlenia
Dim Temp As Byte
Dim Temp_segment As Byte
Dim Timer_val As Word
Dim Dcf_array(8) As Byte 'tablica bitow odebranych
Dim Synchronized As Bit 'czy wykryto szczeline synchronizacyjna
Dim Int0_bit As Bit 'pamietana poprzednia wartosc bitu int0
Dim Dcf_failure As Bit 'flaga ustawiana, gdy wystapil jakikolwiek blad odbioru ramki
Dim Bits_rcvd As Byte 'liczba odebranych bitow DCF
Dim Index As Byte 'pomocnicza zmienna
Int0_bit = Dcf_in
Const 50ms = 234 'jeszcze nieprawidlowe liczby
Const 150ms = 76867
Const 250ms = 2344
Const 1500ms = 3213244
Const 2000ms = 45454544
Config Int0 = Change
Config Timer2 = Timer , Prescale = 64
Config Timer1 = Timer , Prescale = 1024
Timer2 = 6
Start Timer2
Hours = 12
Minutes = 0
Seconds = 0
2ms_cntr = 0
Umode = 0
Dcf_allowed = 1
Display_nr = 1
On Int0 Interrupt_dcf
On Timer2 Interrupt_2ms
Enable Interrupts
Enable Int0
Enable Timer2
'************************************************
'poczatek glownej petli
'************************************************
Do
If B1 = 0 Then ' Obsluga Przycisku 1(zmiana Trybu)
Waitms 20
If B1 = 0 Then
Umode = Umode + 1
If Umode > 5 Then Umode = 0
Bitwait B1 , Set
End If
End If '===========
Select Case Umode
Case 0 :
'tryb zegara
Temp = Makebcd(hours)
Temp_segment = Temp And &B00001111 'jednostki godzin
Temp_segment = Lookup(temp_segment , 7seg_code) 'odczyt kodu cyfry
Display_values(3) = Temp_segment
Temp_segment = Temp / 16
Temp_segment = Lookup(temp_segment , 7seg_code) 'odczyt kodu cyfry
Display_values(4) = Temp_segment 'dziesiatki godzin
Temp = Makebcd(minutes)
Temp_segment = Temp And &B00001111 'jednostki minut
Temp_segment = Lookup(temp_segment , 7seg_code) 'odczyt kodu cyfry
Display_values(1) = Temp_segment
Temp_segment = Temp / 16
Temp_segment = Lookup(temp_segment , 7seg_code) 'odczyt kodu cyfry
Display_values(2) = Temp_segment 'dziesiatki minut
Temp = Seconds Mod 2
If Temp = 0 Then
Display_values(3) = Display_values(3) And &B01111111
Display_values(3) = Display_values(3) Or &B10000000
End If
If Temp = 1 Then
Display_values(3) = Display_values(3) And &B01111111
End If
If Synchronized = 1 Then
Display_values(1) = Display_values(1) And &B01111111
Display_values(1) = Display_values(1) Or &B10000000
End If
Case 1:
If B2 = 0 Then ' Obsluga Przycisku 2(zmiana wartosci)
Waitms 20
If B2 = 0 Then Toggle Dcf_allowed
Bitwait B2 , Set
End If '===========
Display_values(4) = &B00111111 'kod litery D
Display_values(3) = &B00111001 'kod litery C
Display_values(2) = &B01110001 'kod litery F
If Dcf_allowed = 1 Then
Display_values(1) = &B00000110 'kod cyfry 1
Else
Display_values(1) = &B00111111 'kod cyfry 0
End If
Case 2:
'ostatnio odebrany bit
Index = Bits_rcvd - 1
If Index > 59 Then Index = 59
Temp = Makebcd(index)
Temp_segment = Temp And &B00001111 'jednostki nr bitu
Temp_segment = Lookup(temp_segment , 7seg_code) 'odczyt kodu cyfry
Display_values(3) = Temp_segment
Temp_segment = Temp / 16
Temp_segment = Lookup(temp_segment , 7seg_code) 'odczyt kodu cyfry
Display_values(4) = Temp_segment 'dziesiatki numeru bitu
Display_values(2) = &B01000000 ' Kod Myslnika
If Dcf_array(1).index = 1 Then Display_values(1) = &B00000110
'If Dcf_array(1).index = 0 Then Display_values(1) = &B00111111
Else Display_values(1) = &B00111111
Case 3: ' tryb nastawy godzin
Display_values(4) = &B01110110 'kod litery H
Display_values(3) = &B01110110 'kod litery H
Temp = Makebcd(hours) 'wyswietla aktualna godzine
Temp_segment = Temp And &B00001111 'jednostki godzin
Temp_segment = Lookup(temp_segment , 7seg_code) 'odczyt kodu cyfry
Display_values(1) = Temp_segment
Temp_segment = Temp / 16
Temp_segment = Lookup(temp_segment , 7seg_code) 'odczyt kodu cyfry
Display_values(2) = Temp_segment 'dziesiatki godzin
If B2 = 0 Then ' Obsluga Przycisku 2(zmiana wartosci)
Waitms 20
If B2 = 0 Then Gosub Incr_hour
Bitwait B2 , Set
End If
Case 4: ' tryb nastawy minut
Display_values(4) = &B00110111 'kod litery M
Display_values(3) = &B00110111 'kod litery M
Temp = Makebcd(minutes) 'wyswietla aktualna minute
Temp_segment = Temp And &B00001111 'jednostki minut
Temp_segment = Lookup(temp_segment , 7seg_code) 'odczyt kodu cyfry
Display_values(1) = Temp_segment
Temp_segment = Temp / 16
Temp_segment = Lookup(temp_segment , 7seg_code) 'odczyt kodu cyfry
Display_values(2) = Temp_segment 'dziesiatki minut
If B2 = 0 Then ' Obsluga Przycisku 2(zmiana wartosci)
Waitms 20
If B2 = 0 Then Gosub Incr_min
Bitwait B2 , Set
End If
Case 5: ' tryb nastawy sekund
Display_values(4) = &B01101101 'kod litery S
Display_values(3) = &B01101101 'kod litery S
Temp = Makebcd(seconds) 'wyswietla aktualna sekunde
Temp_segment = Temp And &B00001111 'jednostki sekund
Temp_segment = Lookup(temp_segment , 7seg_code) 'odczyt kodu cyfry
Display_values(1) = Temp_segment
Temp_segment = Temp / 16
Temp_segment = Lookup(temp_segment , 7seg_code) 'odczyt kodu cyfry
Display_values(2) = Temp_segment 'dziesiatki sekund
If B2 = 0 Then ' Obsluga Przycisku 2(zmiana wartosci)
Waitms 20
If B2 = 0 Then Seconds = 0
Bitwait B2 , Set
End If
End Select
Loop
End
'************************************************
'koniec programu
'************************************************
Interrupt_2ms:
Timer2 = Timer2 + 6 ' Obsluga Timera
Enable Interrupts
2ms_cntr = 2ms_cntr + 1
If 2ms_cntr = 500 Then
Gosub Incr_sec
2ms_cntr = 0
End If
'obsluga wyswietlacza
Display_nr = Display_nr + 1
If Display_nr > 4 Then Display_nr = 1
Select Case Display_nr
Case 1:
Reset D4
Portc = Display_values(display_nr)
Set D1
Case 2:
Reset D1
Portc = Display_values(display_nr)
Set D2
Case 3:
Reset D2
Portc = Display_values(display_nr)
Set D3
Case 4:
Reset D3
Portc = Display_values(display_nr)
Set D4
End Select
Return
'************************************************
Interrupt_dcf:
Waitus 15 'eliminacja zaklocen impulsowych
If Dcf_in <> Int0_bit Then
Stop Timer1
Timer_val = Timer1
Timer1 = 0
Start Timer1
Int0_bit = Dcf_in
If((dcf_in = 0) And(dcf_failure = 0) And(synchronized = 1)) Then 'wykryto poczatek przerwy miedzy impulsami
If(timer_val > 50ms And Timer_val < 150ms) Then 'odebrano bit 0
Dcf_array(1).bits_rcvd = 0
Bits_rcvd = Bits_rcvd + 1
Elseif(timer_val >= 150ms And Timer_val < 250ms) Then 'odebrano 1
Dcf_array(1).bits_rcvd = 1
Bits_rcvd = Bits_rcvd + 1
Else
Dcf_failure = 1
Synchronized = 0
End If
Else 'wykryto impuls
If(timer_val > 2000ms Or Timer_val < 600ms) Then 'niepoprawna przerwa miedzy impulsami
Set Dcf_failure
Bits_rcvd = 0
Reset Synchronized
Elseif(timer_val > 1500ms) Then 'mamy bit synchronizacyjny
Set Synchronized
If(bits_rcvd = 58 And Dcf_failure = 0) Then Gosub Change_time
Reset Dcf_failure
Bits_rcvd = 0
End If
End If
End If
Return
'************************************************
Change_time:
Dim Dcf_mins As Byte
Dim Dcf_hours As Byte
Dim Crc As Bit
Dim I As Byte
Index = 21
For I = 0 To 6
Crc = Crc + Dcf_array(1).index
Dcf_mins.i = Dcf_array(1).index
Index = Index + 1
Next
If Crc <> Dcf_array(1).28 Then Return
Dcf_mins = Makedec(dcf_mins)
If Dcf_mins > 60 Then Return
Index = 29
For I = 0 To 5
Crc = Crc + Dcf_array(1).index
Dcf_hours.i = Dcf_array(1).index
Index = Index + 1
Next
If Crc <> Dcf_array(1).35 Then Return
Dcf_hours = Makedec(dcf_hours)
If Dcf_hours > 24 Then Return
Hours = Dcf_hours
Minutes = Dcf_mins
Seconds = 0
Return
'************************************************
Incr_sec:
Seconds = Seconds + 1
If Seconds > 59 Then
Seconds = 0
Gosub Incr_min
End If
Return
Incr_min:
Minutes = Minutes + 1
If Minutes > 59 Then
Minutes = 0
Gosub Incr_hour
End If
Return
Incr_hour:
Hours = Hours + 1
If Hours > 23 Then
Hours = 0
End If
Return
'************************************************
7seg_code:
Data &B00111111 , &B00000110 , &B01011011 , &B01001111 , &B01100110,
Data &B01101101 , &B01111101 , &B00000111 , &B01111111 , &B01101111mass85 napisał:Niestety znow mam problem z kompilatorem.
Pluje sie o prosta skladnie:If Dcf_array(1).index = 1 Then Display_values(1) = &B00000110 Else Display_values(1) = &B00111111
If Dcf_array(1).index = 1 Then
Display_values(1) = &B00000110
Else
Display_values(1) = &B00111111
End If
'w 1 linii
If Dcf_array(1).index = 1 Then : Display_values(1) = &B00000110 : Else : Display_values(1) = &B00111111 : End If
If((dcf_in = 0) And(dcf_failure = 0) And(synchronized = 1)) Then 'wykryto poczatek przerwy miedzy impulsami
If(timer_val > 50ms And Timer_val < 150ms) Then 'odebrano bit 0
Dcf_array(1).bits_rcvd = 0
Bits_rcvd = Bits_rcvd + 1
Elseif(timer_val >= 150ms And Timer_val < 250ms) Then 'odebrano 1
Dcf_array(1).bits_rcvd = 1
Bits_rcvd = Bits_rcvd + 1
Else
Dcf_failure = 1
Synchronized = 0
End If
Else 'wykryto impuls
If(timer_val > 2000ms Or Timer_val < 600ms) Then 'niepoprawna przerwa miedzy impulsami
Set Dcf_failure
Bits_rcvd = 0
Reset Synchronized
Elseif(timer_val > 1500ms) Then 'mamy bit synchronizacyjny
Set Synchronized
If(bits_rcvd = 58 And Dcf_failure = 0) Then Gosub Change_time
Reset Dcf_failure
Bits_rcvd = 0
End If
End Ifmass85 napisał:Nikt nie jest w stanie pomoc? Nikt nie wie, dlaczego kompilator zglasza blad w ponizszym fragmencie?
If Timer_val > 2000ms Or Timer_val < 600ms Then
mass85 napisał:...
Jednak nadal jest jeden niezrozumialy dla mnie blad zwiazany z warunkiem logicznym.If Timer_val > 2000ms Or Timer_val < 600ms Then
Tutaj pojawia sie taki komunikat:
Error : 242 Line : 286 Source variable does not match the target variable [ 0] , in File : F:\STUDIA\DCF\PROGRAM\DCF.BAS
Const 50ms = 234 'jeszcze nieprawidlowe liczby
Const 150ms = 76867
Const 250ms = 2344
Const 1500ms = 3213244
Const 2000ms = 45454544
$regfile = "m16def.dat" 'dyrektywa dla mikrokontrolera ATmega16
$crystal = 8000000 'częstotliwość taktowania 8 MHz
Ddra = &B11110000 'PA.7-4 wyjscia wybierajace wyswietlacz, PA.3-2 wejscia przyciskow
Config Portc = Output 'port sterujacy wyswietlaczem
Config Portd.2 = Input 'port DCF_in (INT0)
D1 Alias Porta.7 'linie wybierajace wyswietlacz
D2 Alias Porta.6
D3 Alias Porta.5
D4 Alias Porta.4
B1 Alias Pina.3 'przycisk 1 (aktywne 0)
B2 Alias Pina.2 'przycisk 2 (aktywne 0)
Porta = &B11111100
Dot Alias Portc.7 'linia ustawiajaca kropke
Dcf_in Alias Pind.2
Porta.3 = 1 'ustawienie rezystorow podciagajacych
Porta.2 = 1 'dla wejsc obslugujacych przyciski
Dim Hours As Byte
Dim Minutes As Byte
Dim Seconds As Byte
Dim T2ms_cntr As Word
Dim Display_nr As Byte
Dim Umode As Byte 'zmienna trybu
Dim Dcf_allowed As Bit 'czy mozna sie synchronizowac z DCF
Dim Display_values(4) As Byte 'tablica danych do wyswietlenia
Dim Temp As Byte
Dim Temp_segment As Byte
Dim Timer_val As Word
Dim Dcf_array(8) As Byte 'tablica bitow odebranych
Dim Synchronized As Bit 'czy wykryto szczeline synchronizacyjna
Dim Int0_bit As Bit 'pamietana poprzednia wartosc bitu int0
Dim Dcf_failure As Bit 'flaga ustawiana, gdy wystapil jakikolwiek blad odbioru ramki
Dim Bits_rcvd As Byte 'liczba odebranych bitow DCF
Dim Index As Byte 'pomocnicza zmienna
Int0_bit = Dcf_in
Const T50ms = 390
Const T150ms = 1171
Const T250ms = 1953
Const T600ms = 4684
Const T1500ms = 11718
Const T2000ms = 15625
Config Int0 = Change
Config Timer2 = Timer , Prescale = 64
Config Timer1 = Timer , Prescale = 1024
Timer2 = 6
Start Timer2
Hours = 12
Minutes = 0
Seconds = 0
T2ms_cntr = 0
Umode = 0
Dcf_allowed = 1
Display_nr = 1
On Int0 Interrupt_dcf
On Timer2 Interrupt_2ms
Enable Interrupts
Enable Int0
Enable Timer2
'************************************************
'poczatek glownej petli
'************************************************
Do
If B1 = 0 Then ' Obsluga Przycisku 1(zmiana Trybu)
Waitms 20
If B1 = 0 Then
Umode = Umode + 1
If Umode > 5 Then Umode = 0
Bitwait B1 , Set
End If
End If '===========
Select Case Umode
Case 0 :
'tryb zegara
Temp = Makebcd(hours)
Temp_segment = Temp And &B00001111 'jednostki godzin
Temp_segment = Lookup(temp_segment , 7seg_code) 'odczyt kodu cyfry
Display_values(3) = Temp_segment
Temp_segment = Temp / 16
Temp_segment = Lookup(temp_segment , 7seg_code) 'odczyt kodu cyfry
Display_values(4) = Temp_segment 'dziesiatki godzin
Temp = Makebcd(minutes)
Temp_segment = Temp And &B00001111 'jednostki minut
Temp_segment = Lookup(temp_segment , 7seg_code) 'odczyt kodu cyfry
Display_values(1) = Temp_segment
Temp_segment = Temp / 16
Temp_segment = Lookup(temp_segment , 7seg_code) 'odczyt kodu cyfry
Display_values(2) = Temp_segment 'dziesiatki minut
Temp = Seconds Mod 2
If Temp = 0 Then
Display_values(3) = Display_values(3) And &B01111111
Display_values(3) = Display_values(3) Or &B10000000
End If
If Temp = 1 Then
Display_values(3) = Display_values(3) And &B01111111
End If
If Synchronized = 1 Then
Display_values(1) = Display_values(1) And &B01111111
Display_values(1) = Display_values(1) Or &B10000000
End If
Case 1:
If B2 = 0 Then ' Obsluga Przycisku 2(zmiana wartosci)
Waitms 20
If B2 = 0 Then Toggle Dcf_allowed
Bitwait B2 , Set
End If '===========
Display_values(4) = &B00111111 'kod litery D
Display_values(3) = &B00111001 'kod litery C
Display_values(2) = &B01110001 'kod litery F
If Dcf_allowed = 1 Then
Display_values(1) = &B00000110 'kod cyfry 1
Else
Display_values(1) = &B00111111 'kod cyfry 0
End If
Case 2:
'ostatnio odebrany bit
Index = Bits_rcvd - 1
If Index > 58 Then Index = 58
Temp = Makebcd(index)
Temp_segment = Temp And &B00001111 'jednostki nr bitu
Temp_segment = Lookup(temp_segment , 7seg_code) 'odczyt kodu cyfry
Display_values(3) = Temp_segment
Temp_segment = Temp / 16
Temp_segment = Lookup(temp_segment , 7seg_code) 'odczyt kodu cyfry
Display_values(4) = Temp_segment 'dziesiatki numeru bitu
Display_values(2) = &B01000000 ' Kod Myslnika
If Dcf_array(1).index = 1 Then
Display_values(1) = &B00000110
Else
Display_values(1) = &B00111111
End If
Case 3: ' tryb nastawy godzin
Display_values(4) = &B01110110 'kod litery H
Display_values(3) = &B01110110 'kod litery H
Temp = Makebcd(hours) 'wyswietla aktualna godzine
Temp_segment = Temp And &B00001111 'jednostki godzin
Temp_segment = Lookup(temp_segment , 7seg_code) 'odczyt kodu cyfry
Display_values(1) = Temp_segment
Temp_segment = Temp / 16
Temp_segment = Lookup(temp_segment , 7seg_code) 'odczyt kodu cyfry
Display_values(2) = Temp_segment 'dziesiatki godzin
If B2 = 0 Then ' Obsluga Przycisku 2(zmiana wartosci)
Waitms 20
If B2 = 0 Then Gosub Incr_hour
Bitwait B2 , Set
End If
Case 4: ' tryb nastawy minut
Display_values(4) = &B00110111 'kod litery M
Display_values(3) = &B00110111 'kod litery M
Temp = Makebcd(minutes) 'wyswietla aktualna minute
Temp_segment = Temp And &B00001111 'jednostki minut
Temp_segment = Lookup(temp_segment , 7seg_code) 'odczyt kodu cyfry
Display_values(1) = Temp_segment
Temp_segment = Temp / 16
Temp_segment = Lookup(temp_segment , 7seg_code) 'odczyt kodu cyfry
Display_values(2) = Temp_segment 'dziesiatki minut
If B2 = 0 Then ' Obsluga Przycisku 2(zmiana wartosci)
Waitms 20
If B2 = 0 Then Gosub Incr_min
Bitwait B2 , Set
End If
Case 5: ' tryb nastawy sekund
Display_values(4) = &B01101101 'kod litery S
Display_values(3) = &B01101101 'kod litery S
Temp = Makebcd(seconds) 'wyswietla aktualna sekunde
Temp_segment = Temp And &B00001111 'jednostki sekund
Temp_segment = Lookup(temp_segment , 7seg_code) 'odczyt kodu cyfry
Display_values(1) = Temp_segment
Temp_segment = Temp / 16
Temp_segment = Lookup(temp_segment , 7seg_code) 'odczyt kodu cyfry
Display_values(2) = Temp_segment 'dziesiatki sekund
If B2 = 0 Then ' Obsluga Przycisku 2(zmiana wartosci)
Waitms 20
If B2 = 0 Then Seconds = 0
Bitwait B2 , Set
End If
End Select
Loop
End
'************************************************
'koniec programu
'************************************************
Interrupt_2ms:
Timer2 = Timer2 + 6 ' Obsluga Timera
Enable Interrupts
T2ms_cntr = T2ms_cntr + 1
If T2ms_cntr = 500 Then
Gosub Incr_sec
T2ms_cntr = 0
End If
'obsluga wyswietlacza
Display_nr = Display_nr + 1
If Display_nr > 4 Then Display_nr = 1
Select Case Display_nr
Case 1:
Set D4
Portc = Display_values(display_nr)
Reset D1
Case 2:
Set D1
Portc = Display_values(display_nr)
Reset D2
Case 3:
Set D2
Portc = Display_values(display_nr)
Reset D3
Case 4:
Set D3
Portc = Display_values(display_nr)
Reset D4
End Select
Return
'************************************************
Interrupt_dcf:
Waitus 15 'eliminacja zaklocen impulsowych
If Dcf_in <> Int0_bit Then
Stop Timer1
Timer_val = Timer1
Timer1 = 0
Start Timer1
Int0_bit = Dcf_in
If Dcf_in = 0 And Dcf_failure = 0 And Synchronized = 1 Then 'wykryto poczatek przerwy miedzy impulsami
If Timer_val > T50ms And Timer_val < T150ms Then 'odebrano bit 0
Dcf_array(1).bits_rcvd = 0
Bits_rcvd = Bits_rcvd + 1
Elseif Timer_val >= T150ms And Timer_val < T250ms Then 'odebrano 1
Dcf_array(1).bits_rcvd = 1
Bits_rcvd = Bits_rcvd + 1
Else
Dcf_failure = 1
Synchronized = 0
End If
Else 'wykryto impuls
If Timer_val > T2000ms Or Timer_val < T600ms Then 'niepoprawna przerwa miedzy impulsami
Set Dcf_failure
Bits_rcvd = 0
Reset Synchronized
Elseif Timer_val > T1500ms Then 'mamy bit synchronizacyjny
Set Synchronized
If Bits_rcvd = 58 And Dcf_failure = 0 Then Gosub Change_time
Reset Dcf_failure
Bits_rcvd = 0
End If
End If
End If
Return
'************************************************
Change_time:
Dim Dcf_mins As Byte
Dim Dcf_hours As Byte
Dim Crc As Bit
Dim I As Byte
Index = 21
For I = 0 To 6
Crc = Crc Xor Dcf_array(1).index
Dcf_mins.i = Dcf_array(1).index
Index = Index + 1
Next
If Crc <> Dcf_array(1).28 Then Return
Dcf_mins = Makedec(dcf_mins)
If Dcf_mins > 60 Then Return
Index = 29
For I = 0 To 5
Crc = Crc Xor Dcf_array(1).index
Dcf_hours.i = Dcf_array(1).index
Index = Index + 1
Next
If Crc <> Dcf_array(1).35 Then Return
Dcf_hours = Makedec(dcf_hours)
If Dcf_hours > 24 Then Return
Hours = Dcf_hours
Minutes = Dcf_mins
Seconds = 0
Return
'************************************************
Incr_sec:
Seconds = Seconds + 1
If Seconds > 59 Then
Seconds = 0
Gosub Incr_min
End If
Return
Incr_min:
Minutes = Minutes + 1
If Minutes > 59 Then
Minutes = 0
Gosub Incr_hour
End If
Return
Incr_hour:
Hours = Hours + 1
If Hours > 23 Then
Hours = 0
End If
Return
'************************************************
7seg_code:
Data &B00111111 , &B00000110 , &B01011011 , &B01001111 , &B01100110,
Data &B01101101 , &B01111101 , &B00000111 , &B01111111 , &B01101111mass85 napisał:...Co masz na mysli piszac "chlapniesz"? Chlapanie tutaj na forum czy w swoim kodzie?
mass85 napisał:
Hm skoro widzisz jeszce jakies kwiatki, to bede wdzieczny, jesli sie nimi podzielisz ze mna.![]()
Dcf_array(1).28
'dla const index
Dcf_array(4).4 dla Dcf_array() As Byte
mass85 napisał:
Tylko jedna rzecz mnie martwi - w symulacji Timer2 odmierza mi odcinki 8ms, a nie 2ms... Sprawdzilem ustawienia taktowania uC, jest 8MHz. Preskaler jest ustawiony na 64, licznik zlicza 250impulsow. 8MHz/64/250 = 500Hz, zatem odcinki czasu powinny trwac 2ms.
Temp = Seconds Mod 2
If Temp = 0 Then
Set Display_values(3).7 'zgas kropke
End If
If Temp = 1 Then
Reset Display_values(3).7 'zapal kropke
End If Temp = Seconds Mod 2
If Temp = 0 Then
Set Display_values(3).index
End If
If Temp = 1 Then
Reset Display_values(3).index
End If Case 3: 'obsluga wyswietlacza nr 3(jednostki godzin)
Reset D2
Portc = Display_values(display_nr)
If Umode = 0 Then
Temp = Seconds Mod 2
If Temp = 0 Then Reset Portc.7
End If
Set D3If Bits_rcvd = 59 And Dcf_failure = 0 Then Gosub Change_time
$regfile = "m16def.dat" 'dyrektywa dla mikrokontrolera ATmega16
$crystal = 8000000 'częstotliwość taktowania 8 MHz
Ddra = &B11110000 'PA.7-4 wyjscia wybierajace wyswietlacz, PA.3-2 wejscia przyciskow
Config Portc = Output 'port sterujacy wyswietlaczem
Config Portd.2 = Input 'port DCF_in (INT0)
D1 Alias Porta.7 'linie wybierajace wyswietlacz
D2 Alias Porta.6
D3 Alias Porta.5
D4 Alias Porta.4
B1 Alias Pina.3 'przycisk 1 (aktywne 0)
B2 Alias Pina.2 'przycisk 2 (aktywne 0)
Porta = &B11111100
Dot Alias Portc.7 'linia ustawiajaca kropke
Dcf_in Alias Pind.2
Porta.3 = 1 'ustawienie rezystorow podciagajacych
Porta.2 = 1 'dla wejsc obslugujacych przyciski
Dim Hours As Byte
Dim Minutes As Byte
Dim Seconds As Byte
Dim T2ms_cntr As Word
Dim Display_nr As Byte
Dim Dcf_mins As Byte
Dim Dcf_hours As Byte
Dim Umode As Byte 'zmienna trybu
Dim Dcf_allowed As Bit 'czy mozna sie synchronizowac z DCF
Dim Display_values(4) As Byte 'tablica danych do wyswietlenia
Dim Temp As Byte
Dim Temp_segment As Byte
Dim Timer_val As Word
Dim Dcf_array(8) As Byte 'tablica bitow odebranych
Dim Synchronized As Bit 'czy wykryto szczeline synchronizacyjna
Dim Int0_bit As Bit 'pamietana poprzednia wartosc bitu int0
Dim Dcf_failure As Bit 'flaga ustawiana, gdy wystapil jakikolwiek blad odbioru ramki
Dim Bits_rcvd As Byte 'liczba odebranych bitow DCF
Dim Index As Byte 'pomocnicza zmienna
Int0_bit = Dcf_in
Const T50ms = 390
Const T150ms = 1171
Const T250ms = 1953
Const T600ms = 4684
Const T1500ms = 11718
Const T2000ms = 15625
Config Int0 = Change
Config Timer2 = Timer , Prescale = 64
Config Timer1 = Timer , Prescale = 1024
Timer2 = 6
Start Timer2
Hours = 12
Minutes = 0
Seconds = 0
T2ms_cntr = 0
Umode = 0
Dcf_allowed = 1
Display_nr = 1
Dcf_mins = 100
On Int0 Interrupt_dcf
On Timer2 Interrupt_2ms
Enable Interrupts
Enable Int0
Enable Timer2
'************************************************
'poczatek glownej petli
'************************************************
Do
If B1 = 0 Then ' Obsluga Przycisku 1(zmiana Trybu)
Waitms 30
If B1 = 0 Then
Umode = Umode + 1
If Umode > 5 Then Umode = 0
Bitwait B1 , Set
End If
End If '===========
Select Case Umode
Case 0 :
'tryb zegara
Temp = Makebcd(hours)
Temp_segment = Temp And &B00001111 'jednostki godzin
Temp_segment = Lookup(temp_segment , 7seg_code) 'odczyt kodu cyfry
Display_values(3) = Temp_segment
Temp_segment = Temp / 16
Temp_segment = Lookup(temp_segment , 7seg_code) 'odczyt kodu cyfry
Display_values(4) = Temp_segment 'dziesiatki godzin
Temp = Makebcd(minutes)
Temp_segment = Temp And &B00001111 'jednostki minut
Temp_segment = Lookup(temp_segment , 7seg_code) 'odczyt kodu cyfry
Display_values(1) = Temp_segment
Temp_segment = Temp / 16
Temp_segment = Lookup(temp_segment , 7seg_code) 'odczyt kodu cyfry
Display_values(2) = Temp_segment 'dziesiatki minut
Case 1:
If B2 = 0 Then ' Obsluga Przycisku 2(zmiana wartosci)
Waitms 30
If B2 = 0 Then Toggle Dcf_allowed
If Dcf_allowed = 0 Then Dcf_mins = 100
Bitwait B2 , Set
End If '===========
Display_values(4) = &B10000001 'kod litery D
Display_values(3) = &B11001001 'kod litery C
Display_values(2) = &B11101000 'kod litery F
If Dcf_allowed = 1 Then
Display_values(1) = &B10110111 'kod cyfry 1
Else
Display_values(1) = &B10000001 'kod cyfry 0
End If
Case 2:
'ostatnio odebrany bit
Index = Bits_rcvd - 1
If Index > 58 Then Index = 58
Temp = Makebcd(index)
Temp_segment = Temp And &B00001111 'jednostki nr bitu
Temp_segment = Lookup(temp_segment , 7seg_code) 'odczyt kodu cyfry
Display_values(3) = Temp_segment
Temp_segment = Temp / 16
Temp_segment = Lookup(temp_segment , 7seg_code) 'odczyt kodu cyfry
Display_values(4) = Temp_segment 'dziesiatki numeru bitu
Display_values(2) = &B11111110 ' Kod Myslnika
If Dcf_array(1).index = 1 Then
Display_values(1) = &B10110111
Else
Display_values(1) = &B10000001
End If
Case 3: ' tryb nastawy godzin
Display_values(4) = &B10100100 'kod litery H
Display_values(3) = &B10100100 'kod litery H
Temp = Makebcd(hours) 'wyswietla aktualna godzine
Temp_segment = Temp And &B00001111 'jednostki godzin
Temp_segment = Lookup(temp_segment , 7seg_code) 'odczyt kodu cyfry
Display_values(1) = Temp_segment
Temp_segment = Temp / 16
Temp_segment = Lookup(temp_segment , 7seg_code) 'odczyt kodu cyfry
Display_values(2) = Temp_segment 'dziesiatki godzin
If B2 = 0 Then ' Obsluga Przycisku 2(zmiana wartosci)
Waitms 30
If B2 = 0 Then Gosub Incr_hour
Bitwait B2 , Set
End If
Case 4: ' tryb nastawy minut
Display_values(4) = &B10100001 'kod litery M
Display_values(3) = &B10100001 'kod litery M
Temp = Makebcd(minutes) 'wyswietla aktualna minute
Temp_segment = Temp And &B00001111 'jednostki minut
Temp_segment = Lookup(temp_segment , 7seg_code) 'odczyt kodu cyfry
Display_values(1) = Temp_segment
Temp_segment = Temp / 16
Temp_segment = Lookup(temp_segment , 7seg_code) 'odczyt kodu cyfry
Display_values(2) = Temp_segment 'dziesiatki minut
If B2 = 0 Then ' Obsluga Przycisku 2(zmiana wartosci)
Waitms 30
If B2 = 0 Then Gosub Incr_min
Bitwait B2 , Set
End If
Case 5: ' tryb nastawy sekund
Display_values(4) = &B10011000 'kod litery S
Display_values(3) = &B10011000 'kod litery S
Temp = Makebcd(seconds) 'wyswietla aktualna sekunde
Temp_segment = Temp And &B00001111 'jednostki sekund
Temp_segment = Lookup(temp_segment , 7seg_code) 'odczyt kodu cyfry
Display_values(1) = Temp_segment
Temp_segment = Temp / 16
Temp_segment = Lookup(temp_segment , 7seg_code) 'odczyt kodu cyfry
Display_values(2) = Temp_segment 'dziesiatki sekund
If B2 = 0 Then ' Obsluga Przycisku 2(zmiana wartosci)
Waitms 30
If B2 = 0 Then Seconds = 0
Bitwait B2 , Set
End If
End Select
Loop
End
'************************************************
'koniec programu
'************************************************
Interrupt_2ms:
Timer2 = Timer2 + 6 ' Obsluga Timera
Enable Interrupts
T2ms_cntr = T2ms_cntr + 1
If T2ms_cntr = 500 Then
Gosub Incr_sec
T2ms_cntr = 0
End If
'obsluga wyswietlacza
Display_nr = Display_nr + 1
If Display_nr > 4 Then Display_nr = 1
Select Case Display_nr
Case 1:
Reset D4
Portc = Display_values(display_nr)
Temp = Seconds Mod 2
If Synchronized = 1 Then
Reset Portc.7 'swiecenie ciagle kropki gdy tylko wykryto szczeline synchr.
If Dcf_mins = Minutes And Temp = 1 Then 'miganie kropki, gdy wyswietlany czas jest
Set Portc.7 'zgodny z czasem dcf
End If
Elseif Dcf_mins = Minutes And Temp = 0 Then 'miganie kropki, gdy wyswietlany czas jest
Reset Portc.7 'zgodny z czasem dcf
End If
Set D1
Case 2:
Reset D1
Portc = Display_values(display_nr)
Set D2
Case 3:
Reset D2
Portc = Display_values(display_nr)
Temp = Seconds Mod 2
If Temp = 0 Then Reset Portc.7
Set D3
Case 4:
Reset D3
Portc = Display_values(display_nr)
Set D4
End Select
Return
'************************************************
Interrupt_dcf:
Waitus 15 'eliminacja zaklocen impulsowych
If Dcf_in <> Int0_bit Then
Stop Timer1
Timer_val = Timer1
Timer1 = 0
Start Timer1
Int0_bit = Dcf_in
If Dcf_in = 0 And Dcf_failure = 0 And Synchronized = 1 Then 'wykryto poczatek przerwy miedzy impulsami
If Timer_val > T50ms And Timer_val < T150ms Then 'odebrano bit 0
Dcf_array(1).bits_rcvd = 0
Bits_rcvd = Bits_rcvd + 1
Elseif Timer_val >= T150ms And Timer_val < T250ms Then 'odebrano 1
Dcf_array(1).bits_rcvd = 1
Bits_rcvd = Bits_rcvd + 1
Else 'blad
Dcf_failure = 1
Synchronized = 0
End If
Else 'wykryto impuls
If Timer_val > T2000ms Or Timer_val < T600ms Then 'blad - niepoprawna przerwa miedzy impulsami
Set Dcf_failure
Reset Synchronized
Elseif Timer_val > T1500ms Then 'mamy bit synchronizacyjny
Set Synchronized
If Bits_rcvd = 59 And Dcf_failure = 0 Then Gosub Change_time
Reset Dcf_failure
Bits_rcvd = 0
End If
End If
End If
Return
'************************************************
Change_time:
Dim Crc As Bit
Dim I As Byte
If Dcf_allowed = 0 Then Return
Index = 20
If Dcf_array(1).index = 0 Then Return
Index = 21
For I = 0 To 6
Crc = Crc Xor Dcf_array(1).index
Dcf_mins.i = Dcf_array(1).index
Index = Index + 1
Next
Index = 28
If Crc <> Dcf_array(1).index Then Return
Dcf_mins = Makedec(dcf_mins)
If Dcf_mins > 60 Then Return
Index = 29
For I = 0 To 5
Crc = Crc Xor Dcf_array(1).index
Dcf_hours.i = Dcf_array(1).index
Index = Index + 1
Next
Index = 35
If Crc <> Dcf_array(1).index Then Return
Dcf_hours = Makedec(dcf_hours)
If Dcf_hours > 24 Then Return
Hours = Dcf_hours
Minutes = Dcf_mins
Seconds = 0
Return
'************************************************
Incr_sec:
Seconds = Seconds + 1
If Seconds > 59 Then
Seconds = 0
Gosub Incr_min
End If
Return
Incr_min:
Minutes = Minutes + 1
If Minutes > 59 Then
Minutes = 0
Gosub Incr_hour
End If
Return
Incr_hour:
Hours = Hours + 1
If Hours > 23 Then
Hours = 0
End If
Return
'************************************************
7seg_code:
Data &B10000001 , &B10110111 , &B11000010 , &B10010010 , &B10110100,
Data &B10011000 , &B10001000 , &B10110011 , &B10000000 , &B10010000