1 /* $NetBSD: inet_addr_sizes.c,v 1.2 2023/12/23 20:30:46 christos Exp $ */
2
3 /*++
4 /* NAME
5 /* inet_addr_sizes 3
6 /* SUMMARY
7 /* get network address size metrics
8 /* SYNOPSIS
9 /* #include <inet_addr_sizes.h>
10 /*
11 /* typedef struct {
12 /* .in +4
13 /* int af; /* network address family (binary) */
14 /* char *ipproto_str; /* IP protocol version (string) */
15 /* int addr_bitcount; /* bits per address */
16 /* int addr_bytecount; /* bytes per address */
17 /* int addr_strlen; /* address string length */
18 /* int addr_bitcount_strlen;/* addr_bitcount string length */
19 /* .in -4
20 /* } INET_ADDR_SIZES;
21 /*
22 /* const INET_ADDR_SIZES *inet_addr_sizes(int family)
23 /* DESCRIPTION
24 /* inet_addr_sizes() returns address size metrics for the
25 /* specified network address family, AF_INET or AF_INET6.
26 /* DIAGNOSTICS
27 /* inet_addr_sizes() returns a null pointer when the argument
28 /* specifies an unexpected address family.
29 /* LICENSE
30 /* .ad
31 /* .fi
32 /* The Secure Mailer license must be distributed with this software.
33 /* AUTHOR(S)
34 /* Wietse Venema
35 /*--*/
36
37 /*
38 * System library.
39 */
40 #include <sys_defs.h>
41 #include <string.h>
42
43 /*
44 * Utility library.
45 */
46 #include <inet_addr_sizes.h>
47 #include <msg.h>
48 #include <myaddrinfo.h>
49
50 /*
51 * Stringify a numeric constant and use sizeof() to determine the resulting
52 * string length at compile time. Note that sizeof() includes a null
53 * terminator; the -1 corrects for that.
54 */
55 #define _STRINGIFY(x) #x
56 #define _STRLEN(x) (sizeof(_STRINGIFY(x)) - 1)
57
58 static const INET_ADDR_SIZES table[] = {
59 {AF_INET, "IPv4", MAI_V4ADDR_BITS, MAI_V4ADDR_BYTES, INET_ADDRSTRLEN,
60 _STRLEN(MAI_V4ADDR_BITS)},
61 #ifdef HAS_IPV6
62 {AF_INET6, "IPv6", MAI_V6ADDR_BITS, MAI_V6ADDR_BYTES, INET6_ADDRSTRLEN,
63 _STRLEN(MAI_V6ADDR_BITS)},
64 #endif
65 };
66
67 /* inet_addr_sizes - get address size metrics for address family */
68
inet_addr_sizes(int af)69 const INET_ADDR_SIZES *inet_addr_sizes(int af)
70 {
71 const INET_ADDR_SIZES *sp;
72
73 for (sp = table; /* see below */ ; sp++) {
74 if (sp >= table + sizeof(table) / sizeof(*table))
75 return (0);
76 if (sp->af == af)
77 return (sp);
78 }
79 }
80