# /* nettime.c */ /* EMACS_MODES: c !fill */ /* This file contains the routines to deal with the Internet time * servers for finding out the time. Presently the addresses * of the available Internet time servers are compiled in; the * routine udptime () goes out to all the available Internet * time servers to try to get the time. * This file contains the following routines: * udptime ask some udp timeservers what time it is */ typedef long time_t; /* ugly! */ #include #include #define TIMEOUT 5 /* response timeout */ #define TIMESOCK 37 /* time server socket */ #define MAGICFUDGE 0x83AA7e80 /* seconds from 1900 to 1970 */ /* Table of all known timeservers */ static in_name timeservers[] = { 0x000A0600, /* mit-multics */ 0x04800700, /* dcn7 */ }; static int ntsrv = sizeof(timeservers)/sizeof(in_name); time_t udptime () /* Try to find the current time by asking other udp timeservers. * Build timeserver requests for each of the timeservers we presently * know about, send them all out, then wait for responses. Returns * the time in seconds since midnight Jan 1 1970 GMT, or 0 if unknown. */ { register in_name *pn; /* pointer to current ts */ register struct udp *pup; /* ptr. to udp header */ register struct ip *pip; /* ptr. to internet header */ unshort *ptm; /* ptr. to returned time */ unshort locsoc; /* local socket number */ caddr_t inpkt; /* received packet */ caddr_t outpkt; /* output packet */ int udpfd; /* udp file descriptor */ union { time_t r_time; unshort r_word[2]; } res; /* returned time */ int rcvlen; /* len of received packet */ int i; /* temp index */ locsoc = udp_socket (); if ((udpfd = udp_open (0L, 0, locsoc)) < 0) return (0L); if ((inpkt = udp_alloc (INETLEN, 0)) == NULL) return (0L); if ((outpkt = udp_alloc (0, 0)) == NULL) { udp_free (inpkt); return (0L); } pip = in_head(outpkt); /* get headers */ pup = udp_head(pip); for (pn = ×ervers[0]; pn < ×ervers[ntsrv]; pn++) { pip->ip_dest = *pn; /* set up headers */ pip->ip_id = 0; /* kernel fills id */ pup->ud_srcp = locsoc; /* udp headers must be built here */ pup->ud_dstp = TIMESOCK; /* they're byteswapped in pkt */ udp_write (udpfd, outpkt, 0); #ifdef DEBUG in_logpkt (outpkt,sizeof(struct udp),OUTPKT); #endif } res.r_time = 0L; if ((rcvlen = udp_bread (udpfd, inpkt, INETLEN, TIMEOUT)) > 0) { pip = in_head(inpkt); pup = udp_head(pip); ptm = (unshort *)udp_data(pup); #ifdef DEBUG in_logpkt (inpkt,pup->ud_len,INPKT); #endif res.r_word[0] = short_to_net (*ptm++); /* byte swap */ res.r_word[1] = short_to_net (*ptm++); /* the sucker */ res.r_time -= MAGICFUDGE; /* cvt to 1970-based time */ } udp_close (udpfd); udp_free (outpkt); udp_free (inpkt); return (res.r_time); }