]> git.ipfire.org Git - thirdparty/ntp.git/commitdiff
Guys,
authorHarlan Stenn <stenn@ntp.org>
Sat, 22 Dec 2001 03:24:22 +0000 (22:24 -0500)
committerHarlan Stenn <stenn@ntp.org>
Sat, 22 Dec 2001 03:24:22 +0000 (22:24 -0500)
Fixed a wee bug and the house caved in. Just about every driver was
broken in a little evil way and broke the interface conventions in the
following:

1. The drivers did not correctly update the reference time variable
pp->lastref. Some left it untouched, some broke the rule that the
reference time must not be later than the receive timestamp. I added
pp->lastref = pp->lastrec just before the refclock_receive() call, which
should be correct in most cases. For those drivers that use
refclock_process(), coders might want to move the line just before that
call.

2. There were two variables pp->usec and pp->msec for microseconds and
milliseconds, respectively, of the second. There was no provision for
nanoseconds. Some drivers used both of these, which was not handled
correctly in the interface. I removed both and replaced with pp->nsec
for nanoseconds and recoded various drivers to do that correctly.

3. Some drivers did not zero the fraction part of the l_fp offset
variable computed by clocktime(). This was the first thing I noticed in
testing. The result in some cases was garbage when computing the
difference between clock time and system time.

4. The SAMPLE macro in ntp_refclock.h and the refclock_sample() routine
was defective. If the median filter ever filled up, the latter would
consider it empty and toss the entire filter contents. The intent when
the filter fills up is that old samples are overwritten and the filter
retains its maximum size untl refclock_receive() empties it.

5. Small changes were made to interface routines in order to improve and
simplify the debug trace.

While I carefully checked all the drivers and the changes are minor, I
am able to test only a few, including the audio drivers, PSTI,
Spectracom, Arbiter and PPS, which do just fine. I have done nothing for
the parse drivers, which may or may not need the same updates. I was
able to confirm the Solaris, SunOS, FreeBSD and Linux builds work. Later
for HPUX and Alpha.

Aside: In experimenting with the -N high option, which is necessary for
the WWV audio driver, I discovered some little evils. First, the serial
port jitter is terrible with my Ultra 30 - simething like 10 ms - and
the latency surprisingly large, like 10 ms. Checking timestamps, I
discovered without -N the CR and LF have the same timestamp, while with
-N they have separate and much more precise timestamps. I also
discovered for whatever reason the monitor function of the audio codec
doesn't work in the Ultra 30, but works just fine using the same code in
the Blade 1000, both Solariba 8.

bk: 3c23fce6nzgEZzf0wMIaQZAbssPy2w

37 files changed:
include/ntp_refclock.h
ntpd/ntp_refclock.c
ntpd/refclock_acts.c
ntpd/refclock_arbiter.c
ntpd/refclock_arc.c
ntpd/refclock_as2201.c
ntpd/refclock_atom.c
ntpd/refclock_bancomm.c
ntpd/refclock_chronolog.c
ntpd/refclock_chu.c
ntpd/refclock_datum.c
ntpd/refclock_dumbclock.c
ntpd/refclock_fg.c
ntpd/refclock_gpsvme.c
ntpd/refclock_heath.c
ntpd/refclock_hopfpci.c
ntpd/refclock_hopfser.c
ntpd/refclock_hpgps.c
ntpd/refclock_irig.c
ntpd/refclock_jjy.c
ntpd/refclock_jupiter.c
ntpd/refclock_leitch.c
ntpd/refclock_local.c
ntpd/refclock_mx4200.c
ntpd/refclock_nmea.c
ntpd/refclock_oncore.c
ntpd/refclock_palisade.c
ntpd/refclock_pcf.c
ntpd/refclock_pst.c
ntpd/refclock_shm.c
ntpd/refclock_tpro.c
ntpd/refclock_trak.c
ntpd/refclock_true.c
ntpd/refclock_ulink.c
ntpd/refclock_usno.c
ntpd/refclock_wwv.c
ntpd/refclock_wwvb.c

index 812251ae6aa7f6abe48c4cc92a6de681ebf2c0da..682c66657efd82934f84f1b9ad534361a0db909a 100644 (file)
 #define BSD_TTYS
 #endif /* SYSV_TTYS STREAM BSD_TTYS */
 
-#define SAMPLE(x)      pp->filter[pp->coderecv++ % MAXSTAGE] = (x); \
-                       if (pp->coderecv % MAXSTAGE == pp->codeproc % MAXSTAGE) \
-                               pp->codeproc++;
+#define SAMPLE(x)      pp->coderecv = (pp->coderecv + 1) % MAXSTAGE; \
+                       pp->filter[pp->coderecv] = (x); \
+                       if (pp->coderecv == pp->codeproc) \
+                               pp->codeproc = (pp->codeproc + 1) % MAXSTAGE;
 
 /*
  * Macros to determine the clock type and unit numbers from a
@@ -187,13 +188,12 @@ struct refclockproc {
        int     hour;           /* hour of day */
        int     minute;         /* minute of hour */
        int     second;         /* second of minute */
-       int     msec;           /* millisecond of second */
-       long    usec;           /* microsecond of second (alt) */
+       long    nsec;           /* nanosecond of second */
        u_long  yearstart;      /* beginning of year */
        int     coderecv;       /* put pointer */
        int     codeproc;       /* get pointer */
-       l_fp    lastref;        /* timecode timestamp */
-       l_fp    lastrec;        /* local timestamp */
+       l_fp    lastref;        /* reference timestamp */
+       l_fp    lastrec;        /* receive timestamp */
        double  offset;         /* mean offset */
        double  disp;           /* sample dispersion */
        double  jitter;         /* jitter (mean squares) */
index 2b3a19d8b12d9e582f95ed12e0b28f93bc841058..386caa915ddbd29640e27dc5896edad08b967731 100644 (file)
@@ -387,18 +387,19 @@ refclock_cmpl_fp(
  */
 void
 refclock_process_offset(
-       struct refclockproc *pp,
-       l_fp offset,
-       l_fp lastrec,
+       struct refclockproc *pp,        /* refclock structure pointer */
+       l_fp lasttim,                   /* last timecode timestamp */
+       l_fp lastrec,                   /* last receive timestamp */
        double fudge
        )
 {
+       l_fp lftemp;
        double doffset;
 
-       pp->lastref = offset;
        pp->lastrec = lastrec;
-       L_SUB(&offset, &lastrec);
-       LFPTOD(&offset, doffset);
+       lftemp = lasttim;
+       L_SUB(&lftemp, &lastrec);
+       LFPTOD(&lftemp, doffset);
        SAMPLE(doffset + fudge);
 }
 
@@ -413,10 +414,10 @@ refclock_process_offset(
 */
 int
 refclock_process(
-       struct refclockproc *pp
+       struct refclockproc *pp         /* refclock structure pointer */
        )
 {
-       l_fp offset;
+       l_fp offset, ltemp;
 
        /*
         * Compute the timecode timestamp from the days, hours, minutes,
@@ -429,11 +430,9 @@ refclock_process(
        if (!clocktime(pp->day, pp->hour, pp->minute, pp->second, GMT,
                pp->lastrec.l_ui, &pp->yearstart, &offset.l_ui))
                return (0);
-       if (pp->usec) {
-               TVUTOTSF(pp->usec, offset.l_uf);
-       } else {
-               MSUTOTSF(pp->msec, offset.l_uf);
-       }
+       offset.l_uf = 0;
+       DTOLFP(pp->nsec / 1e9, &ltemp);
+       L_ADD(&offset, &ltemp);
        refclock_process_offset(pp, offset, pp->lastrec,
            pp->fudgetime1);
        return (1);
@@ -451,7 +450,7 @@ refclock_process(
  */
 static int
 refclock_sample(
-       struct refclockproc *pp
+       struct refclockproc *pp         /* refclock structure pointer */
        )
 {
        int i, j, k, m, n;
@@ -465,8 +464,10 @@ refclock_sample(
        if (pp->codeproc == pp->coderecv)
                return (0);
        n = 0;
-       while (pp->codeproc != pp->coderecv)
-               off[n++] = pp->filter[pp->codeproc++ % MAXSTAGE];
+       while (pp->codeproc != pp->coderecv) {
+               off[n++] = pp->filter[pp->codeproc];
+               pp->codeproc = (pp->codeproc + 1) % MAXSTAGE;
+       }
        if (n > 1)
                qsort((char *)off, (size_t)n, sizeof(double), refclock_cmpl_fp);
 
@@ -544,7 +545,8 @@ refclock_receive(
        if (!peer->reach)
                report_event(EVNT_REACH, peer);
        peer->reach |= 1;
-       peer->reftime = peer->org = pp->lastrec;
+       peer->reftime = pp->lastref;
+       peer->org = pp->lastrec;
        peer->rootdispersion = pp->disp + SQRT(pp->jitter);
        get_systime(&peer->rec);
        if (!refclock_sample(pp))
@@ -596,7 +598,7 @@ refclock_gtlin(
         * timestamp by noting its value is earlier than the buffer
         * timestamp, but not more than one second earlier.
         */
-       dpt = (char *)&rbufp->recv_space;
+       dpt = rbufp->recv_buffer;
        dpend = dpt + rbufp->recv_length;
        trtmp = rbufp->recv_time;
 
@@ -637,9 +639,14 @@ refclock_gtlin(
        if (i > 0)
                *dp = '\0';
 #ifdef DEBUG
-       if (debug > 1 && i > 0)
-               printf("refclock_gtlin: fd %d time %s timecode %d %s\n",
-                   rbufp->fd, ulfptoa(&trtmp, 6), i, lineptr);
+       if (debug > 1) {
+               if (i > 0)
+                       printf("refclock_gtlin: fd %d time %s timecode %d %s\n",
+                           rbufp->fd, ulfptoa(&trtmp, 6), i, lineptr);
+               else
+                       printf("refclock_gtlin: fd %d time %s\n",
+                           rbufp->fd, ulfptoa(&trtmp, 6));
+       }
 #endif
        *tsptr = trtmp;
        return (i);
@@ -1085,7 +1092,7 @@ refclock_buginfo(
        bug->values[2] = pp->hour;
        bug->values[3] = pp->minute;
        bug->values[4] = pp->second;
-       bug->values[5] = pp->msec;
+       bug->values[5] = pp->nsec;
        bug->values[6] = pp->yearstart;
        bug->values[7] = pp->coderecv;
        bug->stimes = 0xfffffffc;
index efdf536fe8dd32aa17ef20ee65dcf04f30dfc211..31244971b77f5ab280486df3b305b8fdbe54820b 100644 (file)
@@ -733,8 +733,9 @@ acts_receive (
         * waiting for carrier loss or long-space disconnect, but we do
         * these clumsy things anyway.
         */
-       record_clock_stats(&peer->srcadr, pp->a_lastcode);
+       pp->lastref = pp->lastrec;
        refclock_receive(peer);
+       record_clock_stats(&peer->srcadr, pp->a_lastcode);
        pp->sloppyclockflag &= ~CLK_FLAG1;
        up->pollcnt = 0;
        (void)write(pp->io.fd, &hangup, 1);
index cdbe2ee38627b53b7739e0d737d302bb30cd61b6..cf5f92f1f5bede707246ec9c260b9a7d6ba1bf1c 100644 (file)
@@ -419,8 +419,9 @@ arb_poll(
                refclock_report(peer, CEVNT_TIMEOUT);
                return;
        }
-       record_clock_stats(&peer->srcadr, pp->a_lastcode);
+       pp->lastref = pp->lastrec;
        refclock_receive(peer);
+       record_clock_stats(&peer->srcadr, pp->a_lastcode);
 }
 
 #else
index c771f478f67774621c6eba24eac622a62bad99a7..cdd51dc42f10d10879a8f5ff4d6d8e9b104d3649 100644 (file)
@@ -1034,11 +1034,6 @@ arc_receive(
                                       '6' : ('0' + up->quality));
        pp->a_lastcode[pp->lencode + 1] = '\0'; /* Terminate for printf(). */
        record_clock_stats(&peer->srcadr, pp->a_lastcode);
-
-       /* We don't use the micro-/milli- second part... */
-       pp->usec = 0;
-       pp->msec = 0;
-
        n = sscanf(pp->a_lastcode, "o%2d%2d%2d%1d%2d%2d%2d%1d%1d",
                   &pp->hour, &pp->minute, &pp->second,
                   &wday, &pp->day, &month, &pp->year, &bst, &status);
@@ -1188,6 +1183,7 @@ arc_receive(
                refclock_report(peer, CEVNT_BADTIME);
                return;
        }
+       pp->lastref = pp->lastrec;
        refclock_receive(peer);
 }
 
index 516f7adc54d4d313608608aa4924d6cc18dc29d7..8c1a80e59b0e20b118b2ddc5c598e24a9aa574bf 100644 (file)
@@ -300,11 +300,12 @@ as2201_receive(
         * Timecode format: "yy:ddd:hh:mm:ss.mmm"
         */
        if (sscanf(pp->a_lastcode, "%2d:%3d:%2d:%2d:%2d.%3d", &pp->year,
-                  &pp->day, &pp->hour, &pp->minute, &pp->second, &pp->msec)
+                  &pp->day, &pp->hour, &pp->minute, &pp->second, &pp->nsec)
            != 6) {
                refclock_report(peer, CEVNT_BADREPLY);
                return;
        }
+       pp->nsec *= 1000000;
 
        /*
         * Test for synchronization (this is a temporary crock).
index cb3592eee34b6c7f99c5da174cf7671b5cb36b93..d42721bf3b26f293fdb7e42403461ab0c52d6c8f 100644 (file)
@@ -489,6 +489,7 @@ atom_poll(
                peer->refid = pp->refid;
        else
                peer->refid = sys_prefer->srcadr.sin_addr.s_addr;
+       pp->lastref = pp->lastrec;
        refclock_receive(peer);
        peer->burst = ASTAGE;
 }
index a3debcb6795bfa1b3e5195b3a345f928942d45c5..a63be44582f43e086e188ee6e689fc7bd6059628 100644 (file)
@@ -317,8 +317,9 @@ vme_poll(
                refclock_report(peer, CEVNT_BADTIME);
                return;
        }
-       record_clock_stats(&peer->srcadr, pp->a_lastcode);
+       pp->lastref = pp->lastrec;
        refclock_receive(peer);
+       record_clock_stats(&peer->srcadr, pp->a_lastcode);
 }
 
 struct vmedate *
index 9273a84fdfa8dd2c3982bd8c8b1b60f5aaaf2ede..a1d131ec0304641337f43327671dae76c0d9aae8 100644 (file)
@@ -215,7 +215,6 @@ chronolog_receive(
         * calls since it is transmitted a few seconds ahead of the
         * timestamp.
         */
-       pp->msec = 0;
        got_good=0;
        if (sscanf(pp->a_lastcode, "Y %d/%d/%d", &up->year,&up->month,&up->day))
        {
@@ -293,8 +292,9 @@ chronolog_receive(
                refclock_report(peer, CEVNT_BADTIME);
                return;
        }
-       record_clock_stats(&peer->srcadr, pp->a_lastcode);
+       pp->lastref = pp->lastrec;
        refclock_receive(peer);
+       record_clock_stats(&peer->srcadr, pp->a_lastcode);
        up->lasthour = pp->hour;
 }
 
index 4f2bb98f0e5a986ba574afcbb1c4f619e25ae690..70fbfe881b09306905456ce639a834ffa349428e 100644 (file)
@@ -320,7 +320,7 @@ struct chuunit {
        int     fd_audio;       /* audio port file descriptor */
        double  comp[SIZE];     /* decompanding table */
        int     port;           /* codec port */
-       int     gain;           /* codec input gain */
+       int     gain;           /* codec gain */
        int     mongain;        /* codec monitor gain */
        int     clipcnt;        /* sample clip count */
        int     seccnt;         /* second interval counter */
@@ -1317,8 +1317,8 @@ chu_poll(
         * correct and can be selected to discipline the clock.
         */
        if (temp > 0) {
-               record_clock_stats(&peer->srcadr, pp->a_lastcode);
                refclock_receive(peer);
+               record_clock_stats(&peer->srcadr, pp->a_lastcode);
        } else if (pp->sloppyclockflag & CLK_FLAG4) {
                record_clock_stats(&peer->srcadr, pp->a_lastcode);
        }
@@ -1424,15 +1424,16 @@ chu_major(
                up->errflg = CEVNT_BADREPLY;
                return (0);
        }
-       L_CLR(&offset);
        if (!clocktime(pp->day, pp->hour, pp->minute, 0, GMT,
            up->tstamp[0].l_ui, &pp->yearstart, &offset.l_ui)) {
                up->errflg = CEVNT_BADTIME;
                return (0);
        }
+       offset.l_uf = 0;
        for (i = 0; i < up->ntstamp; i++)
-               refclock_process_offset(pp, offset, up->tstamp[i], FUDGE +
-                   pp->fudgetime1);
+               refclock_process_offset(pp, offset, up->tstamp[i],
+                   FUDGE + pp->fudgetime1);
+       pp->lastref = up->timestamp;
        return (i);
 }
 
index db03c95f2c646b0242cd09f072a705c7de8a1436..82b73690f46d7df906fdb09ed11e971a0d4a83bb 100644 (file)
@@ -712,6 +712,7 @@ datum_pts_receive(
                               &datum_pts->yearstart,
                               &datum_pts->lastref.l_ui) ) {
 
+                       datum_pts->lastref.l_uf = 0;
                        error = datum_pts->lastref.l_ui - datum_pts->lastrec.l_ui;
 
 #ifdef DEBUG_DATUM_PTC
@@ -813,6 +814,7 @@ datum_pts_receive(
        ** necessary to use fudge factors in the ntp.conf file. Maybe later we will.
        */
       /*LFPTOD(&tstmp, doffset);*/
+       datum_pts->lastref = datum_pts->lastrec;
        refclock_receive(datum_pts->peer);
 
        /*
index c439646f9130604b31095fb0919e01ceef2bf8bf..355abf4c4ca7781bd077581f3b28b988445c1d38 100644 (file)
@@ -232,7 +232,6 @@ dumbclock_receive(
        /*
         * We get down to business. Check the timecode format...
         */
-       pp->msec = 0;
        got_good=0;
        if (sscanf(pp->a_lastcode,"%02d:%02d:%02d",
                   &hours,&minutes,&seconds) == 3)
@@ -330,8 +329,9 @@ dumbclock_receive(
                refclock_report(peer, CEVNT_BADTIME);
                return;
        }
-       record_clock_stats(&peer->srcadr, pp->a_lastcode);
+       pp->lastref = pp->lastrec;
        refclock_receive(peer);
+       record_clock_stats(&peer->srcadr, pp->a_lastcode);
        up->lasthour = pp->hour;
 }
 
index 655b6bcda1313cb78337a897e03253b5d89b9f99..63c72deea37fa2a2e421f762fa98be33fff0c8c0 100644 (file)
@@ -299,14 +299,14 @@ fg_receive(
        {
                pp->minute = BP1(7)*10 + BP2(7);
                pp->second = BP1(8)*10 + BP2(8);
-               pp->msec = BP1(9)*10 + BP2(9);
-               pp->usec = BP1(10);
+               pp->nsec = (BP1(9)*10 + BP2(9)) * 1000000;
+               pp->nsec += BP1(10) * 1000;
        } else {
                pp->hour = BP1(5)*10 + BP2(5);
                pp->minute = BP1(6)*10 + BP2(6);
                pp->second = BP1(7)*10 + BP2(7);
-               pp->msec = BP1(8)*10 + BP2(8);
-               pp->usec = BP1(9);
+               pp->nsec = (BP1(8)*10 + BP2(8)) * 1000000;
+               pp->nsec += BP1(9) * 1000;
        }
         
        if((pp->hour == 10) && (pp->minute == 10))
@@ -337,7 +337,7 @@ fg_receive(
 
         if (!refclock_process(pp))
                 refclock_report(peer, CEVNT_BADTIME);
-        
+        pp->lastref = pp->lastrec;
        refclock_receive(peer);
        return;
 }
index 42eb2f981b2be2ca72a0e95cf0a8cb8a4f9589d0..a7fcf5f62eb8356c6bb1c2701c1a121e68f2c0ed 100644 (file)
@@ -349,6 +349,7 @@ vme_poll(
        l_fp tstmp;
        time_t tloc;
        struct tm *tadr;
+       long ltemp;
 
         
  
@@ -395,13 +396,13 @@ vme_poll(
        vme->hour =   tptr->hr;
        vme->minute =  tptr->mn;
        vme->second =  tptr->sec;
-       vme->usec =   tptr->frac;
+       vme->nsec =   tptr->frac * 1000;
 
 #ifdef DEBUG
        if (debug)
            printf("vme: %3d %02d:%02d:%02d.%06ld %1x\n",
                   vme->day, vme->hour, vme->minute, vme->second,
-                  vme->usec, tptr->status);
+                  vme->nsec, tptr->status);
 #endif
        if (tptr->status ) {       /*  Status 0 is locked to ref., 1 is not */
                vme_report_event(vme, CEVNT_BADREPLY);
@@ -424,14 +425,16 @@ vme_poll(
                msyslog(LOG_ERR, "refclock_gpsvme: bad data!!");
                return;
        }
-       TVUTOTSF(vme->usec, vme->lastref.l_uf);
+       vme->lastref.l_uf = 0;
+       DTOLFP(vme->nsec / 1e9, &ltemp);
+       L_ADD(&vme->lastrec, &ltemp);
        tstmp = vme->lastref;
 
        L_SUB(&tstmp, &vme->lastrec);
        vme->coderecv++;
 
        L_ADD(&tstmp, &(fudgefactor[vme->unit]));
-
+       vme->lastref = vme->lastrec;
        refclock_receive(vme->peer);
 }
 
@@ -548,7 +551,7 @@ vme_buginfo(
        bug->values[4] = (u_long)vme->hour;
        bug->values[5] = (u_long)vme->minute;
        bug->values[6] = (u_long)vme->second;
-       bug->values[7] = (u_long)vme->usec;
+       bug->values[7] = (u_long)vme->nsec;
        bug->values[9] = vme->yearstart;
        bug->stimes = 0x1c;
        bug->times[0] = vme->lastref;
index ef4db5a4d4f867c3ed8e012417780484c0b1e691..ee9cfcca3912dc27668ef387f3cfe8307e606a98 100644 (file)
@@ -176,14 +176,6 @@ static int day2tab[] = {31, 29, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31};
  */
 static int speed[] = {B1200, B2400, B4800, B9600};
 
-/*
- * Unit control structure
- */
-struct heathunit {
-       int     pollcnt;        /* poll message counter */
-       l_fp    tstamp;         /* timestamp of last poll */
-};
-
 /*
  * Function prototypes
  */
@@ -215,7 +207,6 @@ heath_start(
        struct peer *peer
        )
 {
-       register struct heathunit *up;
        struct refclockproc *pp;
        int fd;
        char device[20];
@@ -226,16 +217,6 @@ heath_start(
        (void)sprintf(device, DEVICE, unit);
        if (!(fd = refclock_open(device, speed[peer->ttlmax & 0x3], 0)))
            return (0);
-
-       /*
-        * Allocate and initialize unit structure
-        */
-       if (!(up = (struct heathunit *)
-             emalloc(sizeof(struct heathunit)))) {
-               (void) close(fd);
-               return (0);
-       }
-       memset((char *)up, 0, sizeof(struct heathunit));
        pp = peer->procptr;
        pp->io.clock_recv = heath_receive;
        pp->io.srcclock = (caddr_t)peer;
@@ -243,10 +224,8 @@ heath_start(
        pp->io.fd = fd;
        if (!io_addclock(&pp->io)) {
                (void) close(fd);
-               free(up);
                return (0);
        }
-       pp->unitptr = (caddr_t)up;
 
        /*
         * Initialize miscellaneous variables
@@ -255,7 +234,6 @@ heath_start(
        peer->burst = NSTAGE;
        pp->clockdesc = DESCRIPTION;
        memcpy((char *)&pp->refid, REFID, 4);
-       up->pollcnt = 2;
        return (1);
 }
 
@@ -269,13 +247,10 @@ heath_shutdown(
        struct peer *peer
        )
 {
-       register struct heathunit *up;
        struct refclockproc *pp;
 
        pp = peer->procptr;
-       up = (struct heathunit *)pp->unitptr;
        io_closeclock(&pp->io);
-       free(up);
 }
 
 
@@ -287,7 +262,6 @@ heath_receive(
        struct recvbuf *rbufp
        )
 {
-       register struct heathunit *up;
        struct refclockproc *pp;
        struct peer *peer;
        l_fp trtmp;
@@ -300,26 +274,9 @@ heath_receive(
         */
        peer = (struct peer *)rbufp->recv_srcclock;
        pp = peer->procptr;
-       up = (struct heathunit *)pp->unitptr;
        pp->lencode = refclock_gtlin(rbufp, pp->a_lastcode, BMAX,
            &trtmp);
 
-       /*
-        * We get a buffer and timestamp for each <cr>; however, we use
-        * the timestamp captured at the RTS modem control line toggle
-        * on the assumption that's what the radio bases the timecode
-        * on. Apparently, the radio takes about a second to make up its
-        * mind to send a timecode, so the receive timestamp is
-        * worthless.
-        */
-       pp->lastrec = up->tstamp;
-       up->pollcnt = 2;
-#ifdef DEBUG
-       if (debug)
-           printf("heath: timecode %d %s\n", pp->lencode,
-                  pp->a_lastcode);
-#endif
-
        /*
         * We get down to business, check the timecode format and decode
         * its contents. If the timecode has invalid length or is not in
@@ -396,7 +353,7 @@ heath_receive(
        if (!isdigit((int)dsec))
                pp->leap = LEAP_NOTINSYNC;
        else {
-               pp->msec = (dsec - '0') * 100;
+               pp->nsec = (dsec - '0') * 100000000;
                pp->leap = LEAP_NOWARNING;
        }
        if (!refclock_process(pp))
@@ -413,7 +370,6 @@ heath_poll(
        struct peer *peer
        )
 {
-       register struct heathunit *up;
        struct refclockproc *pp;
        int bits = TIOCM_RTS;
 
@@ -421,10 +377,11 @@ heath_poll(
         * At each poll we check for timeout and toggle the RTS modem
         * control line, then take a timestamp. Presumably, this is the
         * event the radio captures to generate the timecode.
+        * Apparently, the radio takes about a second to make up its
+        * mind to send a timecode, so the receive timestamp is
+        * worthless.
         */
        pp = peer->procptr;
-       up = (struct heathunit *)pp->unitptr;
-       pp->polls++;
 
        /*
         * We toggle the RTS modem control lead (GC-1000) and sent a T
@@ -437,19 +394,26 @@ heath_poll(
         */
        if (ioctl(pp->io.fd, TIOCMBIC, (char *)&bits) < 0)
                refclock_report(peer, CEVNT_FAULT);
-       get_systime(&up->tstamp);
-       ioctl(pp->io.fd, TIOCMBIS, (char *)&bits);
+       get_systime(&pp->lastrec);
        if (write(pp->io.fd, "T", 1) != 1)
                refclock_report(peer, CEVNT_FAULT);
+       ioctl(pp->io.fd, TIOCMBIS, (char *)&bits);
        if (peer->burst > 0)
                return;
        if (pp->coderecv == pp->codeproc) {
                refclock_report(peer, CEVNT_TIMEOUT);
                return;
        }
-       record_clock_stats(&peer->srcadr, pp->a_lastcode);
+       pp->lastref = pp->lastrec;
        refclock_receive(peer);
-       peer->burst = NSTAGE;
+       record_clock_stats(&peer->srcadr, pp->a_lastcode);
+#ifdef DEBUG
+       if (debug)
+           printf("heath: timecode %d %s\n", pp->lencode,
+                  pp->a_lastcode);
+#endif
+       peer->burst = MAXSTAGE;
+       pp->polls++;
 }
 
 #else
index a9deb21c17dca9b7329792669e183131fc09591c..007dcd696fee645a27d9c230926f4223ea1b9be6 100644 (file)
@@ -262,10 +262,9 @@ hopfpci_poll(
                refclock_report(peer, CEVNT_BADTIME);
                return;
        }
+       pp->lastref = pp->lastrec;
        refclock_receive(peer);
-
        record_clock_stats(&peer->srcadr, pp->a_lastcode);
-
        return;
 }
 
index a9d74dda1d757b1a22ce3f4330a336c8b72a0d41..9090862c879f4e27e43e651746865af8dd264fa7 100644 (file)
@@ -329,6 +329,7 @@ hopfserial_receive (
                refclock_report(peer, CEVNT_BADTIME);
                return;
        }
+       pp->lastref = pp->lastrec;
        refclock_receive(peer);
 
 #if 0
index 7a506cfc7f9587edc9ee4877a22b6c961ea1c3f9..7c801bb211db313225cb6831db612c98efae6944 100644 (file)
@@ -554,6 +554,7 @@ hpgps_receive(
                refclock_report(peer, CEVNT_BADTIME);
                return;
        }
+       pp->lastref = pp->lastrec;
        refclock_receive(peer);
 
        /*
index 6933f8a118e69d11e9165b496bed17170083050d..ade4611afb01d43b4ecdc23d8408e6858895df26 100644 (file)
@@ -75,8 +75,8 @@
  * o The modulation index is less than MODMIN (0.5). This usually means
  *   overdriven IRIG signal or wrong IRIG format.
  *
- * o A frame synchronization error has occurred. This usually means wrong
- *   IRIG signal format or the IRIG signal source has lost
+ * o A frame synchronization error has occurred. This usually means
+ *   wrong IRIG signal format or the IRIG signal source has lost
  *   synchronization (signature control).
  *
  * o A data decoding error has occurred. This usually means wrong IRIG
 #define PI             3.1415926535 /* the real thing */
 
 /*
- * Experimentally determined fudge factors
+ * Experimentally determined filter delays
  */
-#define IRIG_B         .0019           /* IRIG-B phase delay */
-#define IRIG_E         .0019           /* IRIG-E phase delay */
+#define IRIG_B         .0019   /* IRIG-B filter delay */
+#define IRIG_E         .0019   /* IRIG-E filter delay */
 
 /*
  * Data bit definitions
 #define IRIG_ERR_DECODE        0x10    /* frame decoding error */
 #define IRIG_ERR_CHECK 0x20    /* second numbering discrepancy */
 #define IRIG_ERR_ERROR 0x40    /* codec error (overrun) */
+#define IRIG_ERR_SIGERR        0x80    /* IRIG status error (Spectracom) */
 
 /*
  * IRIG unit control structure
@@ -190,7 +191,6 @@ struct irigunit {
        u_char  timecode[21];   /* timecode string */
        l_fp    timestamp;      /* audio sample timestamp */
        l_fp    tick;           /* audio sample increment */
-       double  comp[SIZE];     /* decompanding table */
        double  integ[BAUD];    /* baud integrator */
        double  phase, freq;    /* logical clock phase and frequency */
        double  zxing;          /* phase detector integrator */
@@ -199,13 +199,15 @@ struct irigunit {
        double  irig_b;         /* IRIG-B signal amplitude */
        double  irig_e;         /* IRIG-E signal amplitude */
        int     errflg;         /* error flags */
-       int     pollcnt;        /* poll counter */
+       /*
+        * Audio codec variables
+        */
+       double  comp[SIZE];     /* decompanding table */
        int     port;           /* codec port */
        int     gain;           /* codec gain */
        int     mongain;        /* codec monitor gain */
        int     clipcnt;        /* sample clipped count */
        int     seccnt;         /* second interval counter */
-       int     decim;          /* sample decimation factor */
 
        /*
         * RF variables
@@ -222,6 +224,7 @@ struct irigunit {
        double  lastsig;        /* last carrier sample */
        double  xxing;          /* phase detector interpolated output */
        double  fdelay;         /* filter delay */
+       int     decim;          /* sample decimation factor */
        int     envphase;       /* envelope phase */
        int     envptr;         /* envelope phase pointer */
        int     carphase;       /* carrier phase */
@@ -234,8 +237,6 @@ struct irigunit {
        /*
         * Decoder variables
         */
-       l_fp    montime;        /* reference timestamp for eyeball */
-       int     timecnt;        /* timecode counter */
        int     pulse;          /* cycle counter */
        int     cycles;         /* carrier cycles */
        int     dcycles;        /* data cycles */
@@ -280,10 +281,10 @@ struct    refclock refclock_irig = {
  * Global variables
  */
 static char    hexchar[] = {   /* really quick decoding table */
-       '0', '8', '4', 'c',             /* 0000 0001 0010 0011 */
-       '2', 'a', '6', 'e',             /* 0100 0101 0110 0111 */
-       '1', '9', '5', 'd',             /* 1000 1001 1010 1011 */
-       '3', 'b', '7', 'f'              /* 1100 1101 1110 1111 */
+       '0', '8', '4', 'c',     /* 0000 0001 0010 0011 */
+       '2', 'a', '6', 'e',     /* 0100 0101 0110 0111 */
+       '1', '9', '5', 'd',     /* 1000 1001 1010 1011 */
+       '3', 'b', '7', 'f'      /* 1100 1101 1110 1111 */
 };
 
 
@@ -348,7 +349,6 @@ irig_start(
        up->decim = 1;
        up->fdelay = IRIG_B;
        up->gain = 127;
-       up->pollcnt = 2;
 
        /*
         * The companded samples are encoded sign-magnitude. The table
@@ -362,7 +362,7 @@ irig_start(
                up->comp[i] = up->comp[i - 1] + step;
                up->comp[OFFSET + i] = -up->comp[i];
                 if (i % 16 == 0)
-                   step *= 2.;
+                       step *= 2.;
        }
        DTOLFP(1. / SECOND, &up->tick);
        return (1);
@@ -519,7 +519,7 @@ irig_rf(
 
        /*
         * IRIG-B filter. 4th-order elliptic, 800-Hz highpass, 0.3 dB
-        * passband ripple, -50 dB stopband ripple, phase delay -.0022
+        * passband ripple, -50 dB stopband ripple, phase delay .0022
         * s)
         */
        irig_b = (up->hpf[4] = up->hpf[3]) * 2.322484e-01;
@@ -556,9 +556,9 @@ irig_rf(
        up->badcnt = (up->badcnt + 1) % up->decim;
        if (up->badcnt == 0) {
                if (up->decim == 1)
-                   irig_base(peer, irig_b);
+                       irig_base(peer, irig_b);
                else
-                   irig_base(peer, irig_e);
+                       irig_base(peer, irig_e);
        }
 }
 
@@ -627,16 +627,17 @@ irig_base(
                up->maxsignal = up->intmax;
                up->noise = up->intmin;
                if (up->maxsignal < DRPOUT)
-                   up->errflg |= IRIG_ERR_AMP;
+                       up->errflg |= IRIG_ERR_AMP;
                if (up->intmax > 0)
-                   up->modndx = (up->intmax - up->intmin) / up->intmax;
+                       up->modndx = (up->intmax - up->intmin) /
+                           up->intmax;
                else
-                   up->modndx = 0;
+                       up->modndx = 0;
                if (up->modndx < MODMIN)
-                   up->errflg |= IRIG_ERR_MOD;
+                       up->errflg |= IRIG_ERR_MOD;
                up->intmin = 1e6; up->intmax = 0;
                if (up->errflg & (IRIG_ERR_AMP | IRIG_ERR_FREQ |
-                                 IRIG_ERR_MOD | IRIG_ERR_SYNCH)) {
+                  IRIG_ERR_MOD | IRIG_ERR_SYNCH)) {
                        up->tc = MINTC;
                        up->tcount = 0;
                }
@@ -672,13 +673,13 @@ irig_base(
         * the slice level and left-shifted in the decoding register.
         */
        if (up->carphase != 7)
-           return;
+               return;
        env = (up->lastenv[2] - up->lastenv[6]) / 2.;
        lope = (up->lastint[2] - up->lastint[6]) / 2.;
        if (lope > up->intmax)
-           up->intmax = lope;
+               up->intmax = lope;
        if (lope < up->intmin)
-           up->intmin = lope;
+               up->intmin = lope;
 
        /*
         * Pulse code demodulator and reference timestamp. The decoder
@@ -688,15 +689,15 @@ irig_base(
         */
        up->pulse = (up->pulse + 1) % 10;
        if (up->pulse == 1)
-           up->envmax = env;
+               up->envmax = env;
        else if (up->pulse == 9)
-           up->envmin = env;
+               up->envmin = env;
        up->dcycles <<= 1;
        if (env >= (up->envmax + up->envmin) / 2.)
-           up->dcycles |= 1;
+               up->dcycles |= 1;
        up->cycles <<= 1;
        if (lope >= (up->maxsignal + up->noise) / 2.)
-           up->cycles |= 1;
+               up->cycles |= 1;
        if ((up->cycles & 0x303c0f03) == 0x300c0300) {
                l_fp ltemp;
                int bitz;
@@ -709,18 +710,18 @@ irig_base(
                 * persist for lots of samples.
                 */
                if (up->pulse != 9)
-                   up->errflg |= IRIG_ERR_SYNCH;
+                       up->errflg |= IRIG_ERR_SYNCH;
                up->pulse = 9;
                dtemp = BAUD - up->zxing;
                i = up->envxing - up->envphase;
                if (i < 0)
-                   i -= i;
+                       i -= i;
                if (i <= 1) {
                        up->tcount++;
                        if (up->tcount > 50 * up->tc) {
                                up->tc++;
                                if (up->tc > MAXTC)
-                                   up->tc = MAXTC;
+                                       up->tc = MAXTC;
                                up->tcount = 0;
                                up->envxing = up->envphase;
                        } else {
@@ -739,7 +740,7 @@ irig_base(
                 * zero crossing.
                 */
                DTOLFP(up->decim * (dtemp / SECOND + 1.) + up->fdelay,
-                      &ltemp);
+                   &ltemp);
                pp->lastrec = up->timestamp;
                L_SUB(&pp->lastrec, &ltemp);
 
@@ -754,23 +755,23 @@ irig_base(
                bitz = up->dcycles & 0xfc;
                switch(bitz) {
 
-                   case 0x00:
-                   case 0x80:
+               case 0x00:
+               case 0x80:
                        irig_decode(peer, BIT0);
                        break;
 
-                   case 0xc0:
-                   case 0xe0:
-                   case 0xf0:
+               case 0xc0:
+               case 0xe0:
+               case 0xf0:
                        irig_decode(peer, BIT1);
                        break;
 
-                   case 0xf8:
-                   case 0xfc:
+               case 0xf8:
+               case 0xfc:
                        irig_decode(peer, BITP);
                        break;
 
-                   default:
+               default:
                        irig_decode(peer, 0);
                        up->errflg |= IRIG_ERR_DECODE;
                }
@@ -799,7 +800,7 @@ irig_decode(
        /*
         * Local variables
         */
-       char    syncchar;       /* sync character (Spectracom only) */
+       char    syncchar;       /* sync character (Spectracom) */
        char    sbs[6];         /* binary seconds since 0h */
        char    spare[2];       /* mulligan digits */
 
@@ -822,15 +823,9 @@ irig_decode(
                up->bitcnt = 1;
                up->fieldcnt = 0;
                up->lastbit = 0;
-               up->montime = pp->lastrec;
                if (up->errflg == 0) {
-                       up->timecnt++;
                        refclock_process(pp);
-               }
-               if (up->timecnt >= MAXSTAGE) {
-                       refclock_receive(peer);
-                       up->timecnt = 0;
-                       up->pollcnt = 2;
+                       pp->lastref = up->timestamp;
                }
                up->errflg = 0;
        }
@@ -846,45 +841,58 @@ irig_decode(
                if (up->xptr < 2)
                    up->xptr = 2 * FIELD;
                up->timecode[--up->xptr] = hexchar[(up->bits >> 5) &
-                                                 0xf];
+                   0xf];
                up->timecode[--up->xptr] = hexchar[up->bits & 0xf];
                up->fieldcnt = (up->fieldcnt + 1) % FIELD;
                if (up->fieldcnt == 0) {
 
                        /*
-                        * End of field. Decode the timecode, adjust the
-                        * gain and set the input port. Set the port
-                        * here on the assumption somebody might even
-                        * change it on-wing.
+                        * End of field. Decode the timecode and wind
+                        * the clock. Not all IRIG generators have the
+                        * year; if so, it is nonzero after year 2000.
+                        * Not all have the hardware status bit; if so,
+                        * it is lit when the source is okay and dim
+                        * when bad. We watch this only if the year is
+                        * nonzero. Not all are configured for signature
+                        * control. If so, all BCD digits are set to
+                        * zero if the source is bad. In this case the
+                        * refclock_process() will reject the timecode
+                        * as invalid.
                         */
                        up->xptr = 2 * FIELD;
                        if (sscanf((char *)up->timecode,
-                                  "%6s%2d%c%2s%3d%2d%2d%2d",
-                                  sbs, &pp->year, &syncchar, spare, &pp->day,
-                                  &pp->hour, &pp->minute, &pp->second) != 8)
-                           pp->leap = LEAP_NOTINSYNC;
+                          "%6s%2d%c%2s%3d%2d%2d%2d", sbs, &pp->year,
+                           &syncchar, spare, &pp->day, &pp->hour,
+                           &pp->minute, &pp->second) != 8)
+                               pp->leap = LEAP_NOTINSYNC;
                        else
-                           pp->leap = LEAP_NOWARNING;
+                               pp->leap = LEAP_NOWARNING;
                        up->second = (up->second + up->decim) % 60;
+                       if (pp->year > 0) {
+                               pp->year += 2000;
+                               if (syncchar == '0')
+                                       up->errflg |= IRIG_ERR_CHECK;
+                       }
                        if (pp->second != up->second)
-                           up->errflg |= IRIG_ERR_CHECK;
+                               up->errflg |= IRIG_ERR_CHECK;
                        up->second = pp->second;
                        sprintf(pp->a_lastcode,
-                               "%02x %c %2d %3d %02d:%02d:%02d %4.0f %3d %6.3f %2d %2d %6.3f %6.1f %s",
-                               up->errflg, syncchar, pp->year, pp->day,
-                               pp->hour, pp->minute, pp->second,
-                               up->maxsignal, up->gain, up->modndx,
-                               up->envxing, up->tc, up->yxing, up->freq *
-                               1e6 / SECOND, ulfptoa(&up->montime, 6));
+                           "%02x %c %2d %3d %02d:%02d:%02d %4.0f %3d %6.3f %2d %2d %6.3f %6.1f",
+                           up->errflg, syncchar, pp->year, pp->day,
+                           pp->hour, pp->minute, pp->second,
+                           up->maxsignal, up->gain, up->modndx,
+                           up->envxing, up->tc, up->yxing, up->freq *
+                           1e6 / SECOND);
                        pp->lencode = strlen(pp->a_lastcode);
-                       if (up->timecnt == 0 || pp->sloppyclockflag &
-                           CLK_FLAG4)
-                           record_clock_stats(&peer->srcadr,
-                                              pp->a_lastcode);
+                       if (pp->sloppyclockflag & CLK_FLAG4) {
+                               record_clock_stats(&peer->srcadr,
+                                   pp->a_lastcode);
 #ifdef DEBUG
-                       if (debug > 2)
-                           printf("irig: %s\n", pp->a_lastcode);
+                               if (debug)
+                                       printf("irig: %s\n",
+                                           pp->a_lastcode);
 #endif /* DEBUG */
+                       }
                }
        }
        up->lastbit = bit;
@@ -894,9 +902,10 @@ irig_decode(
 /*
  * irig_poll - called by the transmit procedure
  *
- * This routine keeps track of status. If nothing is heard for two
- * successive poll intervals, a timeout event is declared and any
- * orphaned timecode updates are sent to foster care. 
+ * This routine sweeps up the timecode updates since the last poll. For
+ * IRIG-B there should be at least 60 updates; for IRIG-E there should
+ * be at least 6. If nothing is heard, a timeout event is declared and
+ * any orphaned timecode updates are sent to foster care. 
  */
 static void
 irig_poll(
@@ -910,15 +919,17 @@ irig_poll(
        pp = peer->procptr;
        up = (struct irigunit *)pp->unitptr;
 
-       /*
-        * Keep book for tattletales
-        */
-       if (up->pollcnt == 0) {
+       if (pp->coderecv == pp->codeproc) {
                refclock_report(peer, CEVNT_TIMEOUT);
-               up->timecnt = 0;
                return;
+       } else {
+               refclock_receive(peer);
+               record_clock_stats(&peer->srcadr, pp->a_lastcode);
+#ifdef DEBUG
+               if (debug)
+                       printf("irig: %s\n", pp->a_lastcode);
+#endif /* DEBUG */
        }
-       up->pollcnt--;
        pp->polls++;
        
 }
@@ -962,7 +973,6 @@ irig_gain(
        up->clipcnt = 0;
 }
 
-
 #else
 int refclock_irig_bs;
 #endif /* REFCLOCK */
index 804c4a22e09d7361dd808bc47e7873936d4de121..eee3d7e30b692283b72fd78ab0e77ede668f4516 100644 (file)
@@ -423,8 +423,7 @@ jjy_receive ( struct recvbuf *rbufp )
        pp->hour   = up->hour ;
        pp->minute = up->minute ;
        pp->second = up->second ;
-       pp->msec   = up->msecond ;
-       pp->usec   = 0;
+       pp->nsec   = up->msecond * 1000000;
 
        /* 
         * JST to UTC 
@@ -461,10 +460,9 @@ jjy_receive ( struct recvbuf *rbufp )
 
        sprintf ( sLogText, "%04d/%02d/%02d %02d:%02d:%02d JST",
                  up->year, up->month, up->day, up->hour, up->minute, up->second ) ;
-       record_clock_stats ( &peer->srcadr, sLogText ) ;
-
+       pp->lastref = pp->lastrec;
        refclock_receive(peer);
-
+       record_clock_stats ( &peer->srcadr, sLogText ) ;
 }
 
 /**************************************************************************************************/
index 4d1d4c24dbd22920e4e6a8965c3f4408e0bc4d8c..75d7d1a6fe403c971be3e59e1fb2fa2f820dadb4 100644 (file)
@@ -556,7 +556,7 @@ avoided firmware bug (stime %.2f, laststime %.2f)\n",
                            pp->year, pp->day,
                            pp->hour, pp->minute, pp->second,
                            prettydate(&pp->lastrec), lfptoa(&pp->offset, 6));
-
+                       pp->lastref = pp->lastrec;
                        refclock_receive(peer);
 
                        /*
@@ -633,11 +633,9 @@ jupiter_offset(register struct peer *peer)
                pp->lastrec.l_ui, &pp->yearstart, &offset.l_ui)) {
                return ("jupiter_process: clocktime failed");
        }
-       if (pp->usec) {
-               TVUTOTSF(pp->usec, offset.l_uf);
-       } else {
-               MSUTOTSF(pp->msec, offset.l_uf);
-       }
+       offset.l_uf = 0;
+        DTOLFP(pp->nsec / 1e9, &ltemp);
+        L_ADD(&offset, &ltemp);
        L_ADD(&offset, &pp->fudgetime1);
        up->lastref = offset;   /* save last reference time */
        L_SUB(&offset, &pp->lastrec); /* form true offset */
@@ -876,8 +874,6 @@ jupiter_parse_t(register struct peer *peer, register u_short *sp)
                pp->hour = jt->hour;
                pp->minute = jt->minute;
                pp->second = jt->second;
-               pp->msec = 0;
-               pp->usec = 0;
        }
 
        /* XXX debugging */
index 42b02fce81d9e42c1d5d42b0ea0b0f7391cc8a2e..d7cd9bbd61687e2c55c70013d30615c0ffdfdf94 100644 (file)
@@ -446,6 +446,7 @@ leitch_receive(
                        leitch->state = STATE_IDLE;
                        break;
                }
+               leitch->reftime1.l_uf = 0;
 #ifdef DEBUG
                if (debug)
                    fprintf(stderr, "%lu\n", (u_long)leitch->reftime1.l_ui);
index 4f131cd1969af5788263269dd891d9939c2cfcfd..70c1a8b3b4e215d09e3f3be5262ed6c33eb16670 100644 (file)
@@ -252,6 +252,7 @@ local_poll(
                ext_enable = 0;
        }
 #endif /* KERNEL_PLL STA_CLK */
+       pp->lastref = pp->lastrec;
        refclock_receive(peer);
        pp->fudgetime1 = 0;
 }
index 3c520b0b190e93e1277be75bbed6817d1f8264c3..0435ad5c0ff9610187092550f184507abb32299e 100644 (file)
@@ -892,7 +892,7 @@ mx4200_receive(
                mx4200_debug(peer, "%4d-%03d %02d:%02d:%02d at %s, %.6f\n",
                    pp->year, pp->day, pp->hour, pp->minute, pp->second,
                    prettydate(&pp->lastrec), pp->offset);
-
+               pp->lastref = pp->lastrec;
                refclock_receive(peer);
 
                /*
@@ -1103,8 +1103,6 @@ mx4200_parse_t(
        pp->hour   = hour;
        pp->minute = minute;
        pp->second = second;
-       pp->msec   = 0;
-       pp->usec   = 0;
 
        /*
         * Toss if sentence is marked invalid
index e9304eed11ec93d173299ccac69dc32cacc01133..a8be38e618f945893757dc8cc5176ee8c32331c0 100644 (file)
@@ -530,21 +530,21 @@ nmea_receive(
        /* Default to 0 milliseconds, if decimal convert milliseconds in
           one, two or three digits
        */
-       pp->msec = 0; 
+       pp->nsec = 0; 
        if (dp[6] == '.') {
                if (isdigit((int)dp[7])) {
-                       pp->msec = (dp[7] - '0') * 100;
+                       pp->nsec = (dp[7] - '0') * 100000000;
                        if (isdigit((int)dp[8])) {
-                               pp->msec += (dp[8] - '0') * 10;
+                               pp->nsec += (dp[8] - '0') * 10000000;
                                if (isdigit((int)dp[9])) {
-                                       pp->msec += (dp[9] - '0');
+                                       pp->nsec += (dp[9] - '0') * 1000000;
                                }
                        }
                }
        }
 
        if (pp->hour > 23 || pp->minute > 59 || pp->second > 59
-         || pp->msec > 1000) {
+         || pp->nsec > 1000000000) {
                refclock_report(peer, CEVNT_BADTIME);
                return;
        }
@@ -604,7 +604,7 @@ nmea_receive(
         */
        if (nmea_pps(up, &rd_tmp) == 1) {
                pp->lastrec = up->tstamp = rd_tmp;
-               pp->msec = 0;
+               pp->nsec = 0;
        }
 #endif /* HAVE_PPSAPI */
 
@@ -630,7 +630,7 @@ nmea_receive(
        if (!up->polled)
            return;
        up->polled = 0;
-
+       pp->lastref = pp->lastrec;
        refclock_receive(peer);
 
         /* If we get here - what we got from the clock is OK, so say so */
index 43a38fb6dd71b7c040b124319adf918d20b5275f..f988618bcedd0dc6ccef0889dd9af61f65a8508a 100644 (file)
@@ -2466,7 +2466,6 @@ oncore_get_timestamp(
 
        ts.l_ui += JAN_1970;
        instance->pp->lastrec = ts;
-       instance->pp->msec = 0;
 
        ts_tmp = ts;
        ts_tmp.l_ui = 0;        /* zero integer part */
@@ -2533,6 +2532,7 @@ oncore_get_timestamp(
 /*
                instance->pp->dispersion = instance->pp->skew = 0;
 */
+               instance->pp->lastref = instance->pp->lastrec;
                refclock_receive(instance->peer);
        }
 }
index d8ce41197f6cff946c54ccc2bb2dc31beca4b59b..19f6fe73eb1cbedec17464311424baa5214f9c3a 100644 (file)
@@ -385,7 +385,7 @@ if (debug > 1) {
                secint = (long) secs;
                secfrac = secs - secint; /* 0.0 <= secfrac < 1.0 */
 
-               pp->usec = (long) (secfrac * 1000000); 
+               pp->nsec = (long) (secfrac * 1000000000); 
 
                secint %= 86400;    /* Only care about today */
                pp->hour = secint / 3600;
@@ -402,7 +402,7 @@ if (debug > 1) {
        if (debug > 1)
                printf("TSIP_decode: unit %d: %02X #%d %02d:%02d:%02d.%06ld %02d/%02d/%04d UTC %02d\n",
                        up->unit, mb(0) & 0xff, event, pp->hour, pp->minute, 
-                       pp->second, pp->usec, mb(12), mb(11), pp->year, GPS_UTC_Offset);
+                       pp->second, pp->nsec, mb(12), mb(11), pp->year, GPS_UTC_Offset);
 #endif
                /* Only use this packet when no
                 * 8F-AD's are being received
@@ -463,7 +463,7 @@ if (debug > 1) {
                        return 0;
                }
 
-               pp->usec = (long) (getdbl((u_char *) &mb(3)) * 1000000);
+               pp->nsec = (long) (getdbl((u_char *) &mb(3)) * 1000000);
 
                if ((pp->day = day_of_year(&mb(14))) < 0) 
                        break;
@@ -476,7 +476,7 @@ if (debug > 1) {
        if (debug > 1)
 printf("TSIP_decode: unit %d: %02X #%d %02d:%02d:%02d.%06ld %02d/%02d/%04d UTC %02x %s\n",
                        up->unit, mb(0) & 0xff, event, pp->hour, pp->minute, 
-                       pp->second, pp->usec, mb(15), mb(14), pp->year,
+                       pp->second, pp->nsec, mb(15), mb(14), pp->year,
                        mb(19), *Tracking_Status[st]);
 #endif
                return 1;
@@ -534,7 +534,7 @@ palisade_receive (
                printf(
        "palisade_receive: unit %d: %4d %03d %02d:%02d:%02d.%06ld\n",
                        up->unit, pp->year, pp->day, pp->hour, pp->minute, 
-                       pp->second, pp->usec);
+                       pp->second, pp->nsec);
 #endif
 
        /*
@@ -544,7 +544,7 @@ palisade_receive (
         */
 
        (void) sprintf(pp->a_lastcode,"%4d %03d %02d:%02d:%02d.%06ld",
-                  pp->year,pp->day,pp->hour,pp->minute, pp->second,pp->usec); 
+                  pp->year,pp->day,pp->hour,pp->minute, pp->second,pp->nsec); 
        pp->lencode = 24;
 
 #ifdef PALISADE
@@ -571,7 +571,7 @@ palisade_receive (
            printf("palisade_receive: unit %d: %s\n",
                   up->unit, prettydate(&pp->lastrec));
 #endif
-
+       pp->lastref = pp->lastrec;
        refclock_receive(peer
 #ifdef PALISADE
                , &pp->offset, 0, pp->dispersion,
index ff2b28ebeec5b900d31ca455fb0c3048031850c1..d4e9fd17a01538e4e0c09d26cad51c3705db79ec 100644 (file)
@@ -196,9 +196,9 @@ pcf_poll(
        pp->hour = tp->tm_hour;
        pp->minute = tp->tm_min;
        pp->second = tp->tm_sec;
-       pp->usec = buf[16] * 31250;
+       pp->nsec = buf[16] * 31250000;
        if (buf[17] & 1)
-               pp->usec += 500000;
+               pp->nsec += 500000000;
 
 #ifdef DEBUG
        if (debug)
@@ -216,6 +216,7 @@ pcf_poll(
                pp->leap = LEAP_NOTINSYNC;
        else
                pp->leap = LEAP_NOWARNING;
+       pp->lastref = pp->lastrec;
        refclock_receive(peer);
 }
 #else
index b92a2e077ab9f3bc9feb969e5ebf5d3f7e0e344e..2443b2ca9c8ac61e16467a45499ddb785d4abfd3 100644 (file)
@@ -71,7 +71,7 @@
 /*
  * Interface definitions
  */
-#define        DEVICE          "/dev/pst%d" /* device name and unit */
+#define        DEVICE          "/dev/wwv%d" /* device name and unit */
 #define        SPEED232        B9600   /* uart speed (9600 baud) */
 #define        PRECISION       (-10)   /* precision assumed (about 1 ms) */
 #define        WWVREFID        "WWV\0" /* WWV reference ID */
@@ -84,7 +84,7 @@
  * Unit control structure
  */
 struct pstunit {
-       u_char  tcswitch;       /* timecode switch */
+       int     tcswitch;       /* timecode switch */
        char    *lastptr;       /* pointer to timecode data */
 };
 
@@ -155,9 +155,9 @@ pst_start(
         * Initialize miscellaneous variables
         */
        peer->precision = PRECISION;
-       peer->burst = NSTAGE;
        pp->clockdesc = DESCRIPTION;
        memcpy((char *)&pp->refid, WWVREFID, 4);
+       peer->burst = MAXSTAGE;
        return (1);
 }
 
@@ -214,17 +214,12 @@ pst_receive(
         * Note we get a buffer and timestamp for each <cr>, but only
         * the first timestamp is retained.
         */
-       if (!up->tcswitch)
+       if (up->tcswitch == 0)
                pp->lastrec = trtmp;
        up->tcswitch++;
        pp->lencode = up->lastptr - pp->a_lastcode;
        if (up->tcswitch < 3)
                return;
-#ifdef DEBUG
-       if (debug)
-               printf("pst: timecode %d %s\n", pp->lencode,
-                   pp->a_lastcode);
-#endif
 
        /*
         * We get down to business, check the timecode format and decode
@@ -240,13 +235,14 @@ pst_receive(
         * Timecode format:
         * "ahh:mm:ss.fffs yy/dd/mm/ddd frdzycchhSSFTttttuuxx"
         */
-       if (sscanf(pp->a_lastcode, "%c%2d:%2d:%2d.%3d%c %9s%3d%13s%4ld",
-           &ampmchar, &pp->hour, &pp->minute, &pp->second,
-           &pp->msec, &daychar, junque, &pp->day,
-           info, &ltemp) != 10) {
+       if (sscanf(pp->a_lastcode,
+           "%c%2d:%2d:%2d.%3ld%c %9s%3d%13s%4ld",
+           &ampmchar, &pp->hour, &pp->minute, &pp->second, &pp->nsec,
+           &daychar, junque, &pp->day, info, &ltemp) != 10) {
                refclock_report(peer, CEVNT_BADREPLY);
                return;
        }
+       pp->nsec *= 1000000;
 
        /*
         * Decode synchronization, quality and last update. If
@@ -263,7 +259,9 @@ pst_receive(
                memcpy((char *)&pp->refid, WWVREFID, 4);
        if (peer->stratum <= 1)
                peer->refid = pp->refid;
-       pp->disp = PST_PHI * ltemp;
+       if (ltemp == 0)
+               pp->lastref = pp->lastrec;
+       pp->disp = PST_PHI * ltemp * 60;
 
        /*
         * Process the new sample in the median filter and determine the
@@ -290,8 +288,10 @@ pst_poll(
        /*
         * Time to poll the clock. The PSTI/Traconex clock responds to a
         * "QTQDQMT" by returning a timecode in the format specified
-        * above. If nothing is heard from the clock for two polls,
-        * declare a timeout and keep going.
+        * above. Note there is no checking on state, since this may not
+        * be the only customer reading the clock. Only one customer
+        * need poll the clock; all others just listen in. If the clock
+        * becomes unreachable, declare a timeout and keep going.
         */
        pp = peer->procptr;
        up = (struct pstunit *)pp->unitptr;
@@ -299,17 +299,21 @@ pst_poll(
        up->lastptr = pp->a_lastcode;
        if (write(pp->io.fd, "QTQDQMT", 6) != 6)
                refclock_report(peer, CEVNT_FAULT);
-       else
-               pp->polls++;
        if (peer->burst > 0)
                return;
        if (pp->coderecv == pp->codeproc) {
                refclock_report(peer, CEVNT_TIMEOUT);
                return;
        }
-       record_clock_stats(&peer->srcadr, pp->a_lastcode);
        refclock_receive(peer);
-       peer->burst = NSTAGE;
+       record_clock_stats(&peer->srcadr, pp->a_lastcode);
+#ifdef DEBUG
+       if (debug)
+               printf("pst: timecode %d %s\n", pp->lencode,
+                   pp->a_lastcode);
+#endif
+       peer->burst = MAXSTAGE;
+       pp->polls++;
 }
 
 #else
index 3747ce085a8b7236314ab3b42b21bd9f44e44c31..d8c6f1aa21e4a7fa667b1b3ba6875eb4be3de0c1 100644 (file)
@@ -292,6 +292,7 @@ shm_poll(
                refclock_report(peer, CEVNT_BADTIME);
                return;
        }
+       pp->lastref = pp->lastrec;
        refclock_receive(peer);
 }
 
index 159f81745f769ce7561013b3d506f79324dee9b7..a4b2e6ee0a309903cd007ee954bfbd68b26b83ac 100644 (file)
@@ -198,6 +198,8 @@ tpro_poll(
                refclock_report(peer, CEVNT_TIMEOUT);
                return;
        }
+       refclock_receive(peer);
+       pp->lastref = pp->lastrec;
        record_clock_stats(&peer->srcadr, pp->a_lastcode);
        refclock_receive(peer);
        peer->burst = NSTAGE;
index 326a8e92620e31777b6a824bc565c920585933fa..3a4a54e653eb89908428402342327c2cdbc4de3f 100644 (file)
@@ -325,6 +325,7 @@ trak_receive(
                refclock_report(peer, CEVNT_BADTIME);
                return;
         }
+       pp->lastref = pp->lastrec;
        refclock_receive(peer);
 }
 
index dcc362d30096f40ce459fe1af7c11e016189dbc3..e1eaae4b94410883a24610d3af9191a5f2a26dc1 100644 (file)
@@ -503,6 +503,7 @@ true_receive(
                                refclock_report(peer, CEVNT_BADTIME);
                                return;
                        }
+                       off.l_uf = 0;
 #endif
 
                        pp->usec = true_sample720();
@@ -545,8 +546,9 @@ true_receive(
                 * If clock is good we send a NOMINAL message so that
                 * any previous BAD messages are nullified
                 */
-                refclock_report(peer, CEVNT_NOMINAL);
+                pp->lastref = pp->lastrec;
                refclock_receive(peer);
+               refclock_report(peer, CEVNT_NOMINAL);
 
                /*
                 * We have succedded in answering the poll.
index 5bf569a6608071d7edbf03ecec8799b94754040f..1f5e78a86db760ac6882e433e26ae2468e893367 100644 (file)
@@ -248,8 +248,6 @@ ulink_receive(
         * proper format, we declare bad format and exit.
         */
        syncchar = leapchar = modechar = ' ';
-       pp->msec = 0;
-
        switch (pp->lencode ) {
                case LEN33X:
                /*
@@ -347,11 +345,11 @@ ulink_receive(
                 * T  = DST <-> STD transition indicators
                 *
                 */
-               if (sscanf(pp->a_lastcode, "%c%1d%c%4d%3d%*c%2d:%2d:%2d.%2d%c",
+               if (sscanf(pp->a_lastcode, "%c%1d%c%4d%3d%*c%2d:%2d:%2d.%2ld%c",
                       &syncchar, &quality, &modechar, &pp->year, &pp->day,
                       &pp->hour, &pp->minute, &pp->second,
-                       &pp->msec,&leapchar) == 10) {
-               pp->msec *= 10; /* M320 returns 10's of msecs */
+                       &pp->nsec, &leapchar) == 10) {
+               pp->nsec *= 10000000; /* M320 returns 10's of msecs */
                if (leapchar == 'I' ) leapchar = '+';
                if (leapchar == 'D' ) leapchar = '-';
                if (syncchar != '?' ) syncchar = ':';
@@ -487,8 +485,9 @@ ulink_poll(
                 refclock_report(peer, CEVNT_TIMEOUT);
                 return;
         }
-        record_clock_stats(&peer->srcadr, pp->a_lastcode);
-        refclock_receive(peer);
+        pp->lastref = pp->lastrec;
+       refclock_receive(peer);
+       record_clock_stats(&peer->srcadr, pp->a_lastcode);
         peer->burst = NSTAGE;
 
 }
index 30a13300bac5d004fd80ded71dfcba54fedbc3ed..d3689d9308854ed2a72ef40dc7a4da24007bee6e 100644 (file)
@@ -344,8 +344,9 @@ usno_receive(
         * protocol module to chuck out the data. Finaly, we unhook the
         * timeout, arm for the next call, fold the tent and go home.
         */
-       record_clock_stats(&peer->srcadr, pp->a_lastcode);
+       pp->lastref = pp->lastrec;
        refclock_receive(peer);
+       record_clock_stats(&peer->srcadr, pp->a_lastcode);
        pp->sloppyclockflag &= ~CLK_FLAG1;
        up->pollcnt = 0;
        up->state = 0;
index acbf56de940e0fa751d4281ac1a0a27cb5375538..fddf40c4b9f2a50c479ddfa976839897f27eab1f 100644 (file)
@@ -491,17 +491,21 @@ struct chan {
 struct wwvunit {
        l_fp    timestamp;      /* audio sample timestamp */
        l_fp    tick;           /* audio sample increment */
-       double  comp[SIZE];     /* decompanding table */
        double  phase, freq;    /* logical clock phase and frequency */
        double  monitor;        /* audio monitor point */
        int     fd_icom;        /* ICOM file descriptor */
        int     errflg;         /* error flags */
+       int     watch;          /* watchcat */
+       int     swatch;         /* second sync watchcat */
+
+       /*
+        * Audio codec variables
+        */
+       double  comp[SIZE];     /* decompanding table */
        int     port;           /* codec port */
        int     gain;           /* codec gain */
        int     mongain;        /* codec monitor gain */
        int     clipcnt;        /* sample clipped count */
-       int     watch;          /* watchcat */
-       int     swatch;         /* second sync watchcat */
 
        /*
         * Variables used to establish basic system timing
@@ -854,11 +858,10 @@ wwv_poll(
        up = (struct wwvunit *)pp->unitptr;
        if (pp->coderecv == pp->codeproc)
                up->errflg = CEVNT_TIMEOUT;
-       else
-               pp->polls++;
        if (up->errflg)
                refclock_report(peer, up->errflg);
        up->errflg = 0;
+       pp->polls++;
 }
 
 
@@ -2028,13 +2031,14 @@ wwv_rsec(
        /*
         * If all nine digits have been found and compared correctly,
         * determine the current offset from the time of century and the
-        * sample timestamp. If in second sync, declare victory and
-        * clamp the root dispersion.
+        * sample timestamp. If in second sync for a couple of minutes,
+        * declare victory.
         */
        if (up->digcnt >= 9 && (up->alarm & (3 << SYNERR)) == 0) {
                up->status |= INSYNC;
                up->watch = 0;
                pp->disp = 0;
+               pp->lastref = up->timestamp;
        }
        up->rsec = nsec;
        if (up->status & INSYNC) {
@@ -2047,10 +2051,7 @@ wwv_rsec(
                    1].digit * 10 + up->decvec[DA + 2].digit * 100;
                pp->year = up->decvec[YR].digit + up->decvec[YR +
                    1].digit * 10;
-               if (pp->year < UTCYEAR)
-                       pp->year += 2000;
-               else
-                       pp->year += 1900;
+               pp->year += 2000;
                L_CLR(&offset);
                if (!clocktime(pp->day, pp->hour, pp->minute,
                    pp->second, GMT, up->timestamp.l_ui,
index 0ca9f75ab7b13548708a006cf8e0ade38120123f..c5ef9f9bc85e09d52399d94f081dc01bf391d747 100644 (file)
 #define        DESCRIPTION     "Spectracom WWVB/GPS Receivers" /* WRU */
 
 #define        LENWWVB0        22      /* format 0 timecode length */
+#define LENWWVB1       22      /* format 1 timecode length */
 #define        LENWWVB2        24      /* format 2 timecode length */
 #define LENWWVB3        29      /* format 3 timecode length */
 #define MONLIN         15      /* number of monitoring lines */
@@ -187,7 +188,7 @@ wwvb_start(
        peer->precision = PRECISION;
        pp->clockdesc = DESCRIPTION;
        memcpy((char *)&pp->refid, REFID, 4);
-       peer->burst = NSTAGE;
+       peer->burst = MAXSTAGE;
        return (1);
 }
 
@@ -263,11 +264,6 @@ wwvb_receive(
        pp->lastrec = up->laststamp;
        up->laststamp = trtmp;
        up->tcswitch = 1;
-#ifdef DEBUG
-       if (debug)
-               printf("wwvb: timecode %d %s\n", pp->lencode,
-                   pp->a_lastcode);
-#endif
 
        /*
         * We get down to business, check the timecode format and decode
@@ -277,10 +273,9 @@ wwvb_receive(
         */
        syncchar = qualchar = leapchar = dstchar = ' ';
        tz = 0;
-       pp->msec = 0;
        switch (pp->lencode) {
 
-               case LENWWVB0:
+       case LENWWVB0:
 
                /*
                 * Timecode format 0: "I  ddd hh:mm:ss DTZ=nn"
@@ -289,20 +284,22 @@ wwvb_receive(
                    "%c %3d %2d:%2d:%2d%c%cTZ=%2d",
                    &syncchar, &pp->day, &pp->hour, &pp->minute,
                    &pp->second, &tmpchar, &dstchar, &tz) == 8)
+                       pp->nsec = 0;
                        break;
 
-               case LENWWVB2:
+       case LENWWVB2:
 
                /*
                 * Timecode format 2: "IQyy ddd hh:mm:ss.mmm LD" */
                if (sscanf(pp->a_lastcode,
-                   "%c%c %2d %3d %2d:%2d:%2d.%3d %c",
+                   "%c%c %2d %3d %2d:%2d:%2d.%3ld %c",
                    &syncchar, &qualchar, &pp->year, &pp->day,
-                   &pp->hour, &pp->minute, &pp->second, &pp->msec,
+                   &pp->hour, &pp->minute, &pp->second, &pp->nsec,
                    &leapchar) == 9)
+                       pp->nsec *= 1000000;
                        break;
 
-               case LENWWVB3:
+       case LENWWVB3:
 
                /*
                 * Timecode format 3: "0003I yyyymmdd hhmmss+0000SL#"
@@ -313,10 +310,11 @@ wwvb_receive(
                    &pp->minute, &pp->second, &dstchar, &leapchar) == 8)
                    {
                        pp->day = ymd2yd(pp->year, month, day);
+                       pp->nsec = 0;
                        break;
                }
 
-               default:
+       default:
 
                /*
                 * Unknown format: If dumping internal table, record
@@ -343,6 +341,7 @@ wwvb_receive(
 
            case ' ':
                pp->disp = .001;
+               pp->lastref = pp->lastrec;
                break;
 
            case 'A':
@@ -411,17 +410,21 @@ wwvb_poll(
                pollchar = 'T';
        if (write(pp->io.fd, &pollchar, 1) != 1)
                refclock_report(peer, CEVNT_FAULT);
-       else
-               pp->polls++;
        if (peer->burst > 0)
                return;
        if (pp->coderecv == pp->codeproc) {
                refclock_report(peer, CEVNT_TIMEOUT);
                return;
        }
-       record_clock_stats(&peer->srcadr, pp->a_lastcode);
        refclock_receive(peer);
-       peer->burst = NSTAGE;
+       record_clock_stats(&peer->srcadr, pp->a_lastcode);
+#ifdef DEBUG
+       if (debug)
+               printf("wwvb: timecode %d %s\n", pp->lencode,
+                   pp->a_lastcode);
+#endif
+       peer->burst = MAXSTAGE;
+       pp->polls++;
 
        /*
         * If the monitor flag is set (flag4), we dump the internal