eGospodarka.pl

eGospodarka.plGrupypl.misc.elektronika › Przykładowe ramki DCF77
Ilość wypowiedzi w tym wątku: 8

  • 1. Data: 2019-05-09 08:04:43
    Temat: Przykładowe ramki DCF77
    Od: Atlantis <m...@w...pl>

    Szukam, ale jakoś znaleźć nie mogę...
    Potrzebuję przykładów poprawnych ramek DCF77, wraz z informacją na temat
    tego, jaki czas jest w nich zakodowany. Chodzi mi po prostu o ciąg bitów.
    Pracuję obecnie nad własną biblioteką do obsługi modułów DCF77
    (częściowo opierając się na kodzie Arduino). Niby działa, jednak od
    czasu do czasu pojawiają się problemu i dekodowany czas różni się od
    poprawnego. Chciałem teraz zrobić krok w tył i sprawdzić poprawność
    działania poszczególnych funkcji, kompilując je na PC, karmiąc
    spreparowanymi danymi i obserwując wynik.

    Niby protokół jest opisany, jednak chcę mieć pewność, że i podczas
    preparowania ramki nie popełnię błędu...


  • 2. Data: 2019-05-09 08:09:24
    Temat: Re: Przykładowe ramki DCF77
    Od: Mateusz Viste <m...@n...pamietam>

    On Thu, 09 May 2019 08:04:43 +0200, Atlantis wrote:
    > Niby działa, jednak od czasu do czasu pojawiają się problemu i
    > dekodowany czas różni się od poprawnego. Chciałem teraz zrobić krok w
    > tył i sprawdzić poprawność działania poszczególnych funkcji (...)

    To pewnie dla ciebie oczywistość, ale podczas transmisji mogą występować
    błędy... Zaufanie do pojedynczej ramki powinno być mocno ograniczone, a
    czas ustawiony tylko wówczas, kiedy ciąg kilku ramek konsekwentnie
    wskazuje bardzo zbliżony czas.

    Mateusz


  • 3. Data: 2019-05-09 10:48:58
    Temat: Re: Przykładowe ramki DCF77
    Od: Piotr Gałka <p...@c...pl>

    W dniu 2019-05-09 o 08:04, Atlantis pisze:

    > Pracuję obecnie nad własną biblioteką do obsługi modułów DCF77
    > (częściowo opierając się na kodzie Arduino). Niby działa, jednak od
    > czasu do czasu pojawiają się problemu i dekodowany czas różni się od
    > poprawnego.

    Może Ci się przyda.
    Dawno, dawno temu (lata 95..97) zrobiłem odbiornik DCF podłączony pod
    COM komputera (zasilanie też z COM). Odbiornik wystawiał sygnał z DCF na
    którejś z linii RS232 i z tej linii go czytałem.
    Trochę się naszukałem w starych plikach, ale znalazłem. Poniżej źródła.
    Zauważyłem, że odwołuję się do doneinfo.h. Poszukałem co to takiego -
    jakaś forma linijki pokazującej postęp procesu - nie ma związku z samym DCF.
    Nie chce mi się wczytywać w szczegóły. Na pierwszy rzut oka widzę, że:
    - RS232 obsługuję po adresach - tak się robiło pod DOS
    - do odmierzania czasu używam wysyłania w koło czegoś po RS232

    Przy ^C^V program pocztowy pozawijał niektóre linijki.

    ============================= plik DCF77.H ============================
    // dcf77.h
    // DCF77 class - odbior sygnalu DCF77 przez port RS232

    #ifndef __DCF77_H
    #define __DCF77_H

    #ifndef __DONEINFO_H
    #include "doneinfo.h"
    #endif

    typedef unsigned char BYTE;
    typedef unsigned short WORD;
    typedef unsigned long DWORD;

    class DCF77
    {
    DWORD blo; // bufory na zbierane bity
    WORD bhi;
    int addr; // adres portu


    enum {DLL=0, // Divisor Latch Low byte
    DLH = 1, // Divisor Latch High byte
    IER = 1, // Interrupt Enable Register - zezw. na przerwania
    IIR = 2, // Interrupt Identification Register
    LCR = 3, // Line Control Register - tryb transmisji
    MCR = 4, // Modem Control Register - set innych linii
    LSR = 5, // Line Status Register - stan transmisji
    MSR = 6}; // Modem Status Register - stan innych linii

    int parity(WORD w); // sprawdzenie parzystosci slowa

    public:
    DCF77(int com); // konstruktor

    int read(DoneInfo *d=0); // odbior DCF77 ret:n imp (<0-bledy)
    int gettime(struct time *t); // odczytany czas ret:0-ok,1-err
    int getdate(struct date* d); // odczytana data ret:0-ok,1-err
    };

    #endif // __DCF77_H


    ============================ plik DCF77.CPP ============================
    // dcf77.cpp
    // DCF77 class - odbior sygnalu DCF77 przez port RS232

    #include <dos.h>
    #include <conio.h>

    #include "dcf77.h"

    DCF77::DCF77(int com):blo(0),bhi(0)
    {
    static int adrt[4]={0x3F8,0x2F8,0x3E8,0x2E8}; // adresy COM-ow

    int div=48; // predkosc 2400
    int lcr=3; // format 8N1
    int mcr=1; // DTR=1
    addr=adrt[com];

    outportb(addr+LCR,0x80); // Divisor Latch Access
    outportb(addr,div&0xFF); // Divisor Latch low byte
    outportb(addr+DLH,div>>8); // high byte
    outportb(addr+LCR,lcr); // Line Control Register
    outportb(addr+MCR,mcr); // Modem Control Register
    outportb(addr+IER,0); // Interrupt Enable Register
    inportb(addr); // wyczyszczenie bufora
    outportb(addr,0); // zapelnienie bufora nadawczego
    outportb(addr,0);
    }

    int DCF77::parity(WORD w)
    {
    w^=w>>8;w^=w>>4;w^=w>>2;w^=w>>1;
    return w&1;
    }

    // zwraca:
    // nb = liczba odebranych impulsow, powinno byc co najmniej 39 impulsow
    // -1 = brak impulsow przez 5 sekund
    // -2 = nie podlaczony odbiornik - szum zamiast impulsow
    // -3 = brak konca
    // -4 = klawisz

    int DCF77::read(DoneInfo *d) // odbior DCF77
    {
    int b,b0=0x10,b1=0x10; // 0x10 -> dodatnie zbocze bedzie prawdziwe
    int valid=0; // na poczatku pracy
    int dn=0; // licznik petli w sekundzie DCF77
    int lock=0; // blokowanie analizy linii wejsciowej
    int down=0; // bylo ujemne zbocze
    int nb=0; // licznik odebranych bitow
    int ns=0; // licznik zmian stanu w czasie blokowania

    // w jednej sekundzie miesci sie 240 nadan 2400B:8N1
    static const
    lockT=234, // blokada dla calego okresu (0.975s)
    lockt=18, // blokada dla impulsu (0.075s)
    lim2s=420, // czas dla znacznika konca (1.75s)
    lim01=31, // prog rozroznienia 0/1 (0.13s)
    lim5s=1200; // czas dla braku impulsow (5s)

    bhi=0; // zeruje bufory wynikowe
    blo=0;
    if(d)d->limit(60); // po 59 impulsie czeka jeszcze 2s
    while(1){
    if(inportb(addr+LSR)&0x20){
    outportb(addr,0); // teraz mamy troche czasu bez naruszania dn
    if(down){ // bylo ujemne zbocze - przetwarzanie i info
    blo>>=1;
    if(bhi&1L)blo|=0x80000000L; // przeniesienie bitu
    bhi>>=1;
    if(dn>lim01)bhi|=0x8000; // wpisanie aktualnego bitu
    nb++; // liczba odebranych bitow
    if(d)d->done(nb); // to moze zajac czas (dlatego down)
    down=0; // obsluzone
    }
    dn++; // licznik wyslanych przez RS232 bajtow w impulsie DCF
    if(dn>lim5s)return -1; // brak impulsow
    if(nb>60)return -3; // za duzo impulsow
    if(kbhit()){getch();return -4;} // nacisniety klawisz
    }

    b=inportb(addr+MSR)&0x10; // sprawdzenie linii wejsciowej
    if(dn>lock){ // tylko gdy nie ma blokady
    if(b!=b0){ // zmiana stanu
    b0=b; // nowy stan
    if(valid){ // juz bylo pierwsze dodatnie zbocze
    if(b){ // dodatnie zbocze
    if(dn>lim2s)return nb; // koniec minuty (dn>1.75s)
    lock=lockt; // blokada do 0.075s
    }
    else{ // ujemne zbocze
    down=1; // flaga ujemnego zbocza
    lock=lockT; // blokada do 0.975 s
    }
    }
    if(b){valid=1;dn=0;}// juz bylo dodatnie zbocze i licznik od 0
    b1=b;
    ns=0;
    }
    }
    if(b!=b1){ // nieoczekiwana zmiana stanu
    b1=b;
    if(++ns>9)return -2; // szum - nie podlaczony odbiornik
    }
    }
    }

    int DCF77::gettime(struct time *t) // odczytany czas ret:0-ok,1-err
    {
    int h,l;

    if((blo&0x200)==0 || // nie ma bitu startu
    parity(WORD((blo>>10)&0xFF)) || // parzystosc minut
    parity(WORD((blo>>18)&0x7F)) )return 1; // parzystosc godzin

    h=int((blo>>14)&7);l=int((blo>>10)&0xF);t->ti_min=h*
    10+l;
    if(h>5 || l>9)return 1; // zle wartosci dla minut

    h=int((blo>>22)&3);l=int((blo>>18)&0xF);t->ti_hour=h
    *10+l;
    if(h>2 || l>9 || t->ti_hour>23)return 1; // zle wartosci dla godzin
    t->ti_sec=0;
    t->ti_hund=0;
    return 0;
    }

    int DCF77::getdate(struct date* d) // odczytana data ret:0-ok,1-err
    {
    int h,l,y;

    if((blo&0x200)==0 || // nie ma bitu startu
    parity(WORD(blo>>25))^parity(bhi) )return 1;// parzystosc daty

    h=int((blo>>29)&3);l=int((blo>>25)&0xF);d->da_day=h*
    10+l;
    if(l>9 || d->da_day>31)return 1; // zle wartosci dnia

    h=(bhi>>6)&1;l=(bhi>>2)&0xF;d->da_mon=h*10+l;
    if(l>9 || d->da_mon>12)return 1; // zle wartosci miesiaca

    h=(bhi>>11)&0xF;l=(bhi>>7)&0xF;y=h*10+l;
    if(h>9 || l>9)return 1;
    d->da_year=(y<98)?2000+y:1900+y; // prawidlowo do 2097 roku
    return 0;
    }


  • 4. Data: 2019-05-09 10:53:31
    Temat: Re: Przykładowe ramki DCF77
    Od: Piotr Gałka <p...@c...pl>

    W dniu 2019-05-09 o 10:48, Piotr Gałka pisze:

    > Przy ^C^V program pocztowy pozawijał niektóre linijki.

    Ciekawe.
    Przed wysłaniem były pozawijane. Jak po wysłaniu zajrzałem to nie są
    pozawijane.

    Nigdy nie zadałem sobie trudu rozejrzenia się w ustawieniach Thunderbirda.
    P.G.


  • 5. Data: 2019-05-09 12:36:38
    Temat: Re: Przykładowe ramki DCF77
    Od: Atlantis <m...@w...pl>

    On 09.05.2019 08:09, Mateusz Viste wrote:

    > To pewnie dla ciebie oczywistość, ale podczas transmisji mogą występować
    > błędy... Zaufanie do pojedynczej ramki powinno być mocno ograniczone, a
    > czas ustawiony tylko wówczas, kiedy ciąg kilku ramek konsekwentnie
    > wskazuje bardzo zbliżony czas.

    Tak. Biblioteka na której się opieram zawiera kilka "sanity checks".
    Problem polega na tym, że błędy nie są wynikiem problemy nie są efektem
    przekłamania w transmisji, ale jakiegoś błędu w kodzie. Przez to są one
    powtarzalne i występują w kolejnych ramkach, prowadząc do zaakceptowania
    błędnego czasu.
    Próbuję ustalić w którym miejscu się tak dzieje. A ponieważ zmęczyło
    mnie debugowanie na "żywym" układzie, w środku nocy, gdy propagacja się
    podnosi, chcę to zrobić w sposób opisany powyżej. ;)


  • 6. Data: 2019-05-09 12:40:22
    Temat: Re: Przykładowe ramki DCF77
    Od: Cezar <c...@t...pl.nospam>

    On 09/05/2019 07:04, Atlantis wrote:
    > Szukam, ale jakoś znaleźć nie mogę...
    > Potrzebuję przykładów poprawnych ramek DCF77, wraz z informacją na temat
    > tego, jaki czas jest w nich zakodowany. Chodzi mi po prostu o ciąg bitów.
    > Pracuję obecnie nad własną biblioteką do obsługi modułów DCF77
    > (częściowo opierając się na kodzie Arduino). Niby działa, jednak od
    > czasu do czasu pojawiają się problemu i dekodowany czas różni się od
    > poprawnego. Chciałem teraz zrobić krok w tył i sprawdzić poprawność
    > działania poszczególnych funkcji, kompilując je na PC, karmiąc
    > spreparowanymi danymi i obserwując wynik.
    >
    > Niby protokół jest opisany, jednak chcę mieć pewność, że i podczas
    > preparowania ramki nie popełnię błędu...
    >


    tutaj masz cos co generuje DCF na GPIO (razem z szumem)
    https://github.com/twam/dcf77gen


    W tym repo masz bardzo duzo informacji jak walczyc z zakłóceniami:

    https://github.com/udoklein/dcf77


  • 7. Data: 2019-05-09 12:49:35
    Temat: Re: Przykładowe ramki DCF77
    Od: Cezar <c...@t...pl.nospam>

    On 09/05/2019 07:04, Atlantis wrote:
    > Szukam, ale jakoś znaleźć nie mogę...
    > Potrzebuję przykładów poprawnych ramek DCF77, wraz z informacją na temat
    > tego, jaki czas jest w nich zakodowany. Chodzi mi po prostu o ciąg bitów.
    > Pracuję obecnie nad własną biblioteką do obsługi modułów DCF77
    > (częściowo opierając się na kodzie Arduino). Niby działa, jednak od
    > czasu do czasu pojawiają się problemu i dekodowany czas różni się od
    > poprawnego. Chciałem teraz zrobić krok w tył i sprawdzić poprawność
    > działania poszczególnych funkcji, kompilując je na PC, karmiąc
    > spreparowanymi danymi i obserwując wynik.
    >
    > Niby protokół jest opisany, jednak chcę mieć pewność, że i podczas
    > preparowania ramki nie popełnię błędu...
    >

    tutaj mozesz zobaczyć ramki na żywo, bit po bicie:

    https://www.dcf77logs.de/live


  • 8. Data: 2019-05-11 00:27:17
    Temat: Re: Przykładowe ramki DCF77
    Od: Atlantis <m...@w...pl>

    On 09.05.2019 12:49, Cezar wrote:

    > tutaj mozesz zobaczyć ramki na żywo, bit po bicie:
    >
    > https://www.dcf77logs.de/live

    Dzięki. Właśnie tego potrzebowałem. ;)

strony : [ 1 ]



Szukaj w grupach

Szukaj w grupach

Eksperci egospodarka.pl

1 1 1

Wpisz nazwę miasta, dla którego chcesz znaleźć jednostkę ZUS.

Wzory dokumentów

Bezpłatne wzory dokumentów i formularzy.
Wyszukaj i pobierz za darmo: