1 /* 2 * ntp_refclock - processing support for reference clocks 3 */ 4 #ifdef HAVE_CONFIG_H 5 # include <config.h> 6 #endif 7 8 #include "ntpd.h" 9 #include "ntp_io.h" 10 #include "ntp_unixtime.h" 11 #include "ntp_tty.h" 12 #include "ntp_refclock.h" 13 #include "ntp_stdlib.h" 14 #include "ntp_assert.h" 15 16 #include <stdio.h> 17 18 #ifdef HAVE_SYS_IOCTL_H 19 # include <sys/ioctl.h> 20 #endif /* HAVE_SYS_IOCTL_H */ 21 22 #ifdef REFCLOCK 23 24 #ifdef KERNEL_PLL 25 #include "ntp_syscall.h" 26 #endif /* KERNEL_PLL */ 27 28 #ifdef HAVE_PPSAPI 29 #include "ppsapi_timepps.h" 30 #include "refclock_atom.h" 31 #endif /* HAVE_PPSAPI */ 32 33 /* 34 * Reference clock support is provided here by maintaining the fiction 35 * that the clock is actually a peer. As no packets are exchanged with 36 * a reference clock, however, we replace the transmit, receive and 37 * packet procedures with separate code to simulate them. Routines 38 * refclock_transmit() and refclock_receive() maintain the peer 39 * variables in a state analogous to an actual peer and pass reference 40 * clock data on through the filters. Routines refclock_peer() and 41 * refclock_unpeer() are called to initialize and terminate reference 42 * clock associations. A set of utility routines is included to open 43 * serial devices, process sample data, and to perform various debugging 44 * functions. 45 * 46 * The main interface used by these routines is the refclockproc 47 * structure, which contains for most drivers the decimal equivalants 48 * of the year, day, month, hour, second and millisecond/microsecond 49 * decoded from the ASCII timecode. Additional information includes 50 * the receive timestamp, exception report, statistics tallies, etc. 51 * In addition, there may be a driver-specific unit structure used for 52 * local control of the device. 53 * 54 * The support routines are passed a pointer to the peer structure, 55 * which is used for all peer-specific processing and contains a 56 * pointer to the refclockproc structure, which in turn contains a 57 * pointer to the unit structure, if used. The peer structure is 58 * identified by an interface address in the dotted quad form 59 * 127.127.t.u, where t is the clock type and u the unit. 60 */ 61 #define FUDGEFAC .1 /* fudge correction factor */ 62 #define LF 0x0a /* ASCII LF */ 63 64 int cal_enable; /* enable refclock calibrate */ 65 66 /* 67 * Forward declarations 68 */ 69 static int refclock_cmpl_fp (const void *, const void *); 70 static int refclock_sample (struct refclockproc *); 71 static int refclock_ioctl(int, u_int); 72 73 74 /* 75 * refclock_report - note the occurance of an event 76 * 77 * This routine presently just remembers the report and logs it, but 78 * does nothing heroic for the trap handler. It tries to be a good 79 * citizen and bothers the system log only if things change. 80 */ 81 void 82 refclock_report( 83 struct peer *peer, 84 int code 85 ) 86 { 87 struct refclockproc *pp; 88 89 pp = peer->procptr; 90 if (pp == NULL) 91 return; 92 93 switch (code) { 94 95 case CEVNT_TIMEOUT: 96 pp->noreply++; 97 break; 98 99 case CEVNT_BADREPLY: 100 pp->badformat++; 101 break; 102 103 case CEVNT_FAULT: 104 break; 105 106 case CEVNT_BADDATE: 107 case CEVNT_BADTIME: 108 pp->baddata++; 109 break; 110 111 default: 112 /* ignore others */ 113 break; 114 } 115 if (pp->lastevent < 15) 116 pp->lastevent++; 117 if (pp->currentstatus != code) { 118 pp->currentstatus = (u_char)code; 119 report_event(PEVNT_CLOCK, peer, ceventstr(code)); 120 } 121 } 122 123 124 /* 125 * init_refclock - initialize the reference clock drivers 126 * 127 * This routine calls each of the drivers in turn to initialize internal 128 * variables, if necessary. Most drivers have nothing to say at this 129 * point. 130 */ 131 void 132 init_refclock(void) 133 { 134 int i; 135 136 for (i = 0; i < (int)num_refclock_conf; i++) 137 if (refclock_conf[i]->clock_init != noentry) 138 (refclock_conf[i]->clock_init)(); 139 } 140 141 142 /* 143 * refclock_newpeer - initialize and start a reference clock 144 * 145 * This routine allocates and initializes the interface structure which 146 * supports a reference clock in the form of an ordinary NTP peer. A 147 * driver-specific support routine completes the initialization, if 148 * used. Default peer variables which identify the clock and establish 149 * its reference ID and stratum are set here. It returns one if success 150 * and zero if the clock address is invalid or already running, 151 * insufficient resources are available or the driver declares a bum 152 * rap. 153 */ 154 int 155 refclock_newpeer( 156 struct peer *peer /* peer structure pointer */ 157 ) 158 { 159 struct refclockproc *pp; 160 u_char clktype; 161 int unit; 162 163 /* 164 * Check for valid clock address. If already running, shut it 165 * down first. 166 */ 167 if (!ISREFCLOCKADR(&peer->srcadr)) { 168 msyslog(LOG_ERR, 169 "refclock_newpeer: clock address %s invalid", 170 stoa(&peer->srcadr)); 171 return (0); 172 } 173 clktype = (u_char)REFCLOCKTYPE(&peer->srcadr); 174 unit = REFCLOCKUNIT(&peer->srcadr); 175 if (clktype >= num_refclock_conf || 176 refclock_conf[clktype]->clock_start == noentry) { 177 msyslog(LOG_ERR, 178 "refclock_newpeer: clock type %d invalid\n", 179 clktype); 180 return (0); 181 } 182 183 /* 184 * Allocate and initialize interface structure 185 */ 186 pp = emalloc_zero(sizeof(*pp)); 187 peer->procptr = pp; 188 189 /* 190 * Initialize structures 191 */ 192 peer->refclktype = clktype; 193 peer->refclkunit = (u_char)unit; 194 peer->flags |= FLAG_REFCLOCK; 195 peer->leap = LEAP_NOTINSYNC; 196 peer->stratum = STRATUM_REFCLOCK; 197 peer->ppoll = peer->maxpoll; 198 pp->type = clktype; 199 pp->conf = refclock_conf[clktype]; 200 pp->timestarted = current_time; 201 pp->io.fd = -1; 202 203 /* 204 * Set peer.pmode based on the hmode. For appearances only. 205 */ 206 switch (peer->hmode) { 207 case MODE_ACTIVE: 208 peer->pmode = MODE_PASSIVE; 209 break; 210 211 default: 212 peer->pmode = MODE_SERVER; 213 break; 214 } 215 216 /* 217 * Do driver dependent initialization. The above defaults 218 * can be wiggled, then finish up for consistency. 219 */ 220 if (!((refclock_conf[clktype]->clock_start)(unit, peer))) { 221 refclock_unpeer(peer); 222 return (0); 223 } 224 peer->refid = pp->refid; 225 return (1); 226 } 227 228 229 /* 230 * refclock_unpeer - shut down a clock 231 */ 232 void 233 refclock_unpeer( 234 struct peer *peer /* peer structure pointer */ 235 ) 236 { 237 u_char clktype; 238 int unit; 239 240 /* 241 * Wiggle the driver to release its resources, then give back 242 * the interface structure. 243 */ 244 if (NULL == peer->procptr) 245 return; 246 247 clktype = peer->refclktype; 248 unit = peer->refclkunit; 249 if (refclock_conf[clktype]->clock_shutdown != noentry) 250 (refclock_conf[clktype]->clock_shutdown)(unit, peer); 251 free(peer->procptr); 252 peer->procptr = NULL; 253 } 254 255 256 /* 257 * refclock_timer - called once per second for housekeeping. 258 */ 259 void 260 refclock_timer( 261 struct peer *p 262 ) 263 { 264 struct refclockproc * pp; 265 int unit; 266 267 unit = p->refclkunit; 268 pp = p->procptr; 269 if (pp->conf->clock_timer != noentry) 270 (*pp->conf->clock_timer)(unit, p); 271 if (pp->action != NULL && pp->nextaction <= current_time) 272 (*pp->action)(p); 273 } 274 275 276 /* 277 * refclock_transmit - simulate the transmit procedure 278 * 279 * This routine implements the NTP transmit procedure for a reference 280 * clock. This provides a mechanism to call the driver at the NTP poll 281 * interval, as well as provides a reachability mechanism to detect a 282 * broken radio or other madness. 283 */ 284 void 285 refclock_transmit( 286 struct peer *peer /* peer structure pointer */ 287 ) 288 { 289 u_char clktype; 290 int unit; 291 292 clktype = peer->refclktype; 293 unit = peer->refclkunit; 294 peer->sent++; 295 get_systime(&peer->xmt); 296 297 /* 298 * This is a ripoff of the peer transmit routine, but 299 * specialized for reference clocks. We do a little less 300 * protocol here and call the driver-specific transmit routine. 301 */ 302 if (peer->burst == 0) { 303 u_char oreach; 304 #ifdef DEBUG 305 if (debug) 306 printf("refclock_transmit: at %ld %s\n", 307 current_time, stoa(&(peer->srcadr))); 308 #endif 309 310 /* 311 * Update reachability and poll variables like the 312 * network code. 313 */ 314 oreach = peer->reach & 0xfe; 315 peer->reach <<= 1; 316 if (!(peer->reach & 0x0f)) 317 clock_filter(peer, 0., 0., MAXDISPERSE); 318 peer->outdate = current_time; 319 if (!peer->reach) { 320 if (oreach) { 321 report_event(PEVNT_UNREACH, peer, NULL); 322 peer->timereachable = current_time; 323 } 324 } else { 325 if (peer->flags & FLAG_BURST) 326 peer->burst = NSTAGE; 327 } 328 } else { 329 peer->burst--; 330 } 331 if (refclock_conf[clktype]->clock_poll != noentry) 332 (refclock_conf[clktype]->clock_poll)(unit, peer); 333 poll_update(peer, peer->hpoll); 334 } 335 336 337 /* 338 * Compare two doubles - used with qsort() 339 */ 340 static int 341 refclock_cmpl_fp( 342 const void *p1, 343 const void *p2 344 ) 345 { 346 const double *dp1 = (const double *)p1; 347 const double *dp2 = (const double *)p2; 348 349 if (*dp1 < *dp2) 350 return -1; 351 if (*dp1 > *dp2) 352 return 1; 353 return 0; 354 } 355 356 357 /* 358 * refclock_process_offset - update median filter 359 * 360 * This routine uses the given offset and timestamps to construct a new 361 * entry in the median filter circular buffer. Samples that overflow the 362 * filter are quietly discarded. 363 */ 364 void 365 refclock_process_offset( 366 struct refclockproc *pp, /* refclock structure pointer */ 367 l_fp lasttim, /* last timecode timestamp */ 368 l_fp lastrec, /* last receive timestamp */ 369 double fudge 370 ) 371 { 372 l_fp lftemp; 373 double doffset; 374 375 pp->lastrec = lastrec; 376 lftemp = lasttim; 377 L_SUB(&lftemp, &lastrec); 378 LFPTOD(&lftemp, doffset); 379 SAMPLE(doffset + fudge); 380 } 381 382 383 /* 384 * refclock_process - process a sample from the clock 385 * refclock_process_f - refclock_process with other than time1 fudge 386 * 387 * This routine converts the timecode in the form days, hours, minutes, 388 * seconds and milliseconds/microseconds to internal timestamp format, 389 * then constructs a new entry in the median filter circular buffer. 390 * Return success (1) if the data are correct and consistent with the 391 * converntional calendar. 392 * 393 * Important for PPS users: Normally, the pp->lastrec is set to the 394 * system time when the on-time character is received and the pp->year, 395 * ..., pp->second decoded and the seconds fraction pp->nsec in 396 * nanoseconds). When a PPS offset is available, pp->nsec is forced to 397 * zero and the fraction for pp->lastrec is set to the PPS offset. 398 */ 399 int 400 refclock_process_f( 401 struct refclockproc *pp, /* refclock structure pointer */ 402 double fudge 403 ) 404 { 405 l_fp offset, ltemp; 406 407 /* 408 * Compute the timecode timestamp from the days, hours, minutes, 409 * seconds and milliseconds/microseconds of the timecode. Use 410 * clocktime() for the aggregate seconds and the msec/usec for 411 * the fraction, when present. Note that this code relies on the 412 * filesystem time for the years and does not use the years of 413 * the timecode. 414 */ 415 if (!clocktime(pp->day, pp->hour, pp->minute, pp->second, GMT, 416 pp->lastrec.l_ui, &pp->yearstart, &offset.l_ui)) 417 return (0); 418 419 offset.l_uf = 0; 420 DTOLFP(pp->nsec / 1e9, <emp); 421 L_ADD(&offset, <emp); 422 refclock_process_offset(pp, offset, pp->lastrec, fudge); 423 return (1); 424 } 425 426 427 int 428 refclock_process( 429 struct refclockproc *pp /* refclock structure pointer */ 430 ) 431 { 432 return refclock_process_f(pp, pp->fudgetime1); 433 } 434 435 436 /* 437 * refclock_sample - process a pile of samples from the clock 438 * 439 * This routine implements a recursive median filter to suppress spikes 440 * in the data, as well as determine a performance statistic. It 441 * calculates the mean offset and RMS jitter. A time adjustment 442 * fudgetime1 can be added to the final offset to compensate for various 443 * systematic errors. The routine returns the number of samples 444 * processed, which could be zero. 445 */ 446 static int 447 refclock_sample( 448 struct refclockproc *pp /* refclock structure pointer */ 449 ) 450 { 451 size_t i, j, k, m, n; 452 double off[MAXSTAGE]; 453 double offset; 454 455 /* 456 * Copy the raw offsets and sort into ascending order. Don't do 457 * anything if the buffer is empty. 458 */ 459 n = 0; 460 while (pp->codeproc != pp->coderecv) { 461 pp->codeproc = (pp->codeproc + 1) % MAXSTAGE; 462 off[n] = pp->filter[pp->codeproc]; 463 n++; 464 } 465 if (n == 0) 466 return (0); 467 468 if (n > 1) 469 qsort(off, n, sizeof(off[0]), refclock_cmpl_fp); 470 471 /* 472 * Reject the furthest from the median of the samples until 473 * approximately 60 percent of the samples remain. 474 */ 475 i = 0; j = n; 476 m = n - (n * 4) / 10; 477 while ((j - i) > m) { 478 offset = off[(j + i) / 2]; 479 if (off[j - 1] - offset < offset - off[i]) 480 i++; /* reject low end */ 481 else 482 j--; /* reject high end */ 483 } 484 485 /* 486 * Determine the offset and jitter. 487 */ 488 pp->offset = 0; 489 pp->jitter = 0; 490 for (k = i; k < j; k++) { 491 pp->offset += off[k]; 492 if (k > i) 493 pp->jitter += SQUARE(off[k] - off[k - 1]); 494 } 495 pp->offset /= m; 496 pp->jitter = max(SQRT(pp->jitter / m), LOGTOD(sys_precision)); 497 #ifdef DEBUG 498 if (debug) 499 printf( 500 "refclock_sample: n %d offset %.6f disp %.6f jitter %.6f\n", 501 (int)n, pp->offset, pp->disp, pp->jitter); 502 #endif 503 return (int)n; 504 } 505 506 507 /* 508 * refclock_receive - simulate the receive and packet procedures 509 * 510 * This routine simulates the NTP receive and packet procedures for a 511 * reference clock. This provides a mechanism in which the ordinary NTP 512 * filter, selection and combining algorithms can be used to suppress 513 * misbehaving radios and to mitigate between them when more than one is 514 * available for backup. 515 */ 516 void 517 refclock_receive( 518 struct peer *peer /* peer structure pointer */ 519 ) 520 { 521 struct refclockproc *pp; 522 523 #ifdef DEBUG 524 if (debug) 525 printf("refclock_receive: at %lu %s\n", 526 current_time, stoa(&peer->srcadr)); 527 #endif 528 529 /* 530 * Do a little sanity dance and update the peer structure. Groom 531 * the median filter samples and give the data to the clock 532 * filter. 533 */ 534 pp = peer->procptr; 535 peer->leap = pp->leap; 536 if (peer->leap == LEAP_NOTINSYNC) 537 return; 538 539 peer->received++; 540 peer->timereceived = current_time; 541 if (!peer->reach) { 542 report_event(PEVNT_REACH, peer, NULL); 543 peer->timereachable = current_time; 544 } 545 peer->reach |= 1; 546 peer->reftime = pp->lastref; 547 peer->aorg = pp->lastrec; 548 peer->rootdisp = pp->disp; 549 get_systime(&peer->dst); 550 if (!refclock_sample(pp)) 551 return; 552 553 clock_filter(peer, pp->offset, 0., pp->jitter); 554 if (cal_enable && fabs(last_offset) < sys_mindisp && sys_peer != 555 NULL) { 556 if (sys_peer->refclktype == REFCLK_ATOM_PPS && 557 peer->refclktype != REFCLK_ATOM_PPS) 558 pp->fudgetime1 -= pp->offset * FUDGEFAC; 559 } 560 } 561 562 563 /* 564 * refclock_gtlin - groom next input line and extract timestamp 565 * 566 * This routine processes the timecode received from the clock and 567 * strips the parity bit and control characters. It returns the number 568 * of characters in the line followed by a NULL character ('\0'), which 569 * is not included in the count. In case of an empty line, the previous 570 * line is preserved. 571 */ 572 int 573 refclock_gtlin( 574 struct recvbuf *rbufp, /* receive buffer pointer */ 575 char *lineptr, /* current line pointer */ 576 int bmax, /* remaining characters in line */ 577 l_fp *tsptr /* pointer to timestamp returned */ 578 ) 579 { 580 const char *sp, *spend; 581 char *dp, *dpend; 582 int dlen; 583 584 if (bmax <= 0) 585 return (0); 586 587 dp = lineptr; 588 dpend = dp + bmax - 1; /* leave room for NUL pad */ 589 sp = (const char *)rbufp->recv_buffer; 590 spend = sp + rbufp->recv_length; 591 592 while (sp != spend && dp != dpend) { 593 char c; 594 595 c = *sp++ & 0x7f; 596 if (c >= 0x20 && c < 0x7f) 597 *dp++ = c; 598 } 599 /* Get length of data written to the destination buffer. If 600 * zero, do *not* place a NUL byte to preserve the previous 601 * buffer content. 602 */ 603 dlen = dp - lineptr; 604 if (dlen) 605 *dp = '\0'; 606 *tsptr = rbufp->recv_time; 607 DPRINTF(2, ("refclock_gtlin: fd %d time %s timecode %d %s\n", 608 rbufp->fd, ulfptoa(&rbufp->recv_time, 6), dlen, 609 (dlen != 0) 610 ? lineptr 611 : "")); 612 return (dlen); 613 } 614 615 616 /* 617 * refclock_gtraw - get next line/chunk of data 618 * 619 * This routine returns the raw data received from the clock in both 620 * canonical or raw modes. The terminal interface routines map CR to LF. 621 * In canonical mode this results in two lines, one containing data 622 * followed by LF and another containing only LF. In raw mode the 623 * interface routines can deliver arbitraty chunks of data from one 624 * character to a maximum specified by the calling routine. In either 625 * mode the routine returns the number of characters in the line 626 * followed by a NULL character ('\0'), which is not included in the 627 * count. 628 * 629 * *tsptr receives a copy of the buffer timestamp. 630 */ 631 int 632 refclock_gtraw( 633 struct recvbuf *rbufp, /* receive buffer pointer */ 634 char *lineptr, /* current line pointer */ 635 int bmax, /* remaining characters in line */ 636 l_fp *tsptr /* pointer to timestamp returned */ 637 ) 638 { 639 if (bmax <= 0) 640 return (0); 641 bmax -= 1; /* leave room for trailing NUL */ 642 if (bmax > rbufp->recv_length) 643 bmax = rbufp->recv_length; 644 memcpy(lineptr, rbufp->recv_buffer, bmax); 645 lineptr[bmax] = '\0'; 646 647 *tsptr = rbufp->recv_time; 648 DPRINTF(2, ("refclock_gtraw: fd %d time %s timecode %d %s\n", 649 rbufp->fd, ulfptoa(&rbufp->recv_time, 6), bmax, 650 lineptr)); 651 return (bmax); 652 } 653 654 655 /* 656 * indicate_refclock_packet() 657 * 658 * Passes a fragment of refclock input read from the device to the 659 * driver direct input routine, which may consume it (batch it for 660 * queuing once a logical unit is assembled). If it is not so 661 * consumed, queue it for the driver's receive entrypoint. 662 * 663 * The return value is TRUE if the data has been consumed as a fragment 664 * and should not be counted as a received packet. 665 */ 666 int 667 indicate_refclock_packet( 668 struct refclockio * rio, 669 struct recvbuf * rb 670 ) 671 { 672 /* Does this refclock use direct input routine? */ 673 if (rio->io_input != NULL && (*rio->io_input)(rb) == 0) { 674 /* 675 * data was consumed - nothing to pass up 676 * into block input machine 677 */ 678 freerecvbuf(rb); 679 680 return TRUE; 681 } 682 add_full_recv_buffer(rb); 683 684 return FALSE; 685 } 686 687 688 /* 689 * process_refclock_packet() 690 * 691 * Used for deferred processing of 'io_input' on systems where threading 692 * is used (notably Windows). This is acting as a trampoline to make the 693 * real calls to the refclock functions. 694 */ 695 #ifdef HAVE_IO_COMPLETION_PORT 696 void 697 process_refclock_packet( 698 struct recvbuf * rb 699 ) 700 { 701 struct refclockio * rio; 702 703 /* get the refclockio structure from the receive buffer */ 704 rio = &rb->recv_peer->procptr->io; 705 706 /* call 'clock_recv' if either there is no input function or the 707 * raw input function tells us to feed the packet to the 708 * receiver. 709 */ 710 if (rio->io_input == NULL || (*rio->io_input)(rb) != 0) { 711 rio->recvcount++; 712 packets_received++; 713 handler_pkts++; 714 (*rio->clock_recv)(rb); 715 } 716 } 717 #endif /* HAVE_IO_COMPLETION_PORT */ 718 719 720 /* 721 * The following code does not apply to WINNT & VMS ... 722 */ 723 #if !defined(SYS_VXWORKS) && !defined(SYS_WINNT) 724 #if defined(HAVE_TERMIOS) || defined(HAVE_SYSV_TTYS) || defined(HAVE_BSD_TTYS) 725 726 /* 727 * refclock_open - open serial port for reference clock 728 * 729 * This routine opens a serial port for I/O and sets default options. It 730 * returns the file descriptor if successful, or logs an error and 731 * returns -1. 732 */ 733 int 734 refclock_open( 735 char *dev, /* device name pointer */ 736 u_int speed, /* serial port speed (code) */ 737 u_int lflags /* line discipline flags */ 738 ) 739 { 740 int fd; 741 int omode; 742 #ifdef O_NONBLOCK 743 char trash[128]; /* litter bin for old input data */ 744 #endif 745 746 /* 747 * Open serial port and set default options 748 */ 749 omode = O_RDWR; 750 #ifdef O_NONBLOCK 751 omode |= O_NONBLOCK; 752 #endif 753 #ifdef O_NOCTTY 754 omode |= O_NOCTTY; 755 #endif 756 757 fd = open(dev, omode, 0777); 758 /* refclock_open() long returned 0 on failure, avoid it. */ 759 if (0 == fd) { 760 fd = dup(0); 761 SAVE_ERRNO( 762 close(0); 763 ) 764 } 765 if (fd < 0) { 766 SAVE_ERRNO( 767 msyslog(LOG_ERR, "refclock_open %s: %m", dev); 768 ) 769 return -1; 770 } 771 if (!refclock_setup(fd, speed, lflags)) { 772 close(fd); 773 return -1; 774 } 775 if (!refclock_ioctl(fd, lflags)) { 776 close(fd); 777 return -1; 778 } 779 #ifdef O_NONBLOCK 780 /* 781 * We want to make sure there is no pending trash in the input 782 * buffer. Since we have non-blocking IO available, this is a 783 * good moment to read and dump all available outdated stuff 784 * that might have become toxic for the driver. 785 */ 786 while (read(fd, trash, sizeof(trash)) > 0 || errno == EINTR) 787 /*NOP*/; 788 #endif 789 return fd; 790 } 791 792 793 /* 794 * refclock_setup - initialize terminal interface structure 795 */ 796 int 797 refclock_setup( 798 int fd, /* file descriptor */ 799 u_int speed, /* serial port speed (code) */ 800 u_int lflags /* line discipline flags */ 801 ) 802 { 803 int i; 804 TTY ttyb, *ttyp; 805 806 /* 807 * By default, the serial line port is initialized in canonical 808 * (line-oriented) mode at specified line speed, 8 bits and no 809 * parity. LF ends the line and CR is mapped to LF. The break, 810 * erase and kill functions are disabled. There is a different 811 * section for each terminal interface, as selected at compile 812 * time. The flag bits can be used to set raw mode and echo. 813 */ 814 ttyp = &ttyb; 815 #ifdef HAVE_TERMIOS 816 817 /* 818 * POSIX serial line parameters (termios interface) 819 */ 820 if (tcgetattr(fd, ttyp) < 0) { 821 SAVE_ERRNO( 822 msyslog(LOG_ERR, 823 "refclock_setup fd %d tcgetattr: %m", 824 fd); 825 ) 826 return FALSE; 827 } 828 829 /* 830 * Set canonical mode and local connection; set specified speed, 831 * 8 bits and no parity; map CR to NL; ignore break. 832 */ 833 if (speed) { 834 u_int ltemp = 0; 835 836 ttyp->c_iflag = IGNBRK | IGNPAR | ICRNL; 837 ttyp->c_oflag = 0; 838 ttyp->c_cflag = CS8 | CLOCAL | CREAD; 839 if (lflags & LDISC_7O1) { 840 /* HP Z3801A needs 7-bit, odd parity */ 841 ttyp->c_cflag = CS7 | PARENB | PARODD | CLOCAL | CREAD; 842 } 843 cfsetispeed(&ttyb, speed); 844 cfsetospeed(&ttyb, speed); 845 for (i = 0; i < NCCS; ++i) 846 ttyp->c_cc[i] = '\0'; 847 848 #if defined(TIOCMGET) && !defined(SCO5_CLOCK) 849 850 /* 851 * If we have modem control, check to see if modem leads 852 * are active; if so, set remote connection. This is 853 * necessary for the kernel pps mods to work. 854 */ 855 if (ioctl(fd, TIOCMGET, (char *)<emp) < 0) 856 msyslog(LOG_ERR, 857 "refclock_setup fd %d TIOCMGET: %m", fd); 858 #ifdef DEBUG 859 if (debug) 860 printf("refclock_setup fd %d modem status: 0x%x\n", 861 fd, ltemp); 862 #endif 863 if (ltemp & TIOCM_DSR && lflags & LDISC_REMOTE) 864 ttyp->c_cflag &= ~CLOCAL; 865 #endif /* TIOCMGET */ 866 } 867 868 /* 869 * Set raw and echo modes. These can be changed on-fly. 870 */ 871 ttyp->c_lflag = ICANON; 872 if (lflags & LDISC_RAW) { 873 ttyp->c_lflag = 0; 874 ttyp->c_iflag = 0; 875 ttyp->c_cc[VMIN] = 1; 876 } 877 if (lflags & LDISC_ECHO) 878 ttyp->c_lflag |= ECHO; 879 if (tcsetattr(fd, TCSANOW, ttyp) < 0) { 880 SAVE_ERRNO( 881 msyslog(LOG_ERR, 882 "refclock_setup fd %d TCSANOW: %m", 883 fd); 884 ) 885 return FALSE; 886 } 887 888 /* 889 * flush input and output buffers to discard any outdated stuff 890 * that might have become toxic for the driver. Failing to do so 891 * is logged, but we keep our fingers crossed otherwise. 892 */ 893 if (tcflush(fd, TCIOFLUSH) < 0) 894 msyslog(LOG_ERR, "refclock_setup fd %d tcflush(): %m", 895 fd); 896 #endif /* HAVE_TERMIOS */ 897 898 #ifdef HAVE_SYSV_TTYS 899 900 /* 901 * System V serial line parameters (termio interface) 902 * 903 */ 904 if (ioctl(fd, TCGETA, ttyp) < 0) { 905 SAVE_ERRNO( 906 msyslog(LOG_ERR, 907 "refclock_setup fd %d TCGETA: %m", 908 fd); 909 ) 910 return FALSE; 911 } 912 913 /* 914 * Set canonical mode and local connection; set specified speed, 915 * 8 bits and no parity; map CR to NL; ignore break. 916 */ 917 if (speed) { 918 u_int ltemp = 0; 919 920 ttyp->c_iflag = IGNBRK | IGNPAR | ICRNL; 921 ttyp->c_oflag = 0; 922 ttyp->c_cflag = speed | CS8 | CLOCAL | CREAD; 923 for (i = 0; i < NCCS; ++i) 924 ttyp->c_cc[i] = '\0'; 925 926 #if defined(TIOCMGET) && !defined(SCO5_CLOCK) 927 928 /* 929 * If we have modem control, check to see if modem leads 930 * are active; if so, set remote connection. This is 931 * necessary for the kernel pps mods to work. 932 */ 933 if (ioctl(fd, TIOCMGET, (char *)<emp) < 0) 934 msyslog(LOG_ERR, 935 "refclock_setup fd %d TIOCMGET: %m", fd); 936 #ifdef DEBUG 937 if (debug) 938 printf("refclock_setup fd %d modem status: %x\n", 939 fd, ltemp); 940 #endif 941 if (ltemp & TIOCM_DSR) 942 ttyp->c_cflag &= ~CLOCAL; 943 #endif /* TIOCMGET */ 944 } 945 946 /* 947 * Set raw and echo modes. These can be changed on-fly. 948 */ 949 ttyp->c_lflag = ICANON; 950 if (lflags & LDISC_RAW) { 951 ttyp->c_lflag = 0; 952 ttyp->c_iflag = 0; 953 ttyp->c_cc[VMIN] = 1; 954 } 955 if (ioctl(fd, TCSETA, ttyp) < 0) { 956 SAVE_ERRNO( 957 msyslog(LOG_ERR, 958 "refclock_setup fd %d TCSETA: %m", fd); 959 ) 960 return FALSE; 961 } 962 #endif /* HAVE_SYSV_TTYS */ 963 964 #ifdef HAVE_BSD_TTYS 965 966 /* 967 * 4.3bsd serial line parameters (sgttyb interface) 968 */ 969 if (ioctl(fd, TIOCGETP, (char *)ttyp) < 0) { 970 SAVE_ERRNO( 971 msyslog(LOG_ERR, 972 "refclock_setup fd %d TIOCGETP: %m", 973 fd); 974 ) 975 return FALSE; 976 } 977 if (speed) 978 ttyp->sg_ispeed = ttyp->sg_ospeed = speed; 979 ttyp->sg_flags = EVENP | ODDP | CRMOD; 980 if (ioctl(fd, TIOCSETP, (char *)ttyp) < 0) { 981 SAVE_ERRNO( 982 msyslog(LOG_ERR, "refclock_setup TIOCSETP: %m"); 983 ) 984 return FALSE; 985 } 986 #endif /* HAVE_BSD_TTYS */ 987 return(1); 988 } 989 #endif /* HAVE_TERMIOS || HAVE_SYSV_TTYS || HAVE_BSD_TTYS */ 990 991 992 /* 993 * refclock_ioctl - set serial port control functions 994 * 995 * This routine attempts to hide the internal, system-specific details 996 * of serial ports. It can handle POSIX (termios), SYSV (termio) and BSD 997 * (sgtty) interfaces with varying degrees of success. The routine sets 998 * up optional features such as tty_clk. The routine returns TRUE if 999 * successful. 1000 */ 1001 int 1002 refclock_ioctl( 1003 int fd, /* file descriptor */ 1004 u_int lflags /* line discipline flags */ 1005 ) 1006 { 1007 /* 1008 * simply return TRUE if no UNIX line discipline is supported 1009 */ 1010 DPRINTF(1, ("refclock_ioctl: fd %d flags 0x%x\n", fd, lflags)); 1011 1012 return TRUE; 1013 } 1014 #endif /* !defined(SYS_VXWORKS) && !defined(SYS_WINNT) */ 1015 1016 1017 /* 1018 * refclock_control - set and/or return clock values 1019 * 1020 * This routine is used mainly for debugging. It returns designated 1021 * values from the interface structure that can be displayed using 1022 * ntpdc and the clockstat command. It can also be used to initialize 1023 * configuration variables, such as fudgetimes, fudgevalues, reference 1024 * ID and stratum. 1025 */ 1026 void 1027 refclock_control( 1028 sockaddr_u *srcadr, 1029 const struct refclockstat *in, 1030 struct refclockstat *out 1031 ) 1032 { 1033 struct peer *peer; 1034 struct refclockproc *pp; 1035 u_char clktype; 1036 int unit; 1037 1038 /* 1039 * Check for valid address and running peer 1040 */ 1041 if (!ISREFCLOCKADR(srcadr)) 1042 return; 1043 1044 clktype = (u_char)REFCLOCKTYPE(srcadr); 1045 unit = REFCLOCKUNIT(srcadr); 1046 1047 peer = findexistingpeer(srcadr, NULL, NULL, -1, 0); 1048 1049 if (NULL == peer) 1050 return; 1051 1052 INSIST(peer->procptr != NULL); 1053 pp = peer->procptr; 1054 1055 /* 1056 * Initialize requested data 1057 */ 1058 if (in != NULL) { 1059 if (in->haveflags & CLK_HAVETIME1) 1060 pp->fudgetime1 = in->fudgetime1; 1061 if (in->haveflags & CLK_HAVETIME2) 1062 pp->fudgetime2 = in->fudgetime2; 1063 if (in->haveflags & CLK_HAVEVAL1) 1064 peer->stratum = pp->stratum = (u_char)in->fudgeval1; 1065 if (in->haveflags & CLK_HAVEVAL2) 1066 peer->refid = pp->refid = in->fudgeval2; 1067 if (in->haveflags & CLK_HAVEFLAG1) { 1068 pp->sloppyclockflag &= ~CLK_FLAG1; 1069 pp->sloppyclockflag |= in->flags & CLK_FLAG1; 1070 } 1071 if (in->haveflags & CLK_HAVEFLAG2) { 1072 pp->sloppyclockflag &= ~CLK_FLAG2; 1073 pp->sloppyclockflag |= in->flags & CLK_FLAG2; 1074 } 1075 if (in->haveflags & CLK_HAVEFLAG3) { 1076 pp->sloppyclockflag &= ~CLK_FLAG3; 1077 pp->sloppyclockflag |= in->flags & CLK_FLAG3; 1078 } 1079 if (in->haveflags & CLK_HAVEFLAG4) { 1080 pp->sloppyclockflag &= ~CLK_FLAG4; 1081 pp->sloppyclockflag |= in->flags & CLK_FLAG4; 1082 } 1083 } 1084 1085 /* 1086 * Readback requested data 1087 */ 1088 if (out != NULL) { 1089 out->fudgeval1 = pp->stratum; 1090 out->fudgeval2 = pp->refid; 1091 out->haveflags = CLK_HAVEVAL1 | CLK_HAVEVAL2; 1092 out->fudgetime1 = pp->fudgetime1; 1093 if (0.0 != out->fudgetime1) 1094 out->haveflags |= CLK_HAVETIME1; 1095 out->fudgetime2 = pp->fudgetime2; 1096 if (0.0 != out->fudgetime2) 1097 out->haveflags |= CLK_HAVETIME2; 1098 out->flags = (u_char) pp->sloppyclockflag; 1099 if (CLK_FLAG1 & out->flags) 1100 out->haveflags |= CLK_HAVEFLAG1; 1101 if (CLK_FLAG2 & out->flags) 1102 out->haveflags |= CLK_HAVEFLAG2; 1103 if (CLK_FLAG3 & out->flags) 1104 out->haveflags |= CLK_HAVEFLAG3; 1105 if (CLK_FLAG4 & out->flags) 1106 out->haveflags |= CLK_HAVEFLAG4; 1107 1108 out->timereset = current_time - pp->timestarted; 1109 out->polls = pp->polls; 1110 out->noresponse = pp->noreply; 1111 out->badformat = pp->badformat; 1112 out->baddata = pp->baddata; 1113 1114 out->lastevent = pp->lastevent; 1115 out->currentstatus = pp->currentstatus; 1116 out->type = pp->type; 1117 out->clockdesc = pp->clockdesc; 1118 out->lencode = (u_short)pp->lencode; 1119 out->p_lastcode = pp->a_lastcode; 1120 } 1121 1122 /* 1123 * Give the stuff to the clock 1124 */ 1125 if (refclock_conf[clktype]->clock_control != noentry) 1126 (refclock_conf[clktype]->clock_control)(unit, in, out, peer); 1127 } 1128 1129 1130 /* 1131 * refclock_buginfo - return debugging info 1132 * 1133 * This routine is used mainly for debugging. It returns designated 1134 * values from the interface structure that can be displayed using 1135 * ntpdc and the clkbug command. 1136 */ 1137 void 1138 refclock_buginfo( 1139 sockaddr_u *srcadr, /* clock address */ 1140 struct refclockbug *bug /* output structure */ 1141 ) 1142 { 1143 struct peer *peer; 1144 struct refclockproc *pp; 1145 int clktype; 1146 int unit; 1147 unsigned u; 1148 1149 /* 1150 * Check for valid address and peer structure 1151 */ 1152 if (!ISREFCLOCKADR(srcadr)) 1153 return; 1154 1155 clktype = (u_char) REFCLOCKTYPE(srcadr); 1156 unit = REFCLOCKUNIT(srcadr); 1157 1158 peer = findexistingpeer(srcadr, NULL, NULL, -1, 0); 1159 1160 if (NULL == peer || NULL == peer->procptr) 1161 return; 1162 1163 pp = peer->procptr; 1164 1165 /* 1166 * Copy structure values 1167 */ 1168 bug->nvalues = 8; 1169 bug->svalues = 0x0000003f; 1170 bug->values[0] = pp->year; 1171 bug->values[1] = pp->day; 1172 bug->values[2] = pp->hour; 1173 bug->values[3] = pp->minute; 1174 bug->values[4] = pp->second; 1175 bug->values[5] = pp->nsec; 1176 bug->values[6] = pp->yearstart; 1177 bug->values[7] = pp->coderecv; 1178 bug->stimes = 0xfffffffc; 1179 bug->times[0] = pp->lastref; 1180 bug->times[1] = pp->lastrec; 1181 for (u = 2; u < bug->ntimes; u++) 1182 DTOLFP(pp->filter[u - 2], &bug->times[u]); 1183 1184 /* 1185 * Give the stuff to the clock 1186 */ 1187 if (refclock_conf[clktype]->clock_buginfo != noentry) 1188 (refclock_conf[clktype]->clock_buginfo)(unit, bug, peer); 1189 } 1190 1191 1192 #ifdef HAVE_PPSAPI 1193 /* 1194 * refclock_ppsapi - initialize/update ppsapi 1195 * 1196 * This routine is called after the fudge command to open the PPSAPI 1197 * interface for later parameter setting after the fudge command. 1198 */ 1199 int 1200 refclock_ppsapi( 1201 int fddev, /* fd device */ 1202 struct refclock_atom *ap /* atom structure pointer */ 1203 ) 1204 { 1205 if (ap->handle == 0) { 1206 if (time_pps_create(fddev, &ap->handle) < 0) { 1207 msyslog(LOG_ERR, 1208 "refclock_ppsapi: time_pps_create: %m"); 1209 return (0); 1210 } 1211 } 1212 return (1); 1213 } 1214 1215 1216 /* 1217 * refclock_params - set ppsapi parameters 1218 * 1219 * This routine is called to set the PPSAPI parameters after the fudge 1220 * command. 1221 */ 1222 int 1223 refclock_params( 1224 int mode, /* mode bits */ 1225 struct refclock_atom *ap /* atom structure pointer */ 1226 ) 1227 { 1228 ZERO(ap->pps_params); 1229 ap->pps_params.api_version = PPS_API_VERS_1; 1230 1231 /* 1232 * Solaris serial ports provide PPS pulse capture only on the 1233 * assert edge. FreeBSD serial ports provide capture on the 1234 * clear edge, while FreeBSD parallel ports provide capture 1235 * on the assert edge. Your mileage may vary. 1236 */ 1237 if (mode & CLK_FLAG2) 1238 ap->pps_params.mode = PPS_TSFMT_TSPEC | PPS_CAPTURECLEAR; 1239 else 1240 ap->pps_params.mode = PPS_TSFMT_TSPEC | PPS_CAPTUREASSERT; 1241 if (time_pps_setparams(ap->handle, &ap->pps_params) < 0) { 1242 msyslog(LOG_ERR, 1243 "refclock_params: time_pps_setparams: %m"); 1244 return (0); 1245 } 1246 1247 /* 1248 * If flag3 is lit, select the kernel PPS if we can. 1249 */ 1250 if (mode & CLK_FLAG3) { 1251 if (time_pps_kcbind(ap->handle, PPS_KC_HARDPPS, 1252 ap->pps_params.mode & ~PPS_TSFMT_TSPEC, 1253 PPS_TSFMT_TSPEC) < 0) { 1254 msyslog(LOG_ERR, 1255 "refclock_params: time_pps_kcbind: %m"); 1256 return (0); 1257 } 1258 hardpps_enable = 1; 1259 } 1260 return (1); 1261 } 1262 1263 1264 /* 1265 * refclock_pps - called once per second 1266 * 1267 * This routine is called once per second. It snatches the PPS 1268 * timestamp from the kernel and saves the sign-extended fraction in 1269 * a circular buffer for processing at the next poll event. 1270 */ 1271 int 1272 refclock_pps( 1273 struct peer *peer, /* peer structure pointer */ 1274 struct refclock_atom *ap, /* atom structure pointer */ 1275 int mode /* mode bits */ 1276 ) 1277 { 1278 struct refclockproc *pp; 1279 pps_info_t pps_info; 1280 struct timespec timeout; 1281 double dtemp; 1282 1283 /* 1284 * We require the clock to be synchronized before setting the 1285 * parameters. When the parameters have been set, fetch the 1286 * most recent PPS timestamp. 1287 */ 1288 pp = peer->procptr; 1289 if (ap->handle == 0) 1290 return (0); 1291 1292 if (ap->pps_params.mode == 0 && sys_leap != LEAP_NOTINSYNC) { 1293 if (refclock_params(pp->sloppyclockflag, ap) < 1) 1294 return (0); 1295 } 1296 timeout.tv_sec = 0; 1297 timeout.tv_nsec = 0; 1298 ZERO(pps_info); 1299 if (time_pps_fetch(ap->handle, PPS_TSFMT_TSPEC, &pps_info, 1300 &timeout) < 0) { 1301 refclock_report(peer, CEVNT_FAULT); 1302 return (0); 1303 } 1304 timeout = ap->ts; 1305 if (ap->pps_params.mode & PPS_CAPTUREASSERT) 1306 ap->ts = pps_info.assert_timestamp; 1307 else if (ap->pps_params.mode & PPS_CAPTURECLEAR) 1308 ap->ts = pps_info.clear_timestamp; 1309 else 1310 return (0); 1311 1312 if (0 == memcmp(&timeout, &ap->ts, sizeof(timeout))) 1313 return (0); 1314 1315 /* 1316 * Convert to signed fraction offset and stuff in median filter. 1317 */ 1318 pp->lastrec.l_ui = (u_int32)ap->ts.tv_sec + JAN_1970; 1319 dtemp = ap->ts.tv_nsec / 1e9; 1320 pp->lastrec.l_uf = (u_int32)(dtemp * FRAC); 1321 if (dtemp > .5) 1322 dtemp -= 1.; 1323 SAMPLE(-dtemp + pp->fudgetime1); 1324 #ifdef DEBUG 1325 if (debug > 1) 1326 printf("refclock_pps: %lu %f %f\n", current_time, 1327 dtemp, pp->fudgetime1); 1328 #endif 1329 return (1); 1330 } 1331 #endif /* HAVE_PPSAPI */ 1332 #endif /* REFCLOCK */ 1333