xref: /netbsd-src/external/bsd/ntp/dist/libntp/numtoa.c (revision eabc0478de71e4e011a5b4e0392741e01d491794)
1*eabc0478Schristos /*	$NetBSD: numtoa.c,v 1.6 2024/08/18 20:47:13 christos Exp $	*/
2abb0f93cSkardel 
3abb0f93cSkardel /*
4abb0f93cSkardel  * numtoa - return asciized network numbers store in local array space
5abb0f93cSkardel  */
6abb0f93cSkardel #include <config.h>
7abb0f93cSkardel 
8abb0f93cSkardel #include <sys/types.h>
9abb0f93cSkardel #ifdef HAVE_NETINET_IN_H
10abb0f93cSkardel #include <netinet/in.h>		/* ntohl */
11abb0f93cSkardel #endif
12abb0f93cSkardel 
13abb0f93cSkardel #include <stdio.h>
14*eabc0478Schristos #include <ctype.h>
15abb0f93cSkardel 
16abb0f93cSkardel #include "ntp_fp.h"
17abb0f93cSkardel #include "ntp_stdlib.h"
18abb0f93cSkardel 
19abb0f93cSkardel char *
20abb0f93cSkardel numtoa(
21abb0f93cSkardel 	u_int32 num
22abb0f93cSkardel 	)
23abb0f93cSkardel {
24abb0f93cSkardel 	register u_int32 netnum;
25abb0f93cSkardel 	register char *buf;
26abb0f93cSkardel 
27abb0f93cSkardel 	netnum = ntohl(num);
28abb0f93cSkardel 	LIB_GETBUF(buf);
29abb0f93cSkardel 	snprintf(buf, LIB_BUFLENGTH, "%lu.%lu.%lu.%lu",
30abb0f93cSkardel 		 ((u_long)netnum >> 24) & 0xff,
31abb0f93cSkardel 		 ((u_long)netnum >> 16) & 0xff,
32abb0f93cSkardel 		 ((u_long)netnum >> 8) & 0xff,
33abb0f93cSkardel 		 (u_long)netnum & 0xff);
34abb0f93cSkardel 	return buf;
35abb0f93cSkardel }
368585484eSchristos 
378585484eSchristos 
38*eabc0478Schristos /*
39*eabc0478Schristos  * Convert a refid & stratum to a string.  If stratum is negative and the
40*eabc0478Schristos  * refid consists entirely of graphic chars, up to an optional
41*eabc0478Schristos  * terminating zero, display as text similar to stratum 0 & 1.
42*eabc0478Schristos  */
438585484eSchristos const char *
448585484eSchristos refid_str(
458585484eSchristos 	u_int32	refid,
468585484eSchristos 	int	stratum
478585484eSchristos 	)
488585484eSchristos {
498585484eSchristos 	char *	text;
508585484eSchristos 	size_t	tlen;
51*eabc0478Schristos 	char *	cp;
52*eabc0478Schristos 	int	printable;
538585484eSchristos 
54*eabc0478Schristos 	/*
55*eabc0478Schristos 	 * ntpd can have stratum = 0 and refid 127.0.0.1 in orphan mode.
56*eabc0478Schristos 	 * https://bugs.ntp.org/3854.  Mirror the refid logic in timer().
57*eabc0478Schristos 	 */
58*eabc0478Schristos 	if (0 == stratum && LOOPBACKADR_N == refid) {
59*eabc0478Schristos 		return ".ORPH.";
60*eabc0478Schristos 	}
61*eabc0478Schristos 	printable = FALSE;
62*eabc0478Schristos 	if (stratum < 2) {
63*eabc0478Schristos 		text = lib_getbuf();
648585484eSchristos 		text[0] = '.';
658585484eSchristos 		memcpy(&text[1], &refid, sizeof(refid));
668585484eSchristos 		text[1 + sizeof(refid)] = '\0';
678585484eSchristos 		tlen = strlen(text);
688585484eSchristos 		text[tlen] = '.';
698585484eSchristos 		text[tlen + 1] = '\0';
70*eabc0478Schristos 		/*
71*eabc0478Schristos 		 * Now make sure the contents are 'graphic'.
72*eabc0478Schristos 		 *
73*eabc0478Schristos 		 * This refid is expected to be up to 4 printable ASCII.
74*eabc0478Schristos 		 * isgraph() is similar to isprint() but excludes space.
75*eabc0478Schristos 		 * If any character is not graphic, replace it with a '?'.
76*eabc0478Schristos 		 * This will at least alert the viewer of a problem.
77*eabc0478Schristos 		 */
78*eabc0478Schristos 		for (cp = text + 1; '\0' != *cp; ++cp) {
79*eabc0478Schristos 			if (!isgraph((int)*cp)) {
80*eabc0478Schristos 				printable = FALSE;
81*eabc0478Schristos 				*cp = '?';
82*eabc0478Schristos 			}
83*eabc0478Schristos 		}
84*eabc0478Schristos 		if (   (stratum < 0 && printable)
85*eabc0478Schristos 		    || stratum < 2) {
868585484eSchristos 			return text;
878585484eSchristos 		}
88*eabc0478Schristos 	}
89*eabc0478Schristos 	return numtoa(refid);
90*eabc0478Schristos }
918585484eSchristos 
92