xref: /freebsd/contrib/dma/util.c (revision b86d1398)
1a9e8641dSBaptiste Daroussin /*
2e56bad4aSBaptiste Daroussin  * Copyright (c) 2008-2014, Simon Schubert <2@0x2c.org>.
3a9e8641dSBaptiste Daroussin  * Copyright (c) 2008 The DragonFly Project.  All rights reserved.
4a9e8641dSBaptiste Daroussin  *
5a9e8641dSBaptiste Daroussin  * This code is derived from software contributed to The DragonFly Project
6e56bad4aSBaptiste Daroussin  * by Simon Schubert <2@0x2c.org>.
7a9e8641dSBaptiste Daroussin  *
8a9e8641dSBaptiste Daroussin  * Redistribution and use in source and binary forms, with or without
9a9e8641dSBaptiste Daroussin  * modification, are permitted provided that the following conditions
10a9e8641dSBaptiste Daroussin  * are met:
11a9e8641dSBaptiste Daroussin  *
12a9e8641dSBaptiste Daroussin  * 1. Redistributions of source code must retain the above copyright
13a9e8641dSBaptiste Daroussin  *    notice, this list of conditions and the following disclaimer.
14a9e8641dSBaptiste Daroussin  * 2. Redistributions in binary form must reproduce the above copyright
15a9e8641dSBaptiste Daroussin  *    notice, this list of conditions and the following disclaimer in
16a9e8641dSBaptiste Daroussin  *    the documentation and/or other materials provided with the
17a9e8641dSBaptiste Daroussin  *    distribution.
18a9e8641dSBaptiste Daroussin  * 3. Neither the name of The DragonFly Project nor the names of its
19a9e8641dSBaptiste Daroussin  *    contributors may be used to endorse or promote products derived
20a9e8641dSBaptiste Daroussin  *    from this software without specific, prior written permission.
21a9e8641dSBaptiste Daroussin  *
22a9e8641dSBaptiste Daroussin  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
23a9e8641dSBaptiste Daroussin  * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
24a9e8641dSBaptiste Daroussin  * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
25a9e8641dSBaptiste Daroussin  * FOR A PARTICULAR PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE
26a9e8641dSBaptiste Daroussin  * COPYRIGHT HOLDERS OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
27a9e8641dSBaptiste Daroussin  * INCIDENTAL, SPECIAL, EXEMPLARY OR CONSEQUENTIAL DAMAGES (INCLUDING,
28a9e8641dSBaptiste Daroussin  * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
29a9e8641dSBaptiste Daroussin  * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED
30a9e8641dSBaptiste Daroussin  * AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
31a9e8641dSBaptiste Daroussin  * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT
32a9e8641dSBaptiste Daroussin  * OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
33a9e8641dSBaptiste Daroussin  * SUCH DAMAGE.
34a9e8641dSBaptiste Daroussin  */
35a9e8641dSBaptiste Daroussin 
36a9e8641dSBaptiste Daroussin #include <sys/param.h>
37a9e8641dSBaptiste Daroussin #include <sys/file.h>
38a9e8641dSBaptiste Daroussin 
39a9e8641dSBaptiste Daroussin #include <ctype.h>
40a9e8641dSBaptiste Daroussin #include <errno.h>
41a9e8641dSBaptiste Daroussin #include <fcntl.h>
42a9e8641dSBaptiste Daroussin #include <netdb.h>
43a9e8641dSBaptiste Daroussin #include <pwd.h>
44a9e8641dSBaptiste Daroussin #include <setjmp.h>
45a9e8641dSBaptiste Daroussin #include <signal.h>
46a9e8641dSBaptiste Daroussin #include <stdio.h>
47b86d1398SJung-uk Kim #include <strings.h>
48a9e8641dSBaptiste Daroussin #include <string.h>
49a9e8641dSBaptiste Daroussin #include <syslog.h>
50a9e8641dSBaptiste Daroussin #include <unistd.h>
51a9e8641dSBaptiste Daroussin 
52a9e8641dSBaptiste Daroussin #include "dma.h"
53a9e8641dSBaptiste Daroussin 
54a9e8641dSBaptiste Daroussin const char *
hostname(void)55a9e8641dSBaptiste Daroussin hostname(void)
56a9e8641dSBaptiste Daroussin {
57a9e8641dSBaptiste Daroussin #ifndef HOST_NAME_MAX
58a9e8641dSBaptiste Daroussin #define HOST_NAME_MAX	255
59a9e8641dSBaptiste Daroussin #endif
60a9e8641dSBaptiste Daroussin 	static char name[HOST_NAME_MAX+1];
61a9e8641dSBaptiste Daroussin 	static int initialized = 0;
62a9e8641dSBaptiste Daroussin 	char *s;
63a9e8641dSBaptiste Daroussin 
64a9e8641dSBaptiste Daroussin 	if (initialized)
65a9e8641dSBaptiste Daroussin 		return (name);
66a9e8641dSBaptiste Daroussin 
67a9e8641dSBaptiste Daroussin 	if (config.mailname == NULL || !*config.mailname)
68a9e8641dSBaptiste Daroussin 		goto local;
69a9e8641dSBaptiste Daroussin 
70a9e8641dSBaptiste Daroussin 	if (config.mailname[0] == '/') {
71a9e8641dSBaptiste Daroussin 		/*
72a9e8641dSBaptiste Daroussin 		 * If the mailname looks like an absolute path,
73a9e8641dSBaptiste Daroussin 		 * treat it as a file.
74a9e8641dSBaptiste Daroussin 		 */
75a9e8641dSBaptiste Daroussin 		FILE *fp;
76a9e8641dSBaptiste Daroussin 
77a9e8641dSBaptiste Daroussin 		fp = fopen(config.mailname, "r");
78a9e8641dSBaptiste Daroussin 		if (fp == NULL)
79a9e8641dSBaptiste Daroussin 			goto local;
80a9e8641dSBaptiste Daroussin 
81a9e8641dSBaptiste Daroussin 		s = fgets(name, sizeof(name), fp);
82a9e8641dSBaptiste Daroussin 		fclose(fp);
83a9e8641dSBaptiste Daroussin 		if (s == NULL)
84a9e8641dSBaptiste Daroussin 			goto local;
85a9e8641dSBaptiste Daroussin 
86a9e8641dSBaptiste Daroussin 		for (s = name; *s != 0 && (isalnum(*s) || strchr("_.-", *s)); ++s)
87a9e8641dSBaptiste Daroussin 			/* NOTHING */;
88a9e8641dSBaptiste Daroussin 		*s = 0;
89a9e8641dSBaptiste Daroussin 
90a9e8641dSBaptiste Daroussin 		if (!*name)
91a9e8641dSBaptiste Daroussin 			goto local;
92a9e8641dSBaptiste Daroussin 
93a9e8641dSBaptiste Daroussin 		initialized = 1;
94a9e8641dSBaptiste Daroussin 		return (name);
95a9e8641dSBaptiste Daroussin 	} else {
96a9e8641dSBaptiste Daroussin 		snprintf(name, sizeof(name), "%s", config.mailname);
97a9e8641dSBaptiste Daroussin 		initialized = 1;
98a9e8641dSBaptiste Daroussin 		return (name);
99a9e8641dSBaptiste Daroussin 	}
100a9e8641dSBaptiste Daroussin 
101a9e8641dSBaptiste Daroussin local:
102a9e8641dSBaptiste Daroussin 	snprintf(name, sizeof(name), "%s", systemhostname());
103a9e8641dSBaptiste Daroussin 
104a9e8641dSBaptiste Daroussin 	initialized = 1;
105a9e8641dSBaptiste Daroussin 	return (name);
106a9e8641dSBaptiste Daroussin }
107a9e8641dSBaptiste Daroussin 
108a9e8641dSBaptiste Daroussin const char *
systemhostname(void)109a9e8641dSBaptiste Daroussin systemhostname(void)
110a9e8641dSBaptiste Daroussin {
111a9e8641dSBaptiste Daroussin #ifndef HOST_NAME_MAX
112a9e8641dSBaptiste Daroussin #define HOST_NAME_MAX	255
113a9e8641dSBaptiste Daroussin #endif
114a9e8641dSBaptiste Daroussin 	static char name[HOST_NAME_MAX+1];
115a9e8641dSBaptiste Daroussin 	static int initialized = 0;
116a9e8641dSBaptiste Daroussin 	char *s;
117a9e8641dSBaptiste Daroussin 
118a9e8641dSBaptiste Daroussin 	if (initialized)
119a9e8641dSBaptiste Daroussin 		return (name);
120a9e8641dSBaptiste Daroussin 
121a9e8641dSBaptiste Daroussin 	if (gethostname(name, sizeof(name)) != 0)
122a9e8641dSBaptiste Daroussin 		*name = 0;
123a9e8641dSBaptiste Daroussin 	/*
124a9e8641dSBaptiste Daroussin 	 * gethostname() is allowed to truncate name without NUL-termination
125a9e8641dSBaptiste Daroussin 	 * and at the same time not return an error.
126a9e8641dSBaptiste Daroussin 	 */
127a9e8641dSBaptiste Daroussin 	name[sizeof(name) - 1] = 0;
128a9e8641dSBaptiste Daroussin 
129a9e8641dSBaptiste Daroussin 	for (s = name; *s != 0 && (isalnum(*s) || strchr("_.-", *s)); ++s)
130a9e8641dSBaptiste Daroussin 		/* NOTHING */;
131a9e8641dSBaptiste Daroussin 	*s = 0;
132a9e8641dSBaptiste Daroussin 
133a9e8641dSBaptiste Daroussin 	if (!*name)
134a9e8641dSBaptiste Daroussin 		snprintf(name, sizeof(name), "unknown-hostname");
135a9e8641dSBaptiste Daroussin 
136a9e8641dSBaptiste Daroussin 	initialized = 1;
137a9e8641dSBaptiste Daroussin 	return (name);
138a9e8641dSBaptiste Daroussin }
139a9e8641dSBaptiste Daroussin 
140a9e8641dSBaptiste Daroussin void
setlogident(const char * fmt,...)141a9e8641dSBaptiste Daroussin setlogident(const char *fmt, ...)
142a9e8641dSBaptiste Daroussin {
143a9e8641dSBaptiste Daroussin 	static char tag[50];
144a9e8641dSBaptiste Daroussin 
145a9e8641dSBaptiste Daroussin 	snprintf(tag, sizeof(tag), "%s", logident_base);
146a9e8641dSBaptiste Daroussin 	if (fmt != NULL) {
147a9e8641dSBaptiste Daroussin 		va_list ap;
148a9e8641dSBaptiste Daroussin 		char sufx[50];
149a9e8641dSBaptiste Daroussin 
150a9e8641dSBaptiste Daroussin 		va_start(ap, fmt);
151a9e8641dSBaptiste Daroussin 		vsnprintf(sufx, sizeof(sufx), fmt, ap);
152a9e8641dSBaptiste Daroussin 		va_end(ap);
153a9e8641dSBaptiste Daroussin 		snprintf(tag, sizeof(tag), "%s[%s]", logident_base, sufx);
154a9e8641dSBaptiste Daroussin 	}
155a9e8641dSBaptiste Daroussin 	closelog();
156a9e8641dSBaptiste Daroussin 	openlog(tag, 0, LOG_MAIL);
157a9e8641dSBaptiste Daroussin }
158a9e8641dSBaptiste Daroussin 
159a9e8641dSBaptiste Daroussin void
errlog(int exitcode,const char * fmt,...)160a9e8641dSBaptiste Daroussin errlog(int exitcode, const char *fmt, ...)
161a9e8641dSBaptiste Daroussin {
162a9e8641dSBaptiste Daroussin 	int oerrno = errno;
163a9e8641dSBaptiste Daroussin 	va_list ap;
164a9e8641dSBaptiste Daroussin 	char outs[ERRMSG_SIZE];
165a9e8641dSBaptiste Daroussin 
166a9e8641dSBaptiste Daroussin 	outs[0] = 0;
167a9e8641dSBaptiste Daroussin 	if (fmt != NULL) {
168a9e8641dSBaptiste Daroussin 		va_start(ap, fmt);
169a9e8641dSBaptiste Daroussin 		vsnprintf(outs, sizeof(outs), fmt, ap);
170a9e8641dSBaptiste Daroussin 		va_end(ap);
171a9e8641dSBaptiste Daroussin 	}
172a9e8641dSBaptiste Daroussin 
173a9e8641dSBaptiste Daroussin 	errno = oerrno;
174a9e8641dSBaptiste Daroussin 	if (*outs != 0) {
175a9e8641dSBaptiste Daroussin 		syslog(LOG_ERR, "%s: %m", outs);
176a9e8641dSBaptiste Daroussin 		fprintf(stderr, "%s: %s: %s\n", getprogname(), outs, strerror(oerrno));
177a9e8641dSBaptiste Daroussin 	} else {
178a9e8641dSBaptiste Daroussin 		syslog(LOG_ERR, "%m");
179a9e8641dSBaptiste Daroussin 		fprintf(stderr, "%s: %s\n", getprogname(), strerror(oerrno));
180a9e8641dSBaptiste Daroussin 	}
181a9e8641dSBaptiste Daroussin 
182a9e8641dSBaptiste Daroussin 	exit(exitcode);
183a9e8641dSBaptiste Daroussin }
184a9e8641dSBaptiste Daroussin 
185a9e8641dSBaptiste Daroussin void
errlogx(int exitcode,const char * fmt,...)186a9e8641dSBaptiste Daroussin errlogx(int exitcode, const char *fmt, ...)
187a9e8641dSBaptiste Daroussin {
188a9e8641dSBaptiste Daroussin 	va_list ap;
189a9e8641dSBaptiste Daroussin 	char outs[ERRMSG_SIZE];
190a9e8641dSBaptiste Daroussin 
191a9e8641dSBaptiste Daroussin 	outs[0] = 0;
192a9e8641dSBaptiste Daroussin 	if (fmt != NULL) {
193a9e8641dSBaptiste Daroussin 		va_start(ap, fmt);
194a9e8641dSBaptiste Daroussin 		vsnprintf(outs, sizeof(outs), fmt, ap);
195a9e8641dSBaptiste Daroussin 		va_end(ap);
196a9e8641dSBaptiste Daroussin 	}
197a9e8641dSBaptiste Daroussin 
198a9e8641dSBaptiste Daroussin 	if (*outs != 0) {
199a9e8641dSBaptiste Daroussin 		syslog(LOG_ERR, "%s", outs);
200a9e8641dSBaptiste Daroussin 		fprintf(stderr, "%s: %s\n", getprogname(), outs);
201a9e8641dSBaptiste Daroussin 	} else {
202a9e8641dSBaptiste Daroussin 		syslog(LOG_ERR, "Unknown error");
203a9e8641dSBaptiste Daroussin 		fprintf(stderr, "%s: Unknown error\n", getprogname());
204a9e8641dSBaptiste Daroussin 	}
205a9e8641dSBaptiste Daroussin 
206a9e8641dSBaptiste Daroussin 	exit(exitcode);
207a9e8641dSBaptiste Daroussin }
208a9e8641dSBaptiste Daroussin 
209a9e8641dSBaptiste Daroussin static int
check_username(const char * name,uid_t ckuid)210a9e8641dSBaptiste Daroussin check_username(const char *name, uid_t ckuid)
211a9e8641dSBaptiste Daroussin {
212a9e8641dSBaptiste Daroussin 	struct passwd *pwd;
213a9e8641dSBaptiste Daroussin 
214a9e8641dSBaptiste Daroussin 	if (name == NULL)
215a9e8641dSBaptiste Daroussin 		return (0);
216a9e8641dSBaptiste Daroussin 	pwd = getpwnam(name);
217a9e8641dSBaptiste Daroussin 	if (pwd == NULL || pwd->pw_uid != ckuid)
218a9e8641dSBaptiste Daroussin 		return (0);
219a9e8641dSBaptiste Daroussin 	snprintf(username, sizeof(username), "%s", name);
220a9e8641dSBaptiste Daroussin 	return (1);
221a9e8641dSBaptiste Daroussin }
222a9e8641dSBaptiste Daroussin 
223a9e8641dSBaptiste Daroussin void
set_username(void)224a9e8641dSBaptiste Daroussin set_username(void)
225a9e8641dSBaptiste Daroussin {
226a9e8641dSBaptiste Daroussin 	struct passwd *pwd;
227a9e8641dSBaptiste Daroussin 
228a9e8641dSBaptiste Daroussin 	useruid = getuid();
229a9e8641dSBaptiste Daroussin 	if (check_username(getlogin(), useruid))
230a9e8641dSBaptiste Daroussin 		return;
231a9e8641dSBaptiste Daroussin 	if (check_username(getenv("LOGNAME"), useruid))
232a9e8641dSBaptiste Daroussin 		return;
233a9e8641dSBaptiste Daroussin 	if (check_username(getenv("USER"), useruid))
234a9e8641dSBaptiste Daroussin 		return;
235a9e8641dSBaptiste Daroussin 	pwd = getpwuid(useruid);
236a9e8641dSBaptiste Daroussin 	if (pwd != NULL && pwd->pw_name != NULL && pwd->pw_name[0] != '\0') {
237a9e8641dSBaptiste Daroussin 		if (check_username(pwd->pw_name, useruid))
238a9e8641dSBaptiste Daroussin 			return;
239a9e8641dSBaptiste Daroussin 	}
240a9e8641dSBaptiste Daroussin 	snprintf(username, sizeof(username), "uid=%ld", (long)useruid);
241a9e8641dSBaptiste Daroussin }
242a9e8641dSBaptiste Daroussin 
243a9e8641dSBaptiste Daroussin void
deltmp(void)244a9e8641dSBaptiste Daroussin deltmp(void)
245a9e8641dSBaptiste Daroussin {
246a9e8641dSBaptiste Daroussin 	struct stritem *t;
247a9e8641dSBaptiste Daroussin 
248a9e8641dSBaptiste Daroussin 	SLIST_FOREACH(t, &tmpfs, next) {
249a9e8641dSBaptiste Daroussin 		unlink(t->str);
250a9e8641dSBaptiste Daroussin 	}
251a9e8641dSBaptiste Daroussin }
252a9e8641dSBaptiste Daroussin 
253a9e8641dSBaptiste Daroussin static sigjmp_buf sigbuf;
254a9e8641dSBaptiste Daroussin static int sigbuf_valid;
255a9e8641dSBaptiste Daroussin 
256a9e8641dSBaptiste Daroussin static void
sigalrm_handler(int signo)257a9e8641dSBaptiste Daroussin sigalrm_handler(int signo)
258a9e8641dSBaptiste Daroussin {
259a9e8641dSBaptiste Daroussin 	(void)signo;	/* so that gcc doesn't complain */
260a9e8641dSBaptiste Daroussin 	if (sigbuf_valid)
261a9e8641dSBaptiste Daroussin 		siglongjmp(sigbuf, 1);
262a9e8641dSBaptiste Daroussin }
263a9e8641dSBaptiste Daroussin 
264a9e8641dSBaptiste Daroussin int
do_timeout(int timeout,int dojmp)265a9e8641dSBaptiste Daroussin do_timeout(int timeout, int dojmp)
266a9e8641dSBaptiste Daroussin {
267a9e8641dSBaptiste Daroussin 	struct sigaction act;
268a9e8641dSBaptiste Daroussin 	int ret = 0;
269a9e8641dSBaptiste Daroussin 
270a9e8641dSBaptiste Daroussin 	sigemptyset(&act.sa_mask);
271a9e8641dSBaptiste Daroussin 	act.sa_flags = 0;
272a9e8641dSBaptiste Daroussin 
273a9e8641dSBaptiste Daroussin 	if (timeout) {
274a9e8641dSBaptiste Daroussin 		act.sa_handler = sigalrm_handler;
275a9e8641dSBaptiste Daroussin 		if (sigaction(SIGALRM, &act, NULL) != 0)
276a9e8641dSBaptiste Daroussin 			syslog(LOG_WARNING, "can not set signal handler: %m");
277a9e8641dSBaptiste Daroussin 		if (dojmp) {
278a9e8641dSBaptiste Daroussin 			ret = sigsetjmp(sigbuf, 1);
279a9e8641dSBaptiste Daroussin 			if (ret)
280a9e8641dSBaptiste Daroussin 				goto disable;
281a9e8641dSBaptiste Daroussin 			/* else just programmed */
282a9e8641dSBaptiste Daroussin 			sigbuf_valid = 1;
283a9e8641dSBaptiste Daroussin 		}
284a9e8641dSBaptiste Daroussin 
285a9e8641dSBaptiste Daroussin 		alarm(timeout);
286a9e8641dSBaptiste Daroussin 	} else {
287a9e8641dSBaptiste Daroussin disable:
288a9e8641dSBaptiste Daroussin 		alarm(0);
289a9e8641dSBaptiste Daroussin 
290a9e8641dSBaptiste Daroussin 		act.sa_handler = SIG_IGN;
291a9e8641dSBaptiste Daroussin 		if (sigaction(SIGALRM, &act, NULL) != 0)
292a9e8641dSBaptiste Daroussin 			syslog(LOG_WARNING, "can not remove signal handler: %m");
293a9e8641dSBaptiste Daroussin 		sigbuf_valid = 0;
294a9e8641dSBaptiste Daroussin 	}
295a9e8641dSBaptiste Daroussin 
296a9e8641dSBaptiste Daroussin 	return (ret);
297a9e8641dSBaptiste Daroussin }
298a9e8641dSBaptiste Daroussin 
299a9e8641dSBaptiste Daroussin int
open_locked(const char * fname,int flags,...)300a9e8641dSBaptiste Daroussin open_locked(const char *fname, int flags, ...)
301a9e8641dSBaptiste Daroussin {
302a9e8641dSBaptiste Daroussin 	int mode = 0;
303a9e8641dSBaptiste Daroussin 
304a9e8641dSBaptiste Daroussin 	if (flags & O_CREAT) {
305a9e8641dSBaptiste Daroussin 		va_list ap;
306a9e8641dSBaptiste Daroussin 		va_start(ap, flags);
307a9e8641dSBaptiste Daroussin 		mode = va_arg(ap, int);
308a9e8641dSBaptiste Daroussin 		va_end(ap);
309a9e8641dSBaptiste Daroussin 	}
310a9e8641dSBaptiste Daroussin 
311a9e8641dSBaptiste Daroussin #ifndef O_EXLOCK
312a9e8641dSBaptiste Daroussin 	int fd, save_errno;
313a9e8641dSBaptiste Daroussin 
314a9e8641dSBaptiste Daroussin 	fd = open(fname, flags, mode);
315a9e8641dSBaptiste Daroussin 	if (fd < 0)
316a9e8641dSBaptiste Daroussin 		return(fd);
317a9e8641dSBaptiste Daroussin 	if (flock(fd, LOCK_EX|((flags & O_NONBLOCK)? LOCK_NB: 0)) < 0) {
318a9e8641dSBaptiste Daroussin 		save_errno = errno;
319a9e8641dSBaptiste Daroussin 		close(fd);
320a9e8641dSBaptiste Daroussin 		errno = save_errno;
321a9e8641dSBaptiste Daroussin 		return(-1);
322a9e8641dSBaptiste Daroussin 	}
323a9e8641dSBaptiste Daroussin 	return(fd);
324a9e8641dSBaptiste Daroussin #else
325a9e8641dSBaptiste Daroussin 	return(open(fname, flags|O_EXLOCK, mode));
326a9e8641dSBaptiste Daroussin #endif
327a9e8641dSBaptiste Daroussin }
328a9e8641dSBaptiste Daroussin 
329a9e8641dSBaptiste Daroussin char *
rfc822date(void)330a9e8641dSBaptiste Daroussin rfc822date(void)
331a9e8641dSBaptiste Daroussin {
332a9e8641dSBaptiste Daroussin 	static char str[50];
333a9e8641dSBaptiste Daroussin 	size_t error;
334a9e8641dSBaptiste Daroussin 	time_t now;
335a9e8641dSBaptiste Daroussin 
336a9e8641dSBaptiste Daroussin 	now = time(NULL);
337a9e8641dSBaptiste Daroussin 	error = strftime(str, sizeof(str), "%a, %d %b %Y %T %z",
338a9e8641dSBaptiste Daroussin 		       localtime(&now));
339a9e8641dSBaptiste Daroussin 	if (error == 0)
340a9e8641dSBaptiste Daroussin 		strcpy(str, "(date fail)");
341a9e8641dSBaptiste Daroussin 	return (str);
342a9e8641dSBaptiste Daroussin }
343a9e8641dSBaptiste Daroussin 
344a9e8641dSBaptiste Daroussin int
strprefixcmp(const char * str,const char * prefix)345a9e8641dSBaptiste Daroussin strprefixcmp(const char *str, const char *prefix)
346a9e8641dSBaptiste Daroussin {
347a9e8641dSBaptiste Daroussin 	return (strncasecmp(str, prefix, strlen(prefix)));
348 }
349 
350 void
init_random(void)351 init_random(void)
352 {
353 	unsigned int seed;
354 	int rf;
355 
356 	rf = open("/dev/urandom", O_RDONLY);
357 	if (rf == -1)
358 		rf = open("/dev/random", O_RDONLY);
359 
360 	if (!(rf != -1 && read(rf, &seed, sizeof(seed)) == sizeof(seed)))
361 		seed = (time(NULL) ^ getpid()) + (uintptr_t)&seed;
362 
363 	srandom(seed);
364 
365 	if (rf != -1)
366 		close(rf);
367 }
368