Deleted Added
sdiff udiff text old ( 106424 ) new ( 132451 )
full compact
1/*
2 * ntpdate - set the time of day by polling one or more NTP servers
3 */
4
5#ifdef HAVE_CONFIG_H
6# include <config.h>
7#endif
8

--- 32 unchanged lines hidden (view full) ---

41# ifdef HAVE_SYS_IOCTL_H
42# include <sys/ioctl.h>
43# endif
44#endif /* SYS_WINNT */
45#ifdef HAVE_SYS_RESOURCE_H
46# include <sys/resource.h>
47#endif /* HAVE_SYS_RESOURCE_H */
48
49#ifdef SYS_VXWORKS
50# include "ioLib.h"
51# include "sockLib.h"
52# include "timers.h"
53
54/* select wants a zero structure ... */
55struct timeval timeout = {0,0};
56#else
57struct timeval timeout = {60,0};
58#endif
59
60#include "recvbuff.h"
61
62#ifdef SYS_WINNT
63# define TARGET_RESOLUTION 1 /* Try for 1-millisecond accuracy
64 on Windows NT timers. */
65#pragma comment(lib, "winmm")
66#endif /* SYS_WINNT */
67
68/*
69 * Scheduling priority we run at
70 */
71#ifndef SYS_VXWORKS

--- 21 unchanged lines hidden (view full) ---

93/*
94 * Debugging flag
95 */
96volatile int debug = 0;
97
98/*
99 * File descriptor masks etc. for call to select
100 */
101int fd;
102#ifdef HAVE_POLL_H
103struct pollfd fdmask;
104#else
105fd_set fdmask;
106#endif
107
108/*
109 * Initializing flag. All async routines watch this and only do their
110 * thing when it is clear.
111 */
112int initializing = 1;
113
114/*

--- 64 unchanged lines hidden (view full) ---

179/*
180 * Miscellaneous flags
181 */
182int verbose = 0;
183int always_step = 0;
184int never_step = 0;
185
186int ntpdatemain P((int, char **));
187static void transmit P((struct server *));
188static void receive P((struct recvbuf *));
189static void server_data P((struct server *, s_fp, l_fp *, u_fp));
190static void clock_filter P((struct server *));
191static struct server *clock_select P((void));
192static int clock_adjust P((void));
193static void addserver P((char *));
194static struct server *findserver P((struct sockaddr_in *));
195 void timer P((void));
196static void init_alarm P((void));
197#ifndef SYS_WINNT
198static RETSIGTYPE alarming P((int));
199#endif /* SYS_WINNT */
200static void init_io P((void));
201static void sendpkt P((struct sockaddr_in *, struct pkt *, int));
202void input_handler P((void));
203
204static int l_adj_systime P((l_fp *));
205static int l_step_systime P((l_fp *));
206
207static int getnetnum P((const char *, u_int32 *));
208static void printserver P((struct server *, FILE *));
209
210#ifdef SYS_WINNT
211int on = 1;
212WORD wVersionRequested;
213WSADATA wsaData;
214HANDLE TimerThreadHandle = NULL;
215#endif /* SYS_WINNT */

--- 84 unchanged lines hidden (view full) ---

300 )
301{
302 int was_alarmed;
303 struct recvbuf *rbuflist;
304 struct recvbuf *rbuf;
305 l_fp tmp;
306 int errflg;
307 int c;
308#ifdef HAVE_NETINFO
309 ni_namelist *netinfoservers;
310#endif
311#ifdef SYS_WINNT
312 HANDLE process_handle;
313
314 wVersionRequested = MAKEWORD(1,1);
315 if (WSAStartup(wVersionRequested, &wsaData)) {
316 msyslog(LOG_ERR, "No useable winsock.dll: %m");
317 exit(1);
318 }
319
320 key_file = key_file_storage;
321
322 if (!ExpandEnvironmentStrings(KEYFILE, key_file, MAX_PATH))
323 {
324 msyslog(LOG_ERR, "ExpandEnvironmentStrings(KEYFILE) failed: %m\n");

--- 6 unchanged lines hidden (view full) ---

331
332 errflg = 0;
333 progname = argv[0];
334 syslogit = 0;
335
336 /*
337 * Decode argument list
338 */
339 while ((c = ntp_getopt(argc, argv, "a:bBde:k:o:p:qr:st:uv")) != EOF)
340 switch (c)
341 {
342 case 'a':
343 c = atoi(ntp_optarg);
344 sys_authenticate = 1;
345 sys_authkey = c;
346 break;
347 case 'b':
348 always_step++;
349 never_step = 0;

--- 73 unchanged lines hidden (view full) ---

423 ++errflg;
424 break;
425 default:
426 break;
427 }
428
429 if (errflg) {
430 (void) fprintf(stderr,
431 "usage: %s [-bBdqsuv] [-a key#] [-e delay] [-k file] [-p samples] [-o version#] [-r rate] [-t timeo] server ...\n",
432 progname);
433 exit(2);
434 }
435
436 if (debug || simple_query) {
437#ifdef HAVE_SETVBUF
438 static char buf[BUFSIZ];
439 setvbuf(stdout, buf, _IOLBF, BUFSIZ);
440#else

--- 92 unchanged lines hidden (view full) ---

533#endif
534#ifdef SYS_WINNT
535 process_handle = GetCurrentProcess();
536 if (!SetPriorityClass(process_handle, (DWORD) REALTIME_PRIORITY_CLASS)) {
537 msyslog(LOG_ERR, "SetPriorityClass failed: %m");
538 }
539#endif /* SYS_WINNT */
540
541 initializing = 0;
542
543 was_alarmed = 0;
544 rbuflist = (struct recvbuf *)0;
545 while (complete_servers < sys_numservers) {
546#ifdef HAVE_POLL_H
547 struct pollfd rdfdes;
548#else
549 fd_set rdfdes;
550#endif
551 int nfound;
552
553 if (alarm_flag) { /* alarmed? */
554 was_alarmed = 1;
555 alarm_flag = 0;
556 }
557 rbuflist = getrecvbufs(); /* get received buffers */
558
559 if (!was_alarmed && rbuflist == (struct recvbuf *)0) {
560 /*
561 * Nothing to do. Wait for something.
562 */
563 rdfdes = fdmask;
564#ifdef HAVE_POLL_H
565 nfound = poll(&rdfdes, 1, timeout.tv_sec * 1000);
566#else
567 nfound = select(fd+1, &rdfdes, (fd_set *)0,
568 (fd_set *)0, &timeout);
569#endif
570 if (nfound > 0)
571 input_handler();
572 else if (
573#ifndef SYS_WINNT
574 nfound == -1
575#else
576 nfound == SOCKET_ERROR
577#endif /* SYS_WINNT */
578 ) {
579#ifndef SYS_WINNT
580 if (errno != EINTR)
581#endif
582 msyslog(LOG_ERR,
583#ifdef HAVE_POLL_H
584 "poll() error: %m"
585#else
586 "select() error: %m"
587#endif
588 );
589 } else {
590#ifndef SYS_VXWORKS
591 msyslog(LOG_DEBUG,
592#ifdef HAVE_POLL_H
593 "poll(): nfound = %d, error: %m",
594#else
595 "select(): nfound = %d, error: %m",
596#endif
597 nfound);
598#endif
599 }

--- 34 unchanged lines hidden (view full) ---

634 */
635#ifdef SYS_WINNT
636 WSACleanup();
637#endif
638#ifdef SYS_VXWORKS
639 close (fd);
640 timer_delete(ntpdate_timerid);
641#endif
642 return clock_adjust();
643}
644
645
646/*
647 * transmit - transmit a packet to the given server, or mark it completed.
648 * This is called by the timeout routine and by the receive
649 * procedure.
650 */
651static void
652transmit(
653 register struct server *server
654 )
655{
656 struct pkt xpkt;
657
658 if (debug)
659 printf("transmit(%s)\n", ntoa(&server->srcadr));
660
661 if (server->filter_nextpt < server->xmtcnt) {
662 l_fp ts;
663 /*
664 * Last message to this server timed out. Shift
665 * zeros into the filter.
666 */
667 L_CLR(&ts);

--- 38 unchanged lines hidden (view full) ---

706 get_systime(&server->xmt);
707 L_ADDUF(&server->xmt, sys_authdelay);
708 HTONL_FP(&server->xmt, &xpkt.xmt);
709 len = authencrypt(sys_authkey, (u_int32 *)&xpkt, LEN_PKT_NOMAC);
710 sendpkt(&(server->srcadr), &xpkt, (int)(LEN_PKT_NOMAC + len));
711
712 if (debug > 1)
713 printf("transmit auth to %s\n",
714 ntoa(&(server->srcadr)));
715 } else {
716 get_systime(&(server->xmt));
717 HTONL_FP(&server->xmt, &xpkt.xmt);
718 sendpkt(&(server->srcadr), &xpkt, LEN_PKT_NOMAC);
719
720 if (debug > 1)
721 printf("transmit to %s\n", ntoa(&(server->srcadr)));
722 }
723
724 /*
725 * Update the server timeout and transmit count
726 */
727 server->event_time = current_time + sys_timeout;
728 server->xmtcnt++;
729}

--- 13 unchanged lines hidden (view full) ---

743 l_fp t10, t23, tmp;
744 l_fp org;
745 l_fp rec;
746 l_fp ci;
747 int has_mac;
748 int is_authentic;
749
750 if (debug)
751 printf("receive(%s)\n", ntoa(&rbufp->recv_srcadr));
752 /*
753 * Check to see if the packet basically looks like something
754 * intended for us.
755 */
756 if (rbufp->recv_length == LEN_PKT_NOMAC)
757 has_mac = 0;
758 else if (rbufp->recv_length >= LEN_PKT_NOMAC)
759 has_mac = 1;

--- 146 unchanged lines hidden (view full) ---

906static void
907server_data(
908 register struct server *server,
909 s_fp d,
910 l_fp *c,
911 u_fp e
912 )
913{
914 register int i;
915
916 i = server->filter_nextpt;
917 if (i < NTP_SHIFT) {
918 server->filter_delay[i] = d;
919 server->filter_offset[i] = *c;
920 server->filter_soffset[i] = LFPTOFP(c);
921 server->filter_error[i] = e;
922 server->filter_nextpt = i + 1;
923 }
924}
925
926
927/*
928 * clock_filter - determine a server's delay, dispersion and offset
929 */
930static void

--- 318 unchanged lines hidden (view full) ---

1249 if (absoffset < 0)
1250 absoffset = -absoffset;
1251 dostep = (absoffset >= NTPDATE_THRESHOLD || absoffset < 0);
1252 }
1253
1254 if (dostep) {
1255 if (simple_query || l_step_systime(&server->offset)) {
1256 msyslog(LOG_NOTICE, "step time server %s offset %s sec",
1257 ntoa(&server->srcadr),
1258 lfptoa(&server->offset, 6));
1259 }
1260 } else {
1261#if !defined SYS_WINNT && !defined SYS_CYGWIN32
1262 if (simple_query || l_adj_systime(&server->offset)) {
1263 msyslog(LOG_NOTICE, "adjust time server %s offset %s sec",
1264 ntoa(&server->srcadr),
1265 lfptoa(&server->offset, 6));
1266 }
1267#else
1268 /* The NT SetSystemTimeAdjustment() call achieves slewing by
1269 * changing the clock frequency. This means that we cannot specify
1270 * it to slew the clock by a definite amount and then stop like
1271 * the Unix adjtime() routine. We can technically adjust the clock
1272 * frequency, have ntpdate sleep for a while, and then wake

--- 15 unchanged lines hidden (view full) ---

1288 * for it.
1289 */
1290static void
1291addserver(
1292 char *serv
1293 )
1294{
1295 register struct server *server;
1296 u_int32 netnum;
1297
1298 if (!getnetnum(serv, &netnum)) {
1299 msyslog(LOG_ERR, "can't find host %s\n", serv);
1300 return;
1301 }
1302
1303 server = (struct server *)emalloc(sizeof(struct server));
1304 memset((char *)server, 0, sizeof(struct server));
1305
1306 server->srcadr.sin_family = AF_INET;
1307 server->srcadr.sin_addr.s_addr = netnum;
1308 server->srcadr.sin_port = htons(NTP_PORT);
1309
1310 server->event_time = ++sys_numservers;
1311 if (sys_servers == NULL)
1312 sys_servers = server;
1313 else {
1314 struct server *sp;
1315
1316 for (sp = sys_servers; sp->next_server != NULL;
1317 sp = sp->next_server) ;
1318 sp->next_server = server;
1319 }
1320}
1321
1322
1323/*
1324 * findserver - find a server in the list given its address
1325 */
1326static struct server *
1327findserver(
1328 struct sockaddr_in *addr
1329 )
1330{
1331 register u_int32 netnum;
1332 struct server *server;
1333 struct server *mc_server;
1334
1335 mc_server = NULL;
1336 if (htons(addr->sin_port) != NTP_PORT)
1337 return 0;
1338 netnum = addr->sin_addr.s_addr;
1339
1340 for (server = sys_servers; server != NULL;
1341 server = server->next_server) {
1342 register u_int32 servnum;
1343
1344 servnum = server->srcadr.sin_addr.s_addr;
1345 if (netnum == servnum)
1346 return server;
1347 if (IN_MULTICAST(ntohl(servnum)))
1348 mc_server = server;
1349 }
1350
1351 if (mc_server != NULL) {
1352 struct server *sp;
1353
1354 if (mc_server->event_time != 0) {
1355 mc_server->event_time = 0;
1356 complete_servers++;
1357 }
1358 server = (struct server *)emalloc(sizeof(struct server));
1359 memset((char *)server, 0, sizeof(struct server));
1360
1361 server->srcadr.sin_family = AF_INET;
1362 server->srcadr.sin_addr.s_addr = netnum;
1363 server->srcadr.sin_port = htons(NTP_PORT);
1364
1365 server->event_time = ++sys_numservers;
1366 for (sp = sys_servers; sp->next_server != NULL;
1367 sp = sp->next_server) ;
1368 sp->next_server = server;
1369 transmit(server);
1370 }
1371 return NULL;
1372}
1373

--- 106 unchanged lines hidden (view full) ---

1480 /*
1481 * Set up the alarm interrupt. The first comes 1/(2*TIMER_HZ)
1482 * seconds from now and they continue on every 1/TIMER_HZ seconds.
1483 */
1484 (void) signal_no_reset(SIGALRM, alarming);
1485 itimer.it_interval.tv_sec = itimer.it_value.tv_sec = 0;
1486 itimer.it_interval.tv_usec = 1000000/TIMER_HZ;
1487 itimer.it_value.tv_usec = 1000000/(TIMER_HZ<<1);
1488 setitimer(ITIMER_REAL, &itimer, (struct itimerval *)0);
1489# endif
1490#if defined SYS_CYGWIN32
1491 /*
1492 * Get previleges needed for fiddling with the clock
1493 */
1494
1495 /* get the current process token handle */

--- 81 unchanged lines hidden (view full) ---

1577
1578
1579/*
1580 * init_io - initialize I/O data and open socket
1581 */
1582static void
1583init_io(void)
1584{
1585 /*
1586 * Init buffer free list and stat counters
1587 */
1588 init_recvbuff(sys_numservers + 2);
1589 /*
1590 * Open the socket
1591 */
1592
1593 /* create a datagram (UDP) socket */
1594 if ((fd = socket(AF_INET, SOCK_DGRAM, 0)) < 0) {
1595 msyslog(LOG_ERR, "socket() failed: %m");
1596 exit(1);
1597 /*NOTREACHED*/
1598 }
1599
1600 /*
1601 * bind the socket to the NTP port
1602 */
1603 if (!debug && !simple_query && !unpriv_port) {
1604 struct sockaddr_in addr;
1605
1606 memset((char *)&addr, 0, sizeof addr);
1607 addr.sin_family = AF_INET;
1608 addr.sin_port = htons(NTP_PORT);
1609 addr.sin_addr.s_addr = htonl(INADDR_ANY);
1610 if (bind(fd, (struct sockaddr *)&addr, sizeof(addr)) < 0) {
1611#ifndef SYS_WINNT
1612 if (errno == EADDRINUSE)
1613#else
1614 if (WSAGetLastError() == WSAEADDRINUSE)
1615#endif /* SYS_WINNT */
1616 msyslog(LOG_ERR,
1617 "the NTP socket is in use, exiting");
1618 else
1619 msyslog(LOG_ERR, "bind() fails: %m");
1620 exit(1);
1621 }
1622 }
1623
1624#ifdef HAVE_POLL_H
1625 fdmask.fd = fd;
1626 fdmask.events = POLLIN;
1627#else
1628 FD_ZERO(&fdmask);
1629 FD_SET(fd, &fdmask);
1630#endif
1631
1632 /*
1633 * set non-blocking,
1634 */
1635#ifndef SYS_WINNT
1636# ifdef SYS_VXWORKS
1637 {
1638 int on = TRUE;
1639
1640 if (ioctl(fd,FIONBIO, &on) == ERROR) {
1641 msyslog(LOG_ERR, "ioctl(FIONBIO) fails: %m");
1642 exit(1);
1643 }
1644 }
1645# else /* not SYS_VXWORKS */
1646# if defined(O_NONBLOCK)
1647 if (fcntl(fd, F_SETFL, O_NONBLOCK) < 0) {
1648 msyslog(LOG_ERR, "fcntl(FNDELAY|FASYNC) fails: %m");
1649 exit(1);
1650 /*NOTREACHED*/
1651 }
1652# else /* not O_NONBLOCK */
1653# if defined(FNDELAY)
1654 if (fcntl(fd, F_SETFL, FNDELAY) < 0) {
1655 msyslog(LOG_ERR, "fcntl(FNDELAY|FASYNC) fails: %m");
1656 exit(1);
1657 /*NOTREACHED*/
1658 }
1659# else /* FNDELAY */
1660# include "Bletch: Need non blocking I/O"
1661# endif /* FNDELAY */
1662# endif /* not O_NONBLOCK */
1663# endif /* SYS_VXWORKS */
1664#else /* SYS_WINNT */
1665 if (ioctlsocket(fd, FIONBIO, (u_long *) &on) == SOCKET_ERROR) {
1666 msyslog(LOG_ERR, "ioctlsocket(FIONBIO) fails: %m");
1667 exit(1);
1668 }
1669#endif /* SYS_WINNT */
1670}
1671
1672
1673/*
1674 * sendpkt - send a packet to the specified destination
1675 */
1676static void
1677sendpkt(
1678 struct sockaddr_in *dest,
1679 struct pkt *pkt,
1680 int len
1681 )
1682{
1683 int cc;
1684
1685#ifdef SYS_WINNT
1686 DWORD err;
1687#endif /* SYS_WINNT */
1688
1689 cc = sendto(fd, (char *)pkt, (size_t)len, 0, (struct sockaddr *)dest,
1690 sizeof(struct sockaddr_in));
1691#ifndef SYS_WINNT
1692 if (cc == -1) {
1693 if (errno != EWOULDBLOCK && errno != ENOBUFS)
1694#else
1695 if (cc == SOCKET_ERROR) {
1696 err = WSAGetLastError();
1697 if (err != WSAEWOULDBLOCK && err != WSAENOBUFS)
1698#endif /* SYS_WINNT */
1699 msyslog(LOG_ERR, "sendto(%s): %m", ntoa(dest));
1700 }
1701}
1702
1703
1704/*
1705 * input_handler - receive packets asynchronously
1706 */
1707void
1708input_handler(void)
1709{
1710 register int n;
1711 register struct recvbuf *rb;
1712 struct timeval tvzero;
1713 int fromlen;
1714 l_fp ts;
1715#ifdef HAVE_POLL_H
1716 struct pollfd fds;
1717#else
1718 fd_set fds;
1719#endif
1720
1721 /*
1722 * Do a poll to see if we have data
1723 */
1724 for (;;) {
1725 fds = fdmask;
1726 tvzero.tv_sec = tvzero.tv_usec = 0;
1727#ifdef HAVE_POLL_H
1728 n = poll(&fds, 1, tvzero.tv_sec * 1000);
1729#else
1730 n = select(fd+1, &fds, (fd_set *)0, (fd_set *)0, &tvzero);
1731#endif
1732
1733 /*
1734 * If nothing to do, just return. If an error occurred,
1735 * complain and return. If we've got some, freeze a
1736 * timestamp.
1737 */
1738 if (n == 0)
1739 return;
1740 else if (n == -1) {
1741 if (errno != EINTR)
1742 msyslog(LOG_ERR,
1743#ifdef HAVE_POLL_H
1744 "poll() error: %m"
1745#else
1746 "select() error: %m"
1747#endif
1748 );
1749 return;
1750 }
1751 get_systime(&ts);
1752
1753 /*
1754 * Get a buffer and read the frame. If we
1755 * haven't got a buffer, or this is received
1756 * on the wild card socket, just dump the packet.
1757 */
1758 if (initializing || free_recvbuffs() == 0) {
1759 char buf[100];
1760
1761#ifndef SYS_WINNT
1762 (void) read(fd, buf, sizeof buf);
1763#else
1764 /* NT's _read does not operate on nonblocking sockets
1765 * either recvfrom or ReadFile() has to be used here.
1766 * ReadFile is used in [ntpd]ntp_intres() and ntpdc,
1767 * just to be different use recvfrom() here
1768 */
1769 recvfrom(fd, buf, sizeof(buf), 0, (struct sockaddr *)0, NULL);
1770#endif /* SYS_WINNT */
1771 continue;
1772 }
1773
1774 rb = get_free_recv_buffer();
1775
1776 fromlen = sizeof(struct sockaddr_in);
1777 rb->recv_length = recvfrom(fd, (char *)&rb->recv_pkt,
1778 sizeof(rb->recv_pkt), 0,
1779 (struct sockaddr *)&rb->recv_srcadr, &fromlen);
1780 if (rb->recv_length == -1) {
1781 freerecvbuf(rb);
1782 continue;
1783 }
1784
1785 /*

--- 117 unchanged lines hidden (view full) ---

1903#else /* SLEWALWAYS */
1904 if (debug)
1905 return 1;
1906 LFPTOD(ts, dtemp);
1907 return step_systime(dtemp);
1908#endif /* SLEWALWAYS */
1909}
1910
1911/*
1912 * getnetnum - given a host name, return its net number
1913 */
1914static int
1915getnetnum(
1916 const char *host,
1917 u_int32 *num
1918 )
1919{
1920 struct hostent *hp;
1921
1922 if (decodenetnum(host, num)) {
1923 return 1;
1924 } else if ((hp = gethostbyname(host)) != 0) {
1925 memmove((char *)num, hp->h_addr, sizeof(u_int32));
1926 return (1);
1927 }
1928 return (0);
1929}
1930
1931/* XXX ELIMINATE printserver similar in ntptrace.c, ntpdate.c */
1932/*
1933 * printserver - print detail information for a server
1934 */
1935static void
1936printserver(
1937 register struct server *pp,
1938 FILE *fp
1939 )
1940{
1941 register int i;
1942 char junk[5];
1943 char *str;
1944
1945 if (!debug) {
1946 (void) fprintf(fp, "server %s, stratum %d, offset %s, delay %s\n",
1947 ntoa(&pp->srcadr), pp->stratum,
1948 lfptoa(&pp->offset, 6), fptoa((s_fp)pp->delay, 5));
1949 return;
1950 }
1951
1952 (void) fprintf(fp, "server %s, port %d\n",
1953 ntoa(&pp->srcadr), ntohs(pp->srcadr.sin_port));
1954
1955 (void) fprintf(fp, "stratum %d, precision %d, leap %c%c, trust %03o\n",
1956 pp->stratum, pp->precision,
1957 pp->leap & 0x2 ? '1' : '0',
1958 pp->leap & 0x1 ? '1' : '0',
1959 pp->trust);
1960
1961 if (pp->stratum == 1) {
1962 junk[4] = 0;
1963 memmove(junk, (char *)&pp->refid, 4);
1964 str = junk;
1965 } else {
1966 str = numtoa(pp->refid);
1967 }
1968 (void) fprintf(fp,
1969 "refid [%s], delay %s, dispersion %s\n",
1970 str, fptoa((s_fp)pp->delay, 5),
1971 ufptoa(pp->dispersion, 5));
1972
1973 (void) fprintf(fp, "transmitted %d, in filter %d\n",
1974 pp->xmtcnt, pp->filter_nextpt);

--- 113 unchanged lines hidden ---