5 * Copyright (C) 2007-2014 Intel Corporation. All rights reserved.
7 * This program is free software; you can redistribute it and/or modify
8 * it under the terms of the GNU General Public License version 2 as
9 * published by the Free Software Foundation.
11 * This program is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 * GNU General Public License for more details.
16 * You should have received a copy of the GNU General Public License
17 * along with this program; if not, write to the Free Software
18 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
33 #include <sys/timex.h>
34 #include <sys/socket.h>
35 #include <netinet/in.h>
36 #include <netinet/ip.h>
37 #include <arpa/inet.h>
47 } __attribute__ ((packed));
52 } __attribute__ ((packed));
55 uint8_t flags; /* Mode, version and leap indicator */
56 uint8_t stratum; /* Stratum details */
57 int8_t poll; /* Maximum interval in log2 seconds */
58 int8_t precision; /* Clock precision in log2 seconds */
59 struct ntp_short rootdelay; /* Root delay */
60 struct ntp_short rootdisp; /* Root dispersion */
61 uint32_t refid; /* Reference ID */
62 struct ntp_time reftime; /* Reference timestamp */
63 struct ntp_time orgtime; /* Origin timestamp */
64 struct ntp_time rectime; /* Receive timestamp */
65 struct ntp_time xmttime; /* Transmit timestamp */
66 } __attribute__ ((packed));
68 #define OFFSET_1900_1970 2208988800UL /* 1970 - 1900 in seconds */
70 #define STEPTIME_MIN_OFFSET 0.4
72 #define LOGTOD(a) ((a) < 0 ? 1. / (1L << -(a)) : 1L << (int)(a))
73 #define NSEC_PER_SEC ((uint64_t)1000000000ULL)
75 #define ADJ_SETOFFSET 0x0100 /* add 'time' to current time */
78 #define NTP_SEND_TIMEOUT 2
79 #define NTP_SEND_RETRIES 3
81 #define NTP_FLAG_LI_SHIFT 6
82 #define NTP_FLAG_LI_MASK 0x3
83 #define NTP_FLAG_LI_NOWARNING 0x0
84 #define NTP_FLAG_LI_ADDSECOND 0x1
85 #define NTP_FLAG_LI_DELSECOND 0x2
86 #define NTP_FLAG_LI_NOTINSYNC 0x3
88 #define NTP_FLAG_VN_SHIFT 3
89 #define NTP_FLAG_VN_MASK 0x7
91 #define NTP_FLAG_MD_SHIFT 0
92 #define NTP_FLAG_MD_MASK 0x7
93 #define NTP_FLAG_MD_UNSPEC 0
94 #define NTP_FLAG_MD_ACTIVE 1
95 #define NTP_FLAG_MD_PASSIVE 2
96 #define NTP_FLAG_MD_CLIENT 3
97 #define NTP_FLAG_MD_SERVER 4
98 #define NTP_FLAG_MD_BROADCAST 5
99 #define NTP_FLAG_MD_CONTROL 6
100 #define NTP_FLAG_MD_PRIVATE 7
102 #define NTP_FLAG_VN_VER3 3
103 #define NTP_FLAG_VN_VER4 4
105 #define NTP_FLAGS_ENCODE(li, vn, md) ((uint8_t)( \
106 (((li) & NTP_FLAG_LI_MASK) << NTP_FLAG_LI_SHIFT) | \
107 (((vn) & NTP_FLAG_VN_MASK) << NTP_FLAG_VN_SHIFT) | \
108 (((md) & NTP_FLAG_MD_MASK) << NTP_FLAG_MD_SHIFT)))
110 #define NTP_FLAGS_LI_DECODE(flags) ((uint8_t)(((flags) >> NTP_FLAG_LI_SHIFT) & NTP_FLAG_LI_MASK))
111 #define NTP_FLAGS_VN_DECODE(flags) ((uint8_t)(((flags) >> NTP_FLAG_VN_SHIFT) & NTP_FLAG_VN_MASK))
112 #define NTP_FLAGS_MD_DECODE(flags) ((uint8_t)(((flags) >> NTP_FLAG_MD_SHIFT) & NTP_FLAG_MD_MASK))
114 #define NTP_PRECISION_S 0
115 #define NTP_PRECISION_DS -3
116 #define NTP_PRECISION_CS -6
117 #define NTP_PRECISION_MS -9
118 #define NTP_PRECISION_US -19
119 #define NTP_PRECISION_NS -29
121 static guint channel_watch = 0;
122 static struct timespec mtx_time;
123 static int transmit_fd = 0;
125 static char *timeserver = NULL;
126 static struct sockaddr_in6 timeserver_addr;
127 static gint poll_id = 0;
128 static gint timeout_id = 0;
129 static guint retries = 0;
131 static void send_packet(int fd, struct sockaddr *server, uint32_t timeout);
133 static void next_server(void)
140 __connman_timeserver_sync_next();
143 static gboolean send_timeout(gpointer user_data)
145 uint32_t timeout = GPOINTER_TO_UINT(user_data);
147 DBG("send timeout %u (retries %d)", timeout, retries);
149 if (retries++ == NTP_SEND_RETRIES)
152 send_packet(transmit_fd, (struct sockaddr *)×erver_addr, timeout << 1);
157 static void send_packet(int fd, struct sockaddr *server, uint32_t timeout)
160 struct timeval transmit_timeval;
164 char ipaddrstring[INET6_ADDRSTRLEN + 1];
167 * At some point, we could specify the actual system precision with:
169 * clock_getres(CLOCK_REALTIME, &ts);
170 * msg.precision = (int)log2(ts.tv_sec + (ts.tv_nsec * 1.0e-9));
172 memset(&msg, 0, sizeof(msg));
173 msg.flags = NTP_FLAGS_ENCODE(NTP_FLAG_LI_NOTINSYNC, NTP_FLAG_VN_VER4,
176 msg.precision = NTP_PRECISION_S;
178 if (server->sa_family == AF_INET) {
179 size = sizeof(struct sockaddr_in);
180 addr = (void *)&(((struct sockaddr_in *)×erver_addr)->sin_addr);
181 } else if (server->sa_family == AF_INET6) {
182 size = sizeof(struct sockaddr_in6);
183 addr = (void *)×erver_addr.sin6_addr;
185 connman_error("Family is neither ipv4 nor ipv6");
189 gettimeofday(&transmit_timeval, NULL);
190 clock_gettime(CLOCK_MONOTONIC, &mtx_time);
192 msg.xmttime.seconds = htonl(transmit_timeval.tv_sec + OFFSET_1900_1970);
193 msg.xmttime.fraction = htonl(transmit_timeval.tv_usec * 1000);
195 len = sendto(fd, &msg, sizeof(msg), MSG_DONTWAIT,
199 connman_error("Time request for server %s failed (%d/%s)",
200 inet_ntop(server->sa_family, addr, ipaddrstring, sizeof(ipaddrstring)),
201 errno, strerror(errno));
203 if (errno == ENETUNREACH)
204 __connman_timeserver_sync_next();
209 if (len != sizeof(msg)) {
210 connman_error("Broken time request for server %s",
211 inet_ntop(server->sa_family, addr, ipaddrstring, sizeof(ipaddrstring)));
216 * Add an exponential retry timeout to retry the existing
217 * request. After a set number of retries, we'll fallback to
218 * trying another server.
221 timeout_id = g_timeout_add_seconds(timeout, send_timeout,
222 GUINT_TO_POINTER(timeout));
225 static gboolean next_poll(gpointer user_data)
229 if (!timeserver || transmit_fd == 0)
232 send_packet(transmit_fd, (struct sockaddr *)×erver_addr, NTP_SEND_TIMEOUT);
237 static void reset_timeout(void)
239 if (timeout_id > 0) {
240 g_source_remove(timeout_id);
247 static void decode_msg(void *base, size_t len, struct timeval *tv,
248 struct timespec *mrx_time)
250 struct ntp_msg *msg = base;
251 double m_delta, org, rec, xmt, dst;
252 double delay, offset;
253 static guint transmit_delay;
254 struct timex tmx = {};
256 if (len < sizeof(*msg)) {
257 connman_error("Invalid response from time server");
262 connman_error("Invalid packet timestamp from time server");
266 DBG("flags : 0x%02x", msg->flags);
267 DBG("stratum : %u", msg->stratum);
268 DBG("poll : %f seconds (%d)",
269 LOGTOD(msg->poll), msg->poll);
270 DBG("precision : %f seconds (%d)",
271 LOGTOD(msg->precision), msg->precision);
272 DBG("root delay : %u seconds (fraction %u)",
273 msg->rootdelay.seconds, msg->rootdelay.fraction);
274 DBG("root disp. : %u seconds (fraction %u)",
275 msg->rootdisp.seconds, msg->rootdisp.fraction);
276 DBG("reference : 0x%04x", msg->refid);
279 /* RFC 4330 ch 8 Kiss-of-Death packet */
280 uint32_t code = ntohl(msg->refid);
282 connman_info("Skipping server %s KoD code %c%c%c%c",
283 timeserver, code >> 24, code >> 16 & 0xff,
284 code >> 8 & 0xff, code & 0xff);
289 transmit_delay = LOGTOD(msg->poll);
291 if (NTP_FLAGS_LI_DECODE(msg->flags) == NTP_FLAG_LI_NOTINSYNC) {
292 DBG("ignoring unsynchronized peer");
297 if (NTP_FLAGS_VN_DECODE(msg->flags) != NTP_FLAG_VN_VER4) {
298 if (NTP_FLAGS_VN_DECODE(msg->flags) == NTP_FLAG_VN_VER3) {
299 DBG("requested version %d, accepting version %d",
300 NTP_FLAG_VN_VER4, NTP_FLAGS_VN_DECODE(msg->flags));
302 DBG("unsupported version %d", NTP_FLAGS_VN_DECODE(msg->flags));
307 if (NTP_FLAGS_MD_DECODE(msg->flags) != NTP_FLAG_MD_SERVER) {
308 DBG("unsupported mode %d", NTP_FLAGS_MD_DECODE(msg->flags));
312 m_delta = mrx_time->tv_sec - mtx_time.tv_sec +
313 1.0e-9 * (mrx_time->tv_nsec - mtx_time.tv_nsec);
315 org = tv->tv_sec + (1.0e-6 * tv->tv_usec) - m_delta + OFFSET_1900_1970;
316 rec = ntohl(msg->rectime.seconds) +
317 ((double) ntohl(msg->rectime.fraction) / UINT_MAX);
318 xmt = ntohl(msg->xmttime.seconds) +
319 ((double) ntohl(msg->xmttime.fraction) / UINT_MAX);
320 dst = tv->tv_sec + (1.0e-6 * tv->tv_usec) + OFFSET_1900_1970;
322 DBG("org=%f rec=%f xmt=%f dst=%f", org, rec, xmt, dst);
324 offset = ((rec - org) + (xmt - dst)) / 2;
325 delay = (dst - org) - (xmt - rec);
327 DBG("offset=%f delay=%f", offset, delay);
329 /* Remove the timeout, as timeserver has responded */
334 * Now poll the server every transmit_delay seconds
335 * for time correction.
338 g_source_remove(poll_id);
340 DBG("Timeserver %s, next sync in %d seconds", timeserver, transmit_delay);
342 poll_id = g_timeout_add_seconds(transmit_delay, next_poll, NULL);
344 if (offset < STEPTIME_MIN_OFFSET && offset > -STEPTIME_MIN_OFFSET) {
345 tmx.modes = ADJ_STATUS | ADJ_NANO | ADJ_OFFSET | ADJ_TIMECONST | ADJ_MAXERROR | ADJ_ESTERROR;
346 tmx.status = STA_PLL;
347 tmx.offset = offset * NSEC_PER_SEC;
348 tmx.constant = msg->poll - 4;
352 connman_info("ntp: adjust (slew): %+.6f sec", offset);
354 tmx.modes = ADJ_STATUS | ADJ_NANO | ADJ_SETOFFSET | ADJ_MAXERROR | ADJ_ESTERROR;
356 /* ADJ_NANO uses nanoseconds in the microseconds field */
357 tmx.time.tv_sec = (long)offset;
358 tmx.time.tv_usec = (offset - tmx.time.tv_sec) * NSEC_PER_SEC;
362 /* the kernel expects -0.3s as {-1, 7000.000.000} */
363 if (tmx.time.tv_usec < 0) {
364 tmx.time.tv_sec -= 1;
365 tmx.time.tv_usec += NSEC_PER_SEC;
368 connman_info("ntp: adjust (jump): %+.6f sec", offset);
371 if (NTP_FLAGS_LI_DECODE(msg->flags) & NTP_FLAG_LI_ADDSECOND)
372 tmx.status |= STA_INS;
373 else if (NTP_FLAGS_LI_DECODE(msg->flags) & NTP_FLAG_LI_DELSECOND)
374 tmx.status |= STA_DEL;
376 if (adjtimex(&tmx) < 0) {
377 connman_error("Failed to adjust time");
381 DBG("interval/delta/delay/drift %fs/%+.3fs/%.3fs/%+ldppm",
382 LOGTOD(msg->poll), offset, delay, tmx.freq / 65536);
385 static gboolean received_data(GIOChannel *channel, GIOCondition condition,
388 unsigned char buf[128];
389 struct sockaddr_in6 sender_addr;
392 struct cmsghdr *cmsg;
394 struct timespec mrx_time;
402 if (condition & (G_IO_HUP | G_IO_ERR | G_IO_NVAL)) {
403 connman_error("Problem with timer server channel");
408 fd = g_io_channel_unix_get_fd(channel);
411 iov.iov_len = sizeof(buf);
413 memset(&msg, 0, sizeof(msg));
416 msg.msg_control = aux;
417 msg.msg_controllen = sizeof(aux);
418 msg.msg_name = &sender_addr;
419 msg.msg_namelen = sizeof(sender_addr);
421 len = recvmsg(fd, &msg, MSG_DONTWAIT);
425 if (sender_addr.sin6_family == AF_INET) {
427 addr_ptr = &((struct sockaddr_in *)×erver_addr)->sin_addr;
428 src_ptr = &((struct sockaddr_in *)&sender_addr)->sin_addr;
429 } else if (sender_addr.sin6_family == AF_INET6) {
431 addr_ptr = &((struct sockaddr_in6 *)×erver_addr)->sin6_addr;
432 src_ptr = &((struct sockaddr_in6 *)&sender_addr)->sin6_addr;
434 connman_error("Not a valid family type");
438 if(memcmp(addr_ptr, src_ptr, size) != 0)
442 clock_gettime(CLOCK_MONOTONIC, &mrx_time);
444 for (cmsg = CMSG_FIRSTHDR(&msg); cmsg; cmsg = CMSG_NXTHDR(&msg, cmsg)) {
445 if (cmsg->cmsg_level != SOL_SOCKET)
448 switch (cmsg->cmsg_type) {
450 tv = (struct timeval *) CMSG_DATA(cmsg);
455 decode_msg(iov.iov_base, iov.iov_len, tv, &mrx_time);
460 static void start_ntp(char *server)
463 struct addrinfo hint;
464 struct addrinfo *info;
465 struct sockaddr * addr;
466 struct sockaddr_in * in4addr;
467 struct sockaddr_in6 in6addr;
470 int tos = IPTOS_LOWDELAY, timestamp = 1;
476 memset(&hint, 0, sizeof(hint));
477 hint.ai_family = AF_UNSPEC;
478 hint.ai_socktype = SOCK_DGRAM;
479 hint.ai_flags = AI_NUMERICHOST | AI_PASSIVE;
480 ret = getaddrinfo(server, NULL, &hint, &info);
483 connman_error("cannot get server info");
487 family = info->ai_family;
489 memcpy(×erver_addr, info->ai_addr, info->ai_addrlen);
491 memset(&in6addr, 0, sizeof(in6addr));
493 if (family == AF_INET) {
494 ((struct sockaddr_in *)×erver_addr)->sin_port = htons(123);
495 in4addr = (struct sockaddr_in *)&in6addr;
496 in4addr->sin_family = family;
497 addr = (struct sockaddr *)in4addr;
498 size = sizeof(struct sockaddr_in);
499 } else if (family == AF_INET6) {
500 timeserver_addr.sin6_port = htons(123);
501 in6addr.sin6_family = family;
502 addr = (struct sockaddr *)&in6addr;
503 size = sizeof(in6addr);
505 connman_error("Family is neither ipv4 nor ipv6");
509 DBG("server %s family %d", server, family);
511 if (channel_watch > 0)
514 transmit_fd = socket(family, SOCK_DGRAM | SOCK_CLOEXEC, 0);
516 if (transmit_fd <= 0) {
517 connman_error("Failed to open time server socket");
521 if (bind(transmit_fd, (struct sockaddr *) addr, size) < 0) {
522 connman_error("Failed to bind time server socket");
527 if (family == AF_INET) {
528 if (setsockopt(transmit_fd, IPPROTO_IP, IP_TOS, &tos, sizeof(tos)) < 0) {
529 connman_error("Failed to set type of service option");
535 if (setsockopt(transmit_fd, SOL_SOCKET, SO_TIMESTAMP, ×tamp,
536 sizeof(timestamp)) < 0) {
537 connman_error("Failed to enable timestamp support");
542 channel = g_io_channel_unix_new(transmit_fd);
548 g_io_channel_set_encoding(channel, NULL, NULL);
549 g_io_channel_set_buffered(channel, FALSE);
551 g_io_channel_set_close_on_unref(channel, TRUE);
553 channel_watch = g_io_add_watch_full(channel, G_PRIORITY_DEFAULT,
554 G_IO_IN | G_IO_HUP | G_IO_ERR | G_IO_NVAL,
555 received_data, NULL, NULL);
557 g_io_channel_unref(channel);
560 send_packet(transmit_fd, (struct sockaddr*)×erver_addr, NTP_SEND_TIMEOUT);
563 int __connman_ntp_start(char *server)
573 timeserver = g_strdup(server);
575 start_ntp(timeserver);
580 void __connman_ntp_stop()
585 g_source_remove(poll_id);
591 if (channel_watch > 0) {
592 g_source_remove(channel_watch);