# 2.11BSD#431 - /usr/src/usr.sbin/ntp/ntp.c

##### Functions

    main              X

##### Variables

    debug             X
    dst               X
    force             X
    modename          X
    set               X
    sin               X
    sp                X
    verbose           X

##### Macros

    RETRY_COUNT       X
    TIME_OUT          X

       1: #ifndef lint
       2: static char *rcsid = "$Source: /usr/users/louie/ntp/RCS/ntp.c,v $ $Revision: 3.4.1.6 $ $Date: 89/05/18 18:21:29 $";
       3: #endif	lint
       4:
       5: /*
       6:  *  $Log:	ntp.c,v $
       7:  * Revision 3.4.1.6  89/05/18  18:21:29  louie
       8:  * A few cosmetic changes in ntp.c for the case when udp/ntp is not in the
       9:  * /etc/services file.
      10:  *
      11:  * Revision 3.4.1.5  89/05/03  15:09:53  louie
      12:  * Fix minor problem in ntp.c to get sin_family set in the proper place.
      13:  *
      14:  * Revision 3.4.1.4  89/04/07  18:04:49  louie
      15:  * Removed unused variables from ntp.c program.
      16:  *
      17:  * Revision 3.4.1.3  89/03/22  18:29:22  louie
      18:  * patch3: Use new RCS headers.
      19:  *
      20:  * Revision 3.4.1.2  89/03/22  17:51:13  louie
      21:  * Use a connect UDP socket so we can pick up ICMP error messages.
      22:  *
      23:  * Revision 3.4.1.1  89/03/20  00:02:32  louie
      24:  * patch1: Shorten timeout interval and clean up timeout message.
      25:  *
      26:  * Revision 3.4  89/03/17  18:36:54  louie
      27:  * Latest test release.
      28:  *
      29:  * Revision 3.3.1.1  89/03/17  18:23:14  louie
      30:  * Fix code that sets time.
      31:  *
      32:  * Revision 3.3  89/03/15  14:19:30  louie
      33:  * New baseline for next release.
      34:  *
      35:  * Revision 3.2.1.2  89/03/15  13:45:13  louie
      36:  * Fix use of NTP_PORT when getservbyname() fails.  Use "%f" in printf format
      37:  * strings rather than "%lf".
      38:  *
      39:  *
      40:  * Revision 3.2.1.1  89/03/10  11:26:23  louie
      41:  * Add (primitive) facility to set the time from an NTP timer server,
      42:  * much the same way as various UDP/TIME based programs do.  The
      43:  * default output format is a one line listing of delay, offset and time.  The
      44:  * previous, longer format can be had by using the -v option.
      45:  *
      46:  * Revision 3.2  89/03/07  18:20:55  louie
      47:  * Cleaned up displays of NTP header fields, also dumping in useful formats
      48:  * (floating point and ctime strings) as well as hex fields.
      49:  *
      50:  * Revision 3.1.1.1  89/02/15  08:53:30  louie
      51:  * Bug fixes to last released version.
      52:  *
      53:  *
      54:  * Revision 3.1  89/01/30  14:43:05  louie
      55:  * Second UNIX NTP test release.
      56:  *
      57:  * Revision 3.0  88/12/12  15:56:10  louie
      58:  * Test release of new UNIX NTP software.  This version should conform to the
      59:  * revised NTP protocol specification.
      60:  *
      61:  */
      62:
      63: /*
      64:  * This program expects a list of host names.  It will send off a
      65:  * network time protocol packet and print out the replies on the
      66:  * terminal.
      67:  *
      68:  * Example:
      69:  *
      70:  *  % ntp umd1.umd.edu
      71:  *  Packet from: [128.8.10.1]
      72:  *  Leap 0, version 1, mode Server, poll 6, precision -10 stratum 1 (WWVB)
      73:  *  Synch Distance is 0000.1999  0.099991
      74:  *  Synch Dispersion is 0000.0000  0.000000
      75:  *  Reference Timestamp is a7bea6c3.88b40000 Tue Mar  7 14:06:43 1989
      76:  *  Originate Timestamp is a7bea6d7.d7e6e652 Tue Mar  7 14:07:03 1989
      77:  *  Receive Timestamp is   a7bea6d7.cf1a0000 Tue Mar  7 14:07:03 1989
      78:  *  Transmit Timestamp is  a7bea6d8.0ccc0000 Tue Mar  7 14:07:04 1989
      79:  *  Input Timestamp is     a7bea6d8.1a77e5ea Tue Mar  7 14:07:04 1989
      80:  *  umd1: delay:0.019028 offset:-0.043890
      81:  *  Tue Mar  7 14:07:04 1989
      82:  *
      83:  */
      84:
      85: #include <stdio.h>
      86: #include <sys/types.h>
      87: #include <sys/param.h>
      88: #include <sys/time.h>
      89: #include <sys/uio.h>
      90: #include <sys/socket.h>
      91: #include <sys/ioctl.h>
      92:
      93: #include <netinet/in.h>
      94: #include <netinet/in_systm.h>
      95: #include <netinet/ip.h>
      96: #include <netinet/udp.h>
      97:
      98: #include <arpa/inet.h>
      99: #include <netdb.h>
     100: #include <strings.h>
     101: #include <errno.h>
     102: #include "ntp.h"
     103:
     104: char *modename[8] = {
     105:     "Unspecified",
     106:     "Symmetric Active",
     107:     "Symmetric Passive",
     108:     "Client",
     109:     "Server",
     110:     "Broadcast",
     111:     "Reserved-1",
     112:     "Reserved-2"
     113:     };
     114:
     115: #define RETRY_COUNT 2   /* number of times we want to retry */
     116: #define TIME_OUT        10  /* time to wait for reply, in secs */
     117:
     118:
     119: struct sockaddr_in sin = {AF_INET};
     120: struct sockaddr_in dst = {AF_INET};
     121: struct servent *sp;
     122: extern double ul_fixed_to_double(), s_fixed_to_double();
     123: extern int errno;
     124: int set, verbose, force;
     125: int debug;
     126: extern int optind;
     127:
     128: main(argc, argv)
     129:     int argc;
     130:     char *argv[];
     131: {
     132:     struct hostent *hp;
     133:     struct in_addr clock_host;
     134:     struct l_fixedpt in_timestamp;
     135:     static struct ntpdata ntp_data;
     136:     struct ntpdata *pkt = &ntp_data;
     137:     struct timeval tp, timeout;
     138:     int host, n, retry, s;
     139:     fd_set readfds;
     140:     int dstlen = sizeof(dst);
     141:     double t1, t2, t3, t4, offset, delay;
     142:     char ref_clock[5];
     143:     time_t net_time;
     144:     ref_clock[4] = '\0';
     145:
     146:     timeout.tv_sec = TIME_OUT;
     147:     timeout.tv_usec = 0;
     148:     retry = RETRY_COUNT;
     149:
     150:     sp = getservbyname("ntp", "udp");
     151:     if (sp == NULL) {
     152:         fprintf(stderr, "udp/ntp: service unknown; using default %d\n",
     153:             NTP_PORT);
     154:         dst.sin_port = htons(NTP_PORT);
     155:     } else
     156:         dst.sin_port = sp->s_port;
     157:
     158:     dst.sin_family = AF_INET;
     159:     while ((n = getopt(argc, argv, "vsf")) != EOF) {
     160:         switch (n) {
     161:         case 'v':
     162:             verbose = 1;
     163:             break;
     164:         case 's':
     165:             set = 1;
     166:             break;
     167:         case 'f':
     168:             force = 1;
     169:             break;
     170:         }
     171:     }
     172:     for (host = optind; host < argc; ++host) {
     173:         long    HostAddr;
     174:
     175:         if (argv[host] == NULL)
     176:             continue;
     177:
     178:         hp = NULL;
     179:         HostAddr = inet_addr(argv[host]);
     180:         dst.sin_addr.s_addr = (u_long) HostAddr;
     181:         if (HostAddr == -1) {
     182:             hp = gethostbyname(argv[host]);
     183:             if (hp == NULL) {
     184:                 fprintf(stderr, "\nNo such host: %s\n",
     185:                     argv[host]);
     186:                 continue;
     187:             }
     188:             bcopy(hp->h_addr, (char *) &dst.sin_addr,hp->h_length);
     189:         }
     190:
     191:         bzero((char *)pkt, sizeof(ntp_data));
     192:
     193:         pkt->status = NTPVERSION_1 | NO_WARNING | MODE_CLIENT;
     194:         pkt->stratum = UNSPECIFIED;
     195:         pkt->ppoll = 0;
     196:
     197:         if ((s = socket(AF_INET, SOCK_DGRAM, 0)) < 0) {
     198:             perror("ntp socket");
     199:             exit(1);
     200:         }
     201:
     202:         FD_ZERO(&readfds);
     203:         FD_SET(s, &readfds);    /* since it's always modified on ret */
     204:
     205:         if (connect(s, (struct sockaddr *)&dst, dstlen)) {
     206:             perror("connect");
     207:             exit(1);
     208:         }
     209:
     210:         /*
     211: 		 * Needed to fill in the time stamp fields
     212: 		 */
     213:         (void) gettimeofday(&tp, (struct timezone *) 0);
     214:         tstamp(&pkt->xmt, &tp);
     215:
     216:         if (send(s, (char *) pkt, sizeof(ntp_data), 0) < 0) {
     217:             perror("send");
     218:             exit(1);
     219:         }
     220:
     221:         /*
     222: 		 * Wait for the reply by watching the file descriptor
     223: 		 */
     224:         if ((n = select(FD_SETSIZE, (fd_set *) & readfds, (fd_set *) 0,
     225:                 (fd_set *) 0, &timeout)) < 0) {
     226:             perror("ntp select");
     227:             exit(1);
     228:         }
     229:
     230:         if (n == 0) {
     231:             fprintf(stderr,"*Timeout*\n");
     232:             if (--retry)
     233:                 --host;
     234:             else {
     235:                 fprintf(stderr,"Host %s is not responding\n",
     236:                        argv[host]);
     237:                 retry = RETRY_COUNT;
     238:             }
     239:             continue;
     240:         }
     241:         if ((recvfrom(s, (char *) pkt, sizeof(ntp_data), 0,
     242:                   (struct sockaddr *) &sin, &dstlen)) < 0) {
     243:             perror("recvfrom");
     244:             exit(1);
     245:         }
     246:         (void) gettimeofday(&tp, (struct timezone *) 0);
     247:         tstamp(&in_timestamp, &tp);
     248:
     249:         close(s);
     250:         if (verbose) {
     251:             printf("Packet from: [%s]\n", inet_ntoa(sin.sin_addr));
     252:             printf("Leap %d, version %d, mode %s, poll %d, precision %d stratum %d",
     253:                    (pkt->status & LEAPMASK) >> 6,
     254:                    (pkt->status & VERSIONMASK) >> 3,
     255:                    modename[pkt->status & MODEMASK],
     256:                    pkt->ppoll, pkt->precision, pkt->stratum);
     257:             switch (pkt->stratum) {
     258:             case 0:
     259:             case 1:
     260:                 (void) strncpy(ref_clock, (char *) &pkt->refid, 4);
     261:                 ref_clock[4] = '\0';
     262:                 printf(" (%s)\n", ref_clock);
     263:                 break;
     264:             default:
     265:                 clock_host.s_addr = (u_long) pkt->refid;
     266:                 printf(" [%s]\n", inet_ntoa(clock_host));
     267:                 break;
     268:             }
     269:             printf("Synch Distance is %04x.%04x  %f\n",
     270:                    ntohs(pkt->distance.int_part),
     271:                    ntohs(pkt->distance.fraction),
     272:                    s_fixed_to_double(&pkt->distance));
     273:
     274:             printf("Synch Dispersion is %04x.%04x  %f\n",
     275:                    ntohs(pkt->dispersion.int_part),
     276:                    ntohs(pkt->dispersion.fraction),
     277:                    s_fixed_to_double(&pkt->dispersion));
     278:
     279:             net_time = ntohl(pkt->reftime.int_part) - JAN_1970;
     280:             printf("Reference Timestamp is %08lx.%08lx %s",
     281:                    ntohl(pkt->reftime.int_part),
     282:                    ntohl(pkt->reftime.fraction),
     283:                    ctime(&net_time));
     284:
     285:             net_time = ntohl(pkt->org.int_part) - JAN_1970;
     286:             printf("Originate Timestamp is %08lx.%08lx %s",
     287:                    ntohl(pkt->org.int_part),
     288:                    ntohl(pkt->org.fraction),
     289:                    ctime(&net_time));
     290:
     291:             net_time = ntohl(pkt->rec.int_part) - JAN_1970;
     292:             printf("Receive Timestamp is   %08lx.%08lx %s",
     293:                    ntohl(pkt->rec.int_part),
     294:                    ntohl(pkt->rec.fraction),
     295:                    ctime(&net_time));
     296:
     297:             net_time = ntohl(pkt->xmt.int_part) - JAN_1970;
     298:             printf("Transmit Timestamp is  %08lx.%08lx %s",
     299:                    ntohl(pkt->xmt.int_part),
     300:                    ntohl(pkt->xmt.fraction),
     301:                    ctime(&net_time));
     302:         }
     303:         t1 = ul_fixed_to_double(&pkt->org);
     304:         t2 = ul_fixed_to_double(&pkt->rec);
     305:         t3 = ul_fixed_to_double(&pkt->xmt);
     306:         t4 = ul_fixed_to_double(&in_timestamp);
     307:
     308:         net_time = ntohl(in_timestamp.int_part) - JAN_1970;
     309:         if (verbose)
     310:             printf("Input Timestamp is     %08lx.%08lx %s",
     311:                    ntohl(in_timestamp.int_part),
     312:                    ntohl(in_timestamp.fraction), ctime(&net_time));
     313:
     314:         delay = (t4 - t1) - (t3 - t2);
     315:         offset = (t2 - t1) + (t3 - t4);
     316:         offset = offset / 2.0;
     317:         printf("%.20s: delay:%f offset:%f  ",
     318:                hp ? hp->h_name : argv[host],
     319:                delay, offset);
     320:         net_time = ntohl(pkt->xmt.int_part) - JAN_1970 + delay;
     321:         fputs(ctime(&net_time), stdout);
     322:         (void)fflush(stdout);
     323:
     324:         if (!set)
     325:             continue;
     326:
     327:         if ((offset < 0 ? -offset  : offset) > WAYTOOBIG && !force) {
     328:             fprintf(stderr, "Offset too large - use -f option to force clock set.\n");
     329:             continue;
     330:         }
     331:
     332:         if (pkt->status & LEAPMASK == ALARM) {
     333:             fprintf(stderr, "Can't set time from %s - unsynchronized\n",
     334:                 argv[host]);
     335:             continue;
     336:         }
     337:
     338:         /* set the clock */
     339:         gettimeofday(&tp, (struct timezone *) 0);
     340:         offset += tp.tv_sec;
     341:         offset += tp.tv_usec / 1000000.0;
     342:         tp.tv_sec = offset;
     343:         tp.tv_usec = (offset - tp.tv_sec) * 1000000.0;
     344:
     345:         if (settimeofday(&tp, (struct timezone *) 0)) {
     346:             perror("Can't set time (settimeofday)");
     347:         } else
     348:             set = 0;
     349:     }           /* end of for each host */
     350:     exit(0);
     351: }               /* end of main */

#### Defined functions

main defined in line 128; never used

#### Defined variables

debug defined in line 125; never used
dst defined in line 120; used 7 times

- in line 140, 154-158(3), 180, 188, 205

force defined in line 124; used 2 times

- in line 168, 327

modename defined in line 104; used 1 times

- in line 255

rcsid defined in line 2; never used
set defined in line 124; used 3 times

- in line 165, 324, 348

sin defined in line 119; used 2 times

- in line 242, 251

sp defined in line 121; used 3 times

- in line 150-156(3)

verbose defined in line 124; used 3 times

- in line 162, 250, 309

#### Defined macros

RETRY_COUNT defined in line 115; used 2 times

- in line 148, 237

TIME_OUT defined in line 116; used 1 times

- in line 146

Last modified: 1989-07-25 Generated: 2016-12-26 | Generated by src2html V0.67 page hit count: 1709 |