No empty .Rs/.Re
[netbsd-mini2440.git] / usr.sbin / rdate / rdate.c
blob36811598142694c02e1f71e8bc3df419c3a60d75
1 /* $NetBSD: rdate.c,v 1.18 2009/03/10 00:26:20 jakllsch Exp $ */
3 /*
4 * Copyright (c) 1994 Christos Zoulas
5 * All rights reserved.
7 * Redistribution and use in source and binary forms, with or without
8 * modification, are permitted provided that the following conditions
9 * are met:
10 * 1. Redistributions of source code must retain the above copyright
11 * notice, this list of conditions and the following disclaimer.
12 * 2. Redistributions in binary form must reproduce the above copyright
13 * notice, this list of conditions and the following disclaimer in the
14 * documentation and/or other materials provided with the distribution.
16 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
17 * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
18 * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
19 * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
20 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
21 * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
22 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
23 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
24 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
25 * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
29 * rdate.c: Set the date from the specified host
31 * Uses the rfc868 time protocol at socket 37.
32 * Time is returned as the number of seconds since
33 * midnight January 1st 1900.
35 #include <sys/cdefs.h>
36 #ifndef lint
37 __RCSID("$NetBSD: rdate.c,v 1.18 2009/03/10 00:26:20 jakllsch Exp $");
38 #endif /* lint */
40 #include <sys/types.h>
41 #include <sys/socket.h>
42 #include <sys/time.h>
44 #include <netinet/in.h>
46 #include <err.h>
47 #include <netdb.h>
48 #include <stdio.h>
49 #include <stdlib.h>
50 #include <string.h>
51 #include <unistd.h>
52 #include <util.h>
54 /* seconds from midnight Jan 1900 - 1970 */
55 #define DIFFERENCE 2208988800ULL
57 int main(int, char **);
58 static void usage(void);
60 static void
61 usage(void)
63 (void) fprintf(stderr, "usage: %s [-psa] host\n", getprogname());
64 (void) fprintf(stderr, " -p: just print, don't set\n");
65 (void) fprintf(stderr, " -s: just set, don't print\n");
66 (void) fprintf(stderr, " -a: use adjtime instead of instant change\n");
69 int
70 main(int argc, char *argv[])
72 int pr = 0, silent = 0, s;
73 int slidetime = 0;
74 int adjustment;
75 uint32_t data;
76 time_t tim;
77 char *hname;
78 const char *emsg = NULL;
79 struct addrinfo hints, *res, *res0;
80 int c;
81 int error;
83 adjustment = 0;
84 while ((c = getopt(argc, argv, "psa")) != -1)
85 switch (c) {
86 case 'p':
87 pr++;
88 break;
90 case 's':
91 silent++;
92 break;
94 case 'a':
95 slidetime++;
96 break;
98 default:
99 usage();
100 return 1;
103 if (argc - 1 != optind) {
104 usage();
105 return 1;
107 hname = argv[optind];
109 memset(&hints, 0, sizeof (hints));
110 hints.ai_family = PF_UNSPEC;
111 hints.ai_socktype = SOCK_STREAM;
112 hints.ai_flags = AI_CANONNAME;
113 error = getaddrinfo(hname, "time", &hints, &res0);
114 if (error)
115 errx(1, "%s: %s", gai_strerror(error), hname);
117 for (res = res0, s = -1; res != NULL; res = res->ai_next) {
118 s = socket(res->ai_family, res->ai_socktype, res->ai_protocol);
119 if (s < 0) {
120 emsg = "socket";
121 continue;
124 if (connect(s, res->ai_addr, res->ai_addrlen)) {
125 close(s);
126 s = -1;
127 emsg = "connect";
128 continue;
131 break;
133 if (s < 0)
134 err(1, "%s", emsg);
136 if (read(s, &data, sizeof(uint32_t)) != sizeof(uint32_t))
137 err(1, "Could not read data");
139 (void) close(s);
140 tim = ntohl(data) - DIFFERENCE;
142 if (!pr) {
143 struct timeval tv;
144 if (!slidetime) {
145 logwtmp("|", "date", "");
146 tv.tv_sec = tim;
147 tv.tv_usec = 0;
148 if (settimeofday(&tv, NULL) == -1)
149 err(1, "Could not set time of day");
150 logwtmp("{", "date", "");
151 } else {
152 struct timeval tv_current;
153 if (gettimeofday(&tv_current, NULL) == -1)
154 err(1, "Could not get local time of day");
155 adjustment = tv.tv_sec = tim - tv_current.tv_sec;
156 tv.tv_usec = 0;
157 if (adjtime(&tv, NULL) == -1)
158 err(1, "Could not adjust time of day");
162 if (!silent) {
163 (void) fputs(ctime(&tim), stdout);
164 if (slidetime)
165 (void) fprintf(stdout,
166 "%s: adjust local clock by %d seconds\n",
167 getprogname(), adjustment);
169 return 0;