static int ntp_init(void) { int ret = gettime(); if (ret) return ret; peer_clear(&peer); return NTP_OK; }
/* * clear_all - flush all time values for all associations */ void clear_all(void) { struct peer *peer, *next_peer; int n; /* * This routine is called when the clock is stepped, and so all * previously saved time values are untrusted. */ for (n = 0; n < NTP_HASH_SIZE; n++) { for (peer = peer_hash[n]; peer != 0; peer = next_peer) { next_peer = peer->next; if (!(peer->cast_flags & (MDF_ACAST | MDF_MCAST | MDF_BCAST))) { peer->hpoll = peer->minpoll; peer_clear(peer, "STEP"); } } } #ifdef DEBUG if (debug) printf("clear_all: at %lu\n", current_time); #endif }
static int clock_adjust(struct p *p) { int i; int ret = NTP_OK; double old; double offset; struct timex tx; dprint("clock_adjust: p->offset:%f\n", p->offset); if (p->offset < CLOCK_MAX) { memset(&tx, 0, sizeof(tx)); tx.modes = ADJ_OFFSET_SINGLESHOT; ret = get_old_offset(&old); if (ret) return ret; offset = p->offset + old; tx.offset = (long)(offset * USEC_IN_SEC); if (adjtimex(&tx) < 0) return NTP_ERR_SYS; for (i = 0; i < NSTAGE; i++) if (p->f[i].t > p->t && p->f[i].disp < MAXDISPERSE) p->f[i].offset -= p->offset; ret = freq_adjust(p); dprint("clock_adjust: freq_adjust_ret:%i\n", ret); } else { ret = movetime(p->offset); offset = p->offset; peer_clear(p); if (ret) return ret; } p->effective_offset = offset; return ret; }
static int l_set_peer(lua_State *L) { double value; luaL_argcheck(L, lua_istable(L, 1), 1, "table expected"); peer_clear(&peer); lua_getfield(L, 1, "poll"); value = luaL_checknumber(L, -1); lua_pop(L, 1); peer.poll = (long)value; return 0; }
/* * clear_all - flush all time values for all associations */ void clear_all(void) { struct peer *p; /* * This routine is called when the clock is stepped, and so all * previously saved time values are untrusted. */ for (p = peer_list; p != NULL; p = p->p_link) if (!(MDF_TXONLY_MASK & p->cast_flags)) peer_clear(p, "STEP"); DPRINTF(1, ("clear_all: at %lu\n", current_time)); }
static int l_clock_update(lua_State *L) { double t[4]; if (lua_gettop(L) < 1) return ntp_pushresult(L, ntp_process(&peer, 0, 0)); else if (lua_gettop(L) < 4) { int ret; t[0] = luaL_checknumber(L, 1); ret = settime(t[0]); if (ret) return ntp_pushresult(L, ret); peer_clear(&peer); return ntp_pushresult(L, NTP_OK); } t[0] = luaL_checknumber(L, 1); t[1] = luaL_checknumber(L, 2); t[2] = luaL_checknumber(L, 3); t[3] = luaL_checknumber(L, 4); return ntp_pushresult(L, ntp_process(&peer, t, 0)); }
/* * peer_config - configure a new association */ struct peer * peer_config( struct sockaddr_storage *srcadr, struct interface *dstadr, int hmode, int version, int minpoll, int maxpoll, u_int flags, int ttl, keyid_t key, u_char *keystr ) { register struct peer *peer; u_char cast_flags; /* * First search from the beginning for an association with given * remote address and mode. If an interface is given, search * from there to find the association which matches that * destination. If the given interface is "any", track down * the actual interface, because that's what gets put into the * peer structure. */ peer = findexistingpeer(srcadr, (struct peer *)0, hmode); if (dstadr != 0) { while (peer != 0) { if (peer->dstadr == dstadr) break; if (dstadr == ANY_INTERFACE_CHOOSE(srcadr) && peer->dstadr == findinterface(srcadr)) break; peer = findexistingpeer(srcadr, peer, hmode); } } /* * We do a dirty little jig to figure the cast flags. This is * probably not the best place to do this, at least until the * configure code is rebuilt. Note only one flag can be set. */ switch (hmode) { case MODE_BROADCAST: if(srcadr->ss_family == AF_INET) { if (IN_CLASSD(ntohl(((struct sockaddr_in*)srcadr)->sin_addr.s_addr))) cast_flags = MDF_MCAST; else cast_flags = MDF_BCAST; break; } else { if (IN6_IS_ADDR_MULTICAST(&((struct sockaddr_in6*)srcadr)->sin6_addr)) cast_flags = MDF_MCAST; else cast_flags = MDF_BCAST; break; } case MODE_CLIENT: if(srcadr->ss_family == AF_INET) { if (IN_CLASSD(ntohl(((struct sockaddr_in*)srcadr)->sin_addr.s_addr))) cast_flags = MDF_ACAST; else cast_flags = MDF_UCAST; break; } else { if (IN6_IS_ADDR_MULTICAST(&((struct sockaddr_in6*)srcadr)->sin6_addr)) cast_flags = MDF_ACAST; else cast_flags = MDF_UCAST; break; } default: cast_flags = MDF_UCAST; } /* * If the peer is already configured, some dope has a duplicate * configureation entry or another dope is wiggling from afar. */ if (peer != 0) { peer->hmode = (u_char)hmode; peer->version = (u_char) version; peer->minpoll = (u_char) minpoll; peer->maxpoll = (u_char) maxpoll; peer->flags = flags | FLAG_CONFIG | (peer->flags & FLAG_REFCLOCK); peer->cast_flags = cast_flags; peer->ttl = (u_char) ttl; peer->keyid = key; peer->precision = sys_precision; peer_clear(peer, "RMOT"); return (peer); } /* * Here no match has been found, so presumably this is a new * persistent association. Mobilize the thing and initialize its * variables. If emulating ntpdate, force iburst. */ if (mode_ntpdate) flags |= FLAG_IBURST; peer = newpeer(srcadr, dstadr, hmode, version, minpoll, maxpoll, flags | FLAG_CONFIG, cast_flags, ttl, key); return (peer); }
/* * refclock_transmit - simulate the transmit procedure * * This routine implements the NTP transmit procedure for a reference * clock. This provides a mechanism to call the driver at the NTP poll * interval, as well as provides a reachability mechanism to detect a * broken radio or other madness. */ void refclock_transmit( struct peer *peer /* peer structure pointer */ ) { u_char clktype; int unit; int hpoll; u_long next; clktype = peer->refclktype; unit = peer->refclkunit; peer->sent++; /* * This is a ripoff of the peer transmit routine, but * specialized for reference clocks. We do a little less * protocol here and call the driver-specific transmit routine. */ hpoll = peer->hpoll; next = peer->outdate; if (peer->burst == 0) { u_char oreach; #ifdef DEBUG if (debug) printf("refclock_transmit: at %ld %s\n", current_time, ntoa(&(peer->srcadr))); #endif /* * Update reachability and poll variables like the * network code. */ oreach = peer->reach; peer->reach <<= 1; if (!peer->reach) { if (oreach) { report_event(EVNT_UNREACH, peer); peer->timereachable = current_time; peer_clear(peer); } } else { if (!(oreach & 0x03)) { clock_filter(peer, 0., 0., MAXDISPERSE); clock_select(); } if (!(oreach & 0x0f)) { hpoll--; } else if ((oreach & 0x0f) == 0x0f) hpoll++; if (peer->flags & FLAG_BURST) peer->burst = NSTAGE; } next = current_time; } get_systime(&peer->xmt); if (refclock_conf[clktype]->clock_poll != noentry) (refclock_conf[clktype]->clock_poll)(unit, peer); peer->outdate = next; if (peer->burst > 0) peer->burst--; poll_update(peer, hpoll); }