bind - Removed version tag from contrib directory and updated README.DRAGONFLY.
[dragonfly.git] / contrib / bind / lib / isc / unix / include / isc / net.h
1 /*
2  * Copyright (C) 2004, 2005, 2007-2009  Internet Systems Consortium, Inc. ("ISC")
3  * Copyright (C) 1999-2003  Internet Software Consortium.
4  *
5  * Permission to use, copy, modify, and/or distribute this software for any
6  * purpose with or without fee is hereby granted, provided that the above
7  * copyright notice and this permission notice appear in all copies.
8  *
9  * THE SOFTWARE IS PROVIDED "AS IS" AND ISC DISCLAIMS ALL WARRANTIES WITH
10  * REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY
11  * AND FITNESS.  IN NO EVENT SHALL ISC BE LIABLE FOR ANY SPECIAL, DIRECT,
12  * INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM
13  * LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE
14  * OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
15  * PERFORMANCE OF THIS SOFTWARE.
16  */
17
18 /* $Id: net.h,v 1.46.128.5 2009/02/16 23:46:44 tbox Exp $ */
19
20 #ifndef ISC_NET_H
21 #define ISC_NET_H 1
22
23 /*****
24  ***** Module Info
25  *****/
26
27 /*! \file
28  * \brief
29  * Basic Networking Types
30  *
31  * This module is responsible for defining the following basic networking
32  * types:
33  *
34  *\li           struct in_addr
35  *\li           struct in6_addr
36  *\li           struct in6_pktinfo
37  *\li           struct sockaddr
38  *\li           struct sockaddr_in
39  *\li           struct sockaddr_in6
40  *\li           in_port_t
41  *
42  * It ensures that the AF_ and PF_ macros are defined.
43  *
44  * It declares ntoh[sl]() and hton[sl]().
45  *
46  * It declares inet_aton(), inet_ntop(), and inet_pton().
47  *
48  * It ensures that #INADDR_LOOPBACK, #INADDR_ANY, #IN6ADDR_ANY_INIT,
49  * in6addr_any, and in6addr_loopback are available.
50  *
51  * It ensures that IN_MULTICAST() is available to check for multicast
52  * addresses.
53  *
54  * MP:
55  *\li   No impact.
56  *
57  * Reliability:
58  *\li   No anticipated impact.
59  *
60  * Resources:
61  *\li   N/A.
62  *
63  * Security:
64  *\li   No anticipated impact.
65  *
66  * Standards:
67  *\li   BSD Socket API
68  *\li   RFC2553
69  */
70
71 /***
72  *** Imports.
73  ***/
74 #include <isc/platform.h>
75
76 #include <sys/types.h>
77 #include <sys/socket.h>         /* Contractual promise. */
78
79 #include <net/if.h>
80
81 #include <netinet/in.h>         /* Contractual promise. */
82 #include <arpa/inet.h>          /* Contractual promise. */
83 #ifdef ISC_PLATFORM_NEEDNETINETIN6H
84 #include <netinet/in6.h>        /* Required on UnixWare. */
85 #endif
86 #ifdef ISC_PLATFORM_NEEDNETINET6IN6H
87 #include <netinet6/in6.h>       /* Required on BSD/OS for in6_pktinfo. */
88 #endif
89
90 #ifndef ISC_PLATFORM_HAVEIPV6
91 #include <isc/ipv6.h>           /* Contractual promise. */
92 #endif
93
94 #include <isc/lang.h>
95 #include <isc/types.h>
96
97 #ifdef ISC_PLATFORM_HAVEINADDR6
98 #define in6_addr in_addr6       /*%< Required for pre RFC2133 implementations. */
99 #endif
100
101 #ifdef ISC_PLATFORM_HAVEIPV6
102 #ifndef IN6ADDR_ANY_INIT
103 #ifdef s6_addr
104 /*%
105  * Required for some pre RFC2133 implementations.
106  * IN6ADDR_ANY_INIT and IN6ADDR_LOOPBACK_INIT were added in
107  * draft-ietf-ipngwg-bsd-api-04.txt or draft-ietf-ipngwg-bsd-api-05.txt.
108  * If 's6_addr' is defined then assume that there is a union and three
109  * levels otherwise assume two levels required.
110  */
111 #define IN6ADDR_ANY_INIT { { { 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 } } }
112 #else
113 #define IN6ADDR_ANY_INIT { { 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 } }
114 #endif
115 #endif
116
117 #ifndef IN6ADDR_LOOPBACK_INIT
118 #ifdef s6_addr
119 /*% IPv6 address loopback init */
120 #define IN6ADDR_LOOPBACK_INIT { { { 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1 } } }
121 #else
122 #define IN6ADDR_LOOPBACK_INIT { { 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1 } }
123 #endif
124 #endif
125
126 #ifndef IN6_IS_ADDR_V4MAPPED
127 /*% Is IPv6 address V4 mapped? */
128 #define IN6_IS_ADDR_V4MAPPED(x) \
129          (memcmp((x)->s6_addr, in6addr_any.s6_addr, 10) == 0 && \
130           (x)->s6_addr[10] == 0xff && (x)->s6_addr[11] == 0xff)
131 #endif
132
133 #ifndef IN6_IS_ADDR_V4COMPAT
134 /*% Is IPv6 address V4 compatible? */
135 #define IN6_IS_ADDR_V4COMPAT(x) \
136          (memcmp((x)->s6_addr, in6addr_any.s6_addr, 12) == 0 && \
137          ((x)->s6_addr[12] != 0 || (x)->s6_addr[13] != 0 || \
138           (x)->s6_addr[14] != 0 || \
139           ((x)->s6_addr[15] != 0 && (x)->s6_addr[15] != 1)))
140 #endif
141
142 #ifndef IN6_IS_ADDR_MULTICAST
143 /*% Is IPv6 address multicast? */
144 #define IN6_IS_ADDR_MULTICAST(a)        ((a)->s6_addr[0] == 0xff)
145 #endif
146
147 #ifndef IN6_IS_ADDR_LINKLOCAL
148 /*% Is IPv6 address linklocal? */
149 #define IN6_IS_ADDR_LINKLOCAL(a) \
150         (((a)->s6_addr[0] == 0xfe) && (((a)->s6_addr[1] & 0xc0) == 0x80))
151 #endif
152
153 #ifndef IN6_IS_ADDR_SITELOCAL
154 /*% is IPv6 address sitelocal? */
155 #define IN6_IS_ADDR_SITELOCAL(a) \
156         (((a)->s6_addr[0] == 0xfe) && (((a)->s6_addr[1] & 0xc0) == 0xc0))
157 #endif
158
159
160 #ifndef IN6_IS_ADDR_LOOPBACK
161 /*% is IPv6 address loopback? */
162 #define IN6_IS_ADDR_LOOPBACK(x) \
163         (memcmp((x)->s6_addr, in6addr_loopback.s6_addr, 16) == 0)
164 #endif
165 #endif
166
167 #ifndef AF_INET6
168 /*% IPv6 */
169 #define AF_INET6 99
170 #endif
171
172 #ifndef PF_INET6
173 /*% IPv6 */
174 #define PF_INET6 AF_INET6
175 #endif
176
177 #ifndef INADDR_LOOPBACK
178 /*% inaddr loopback */
179 #define INADDR_LOOPBACK 0x7f000001UL
180 #endif
181
182 #ifndef ISC_PLATFORM_HAVEIN6PKTINFO
183 /*% IPv6 packet info */
184 struct in6_pktinfo {
185         struct in6_addr ipi6_addr;    /*%< src/dst IPv6 address */
186         unsigned int    ipi6_ifindex; /*%< send/recv interface index */
187 };
188 #endif
189
190 #if defined(ISC_PLATFORM_HAVEIPV6) && defined(ISC_PLATFORM_NEEDIN6ADDRANY)
191 extern const struct in6_addr isc_net_in6addrany;
192 /*%
193  * Cope with a missing in6addr_any and in6addr_loopback.
194  */
195 #define in6addr_any isc_net_in6addrany
196 #endif
197
198 #if defined(ISC_PLATFORM_HAVEIPV6) && defined(ISC_PLATFORM_NEEDIN6ADDRLOOPBACK)
199 extern const struct in6_addr isc_net_in6addrloop;
200 #define in6addr_loopback isc_net_in6addrloop
201 #endif
202
203 #ifdef ISC_PLATFORM_FIXIN6ISADDR
204 #undef  IN6_IS_ADDR_GEOGRAPHIC
205 /*!
206  * \brief
207  * Fix UnixWare 7.1.1's broken IN6_IS_ADDR_* definitions.
208  */
209 #define IN6_IS_ADDR_GEOGRAPHIC(a) (((a)->S6_un.S6_l[0] & 0xE0) == 0x80)
210 #undef  IN6_IS_ADDR_IPX
211 #define IN6_IS_ADDR_IPX(a)        (((a)->S6_un.S6_l[0] & 0xFE) == 0x04)
212 #undef  IN6_IS_ADDR_LINKLOCAL
213 #define IN6_IS_ADDR_LINKLOCAL(a)  (((a)->S6_un.S6_l[0] & 0xC0FF) == 0x80FE)
214 #undef  IN6_IS_ADDR_MULTICAST
215 #define IN6_IS_ADDR_MULTICAST(a)  (((a)->S6_un.S6_l[0] & 0xFF) == 0xFF)
216 #undef  IN6_IS_ADDR_NSAP
217 #define IN6_IS_ADDR_NSAP(a)       (((a)->S6_un.S6_l[0] & 0xFE) == 0x02)
218 #undef  IN6_IS_ADDR_PROVIDER
219 #define IN6_IS_ADDR_PROVIDER(a)   (((a)->S6_un.S6_l[0] & 0xE0) == 0x40)
220 #undef  IN6_IS_ADDR_SITELOCAL
221 #define IN6_IS_ADDR_SITELOCAL(a)  (((a)->S6_un.S6_l[0] & 0xC0FF) == 0xC0FE)
222 #endif /* ISC_PLATFORM_FIXIN6ISADDR */
223
224 #ifdef ISC_PLATFORM_NEEDPORTT
225 /*%
226  * Ensure type in_port_t is defined.
227  */
228 typedef isc_uint16_t in_port_t;
229 #endif
230
231 #ifndef MSG_TRUNC
232 /*%
233  * If this system does not have MSG_TRUNC (as returned from recvmsg())
234  * ISC_PLATFORM_RECVOVERFLOW will be defined.  This will enable the MSG_TRUNC
235  * faking code in socket.c.
236  */
237 #define ISC_PLATFORM_RECVOVERFLOW
238 #endif
239
240 /*% IP address. */
241 #define ISC__IPADDR(x)  ((isc_uint32_t)htonl((isc_uint32_t)(x)))
242
243 /*% Is IP address multicast? */
244 #define ISC_IPADDR_ISMULTICAST(i) \
245                 (((isc_uint32_t)(i) & ISC__IPADDR(0xf0000000)) \
246                  == ISC__IPADDR(0xe0000000))
247
248 #define ISC_IPADDR_ISEXPERIMENTAL(i) \
249                 (((isc_uint32_t)(i) & ISC__IPADDR(0xf0000000)) \
250                  == ISC__IPADDR(0xf0000000))
251
252 /***
253  *** Functions.
254  ***/
255
256 ISC_LANG_BEGINDECLS
257
258 isc_result_t
259 isc_net_probeipv4(void);
260 /*%<
261  * Check if the system's kernel supports IPv4.
262  *
263  * Returns:
264  *
265  *\li   #ISC_R_SUCCESS          IPv4 is supported.
266  *\li   #ISC_R_NOTFOUND         IPv4 is not supported.
267  *\li   #ISC_R_DISABLED         IPv4 is disabled.
268  *\li   #ISC_R_UNEXPECTED
269  */
270
271 isc_result_t
272 isc_net_probeipv6(void);
273 /*%<
274  * Check if the system's kernel supports IPv6.
275  *
276  * Returns:
277  *
278  *\li   #ISC_R_SUCCESS          IPv6 is supported.
279  *\li   #ISC_R_NOTFOUND         IPv6 is not supported.
280  *\li   #ISC_R_DISABLED         IPv6 is disabled.
281  *\li   #ISC_R_UNEXPECTED
282  */
283
284 isc_result_t
285 isc_net_probe_ipv6only(void);
286 /*%<
287  * Check if the system's kernel supports the IPV6_V6ONLY socket option.
288  *
289  * Returns:
290  *
291  *\li   #ISC_R_SUCCESS          the option is supported for both TCP and UDP.
292  *\li   #ISC_R_NOTFOUND         IPv6 itself or the option is not supported.
293  *\li   #ISC_R_UNEXPECTED
294  */
295
296 isc_result_t
297 isc_net_probe_ipv6pktinfo(void);
298 /*
299  * Check if the system's kernel supports the IPV6_(RECV)PKTINFO socket option
300  * for UDP sockets.
301  *
302  * Returns:
303  *
304  * \li  #ISC_R_SUCCESS          the option is supported.
305  * \li  #ISC_R_NOTFOUND         IPv6 itself or the option is not supported.
306  * \li  #ISC_R_UNEXPECTED
307  */
308
309 void
310 isc_net_disableipv4(void);
311
312 void
313 isc_net_disableipv6(void);
314
315 void
316 isc_net_enableipv4(void);
317
318 void
319 isc_net_enableipv6(void);
320
321 isc_result_t
322 isc_net_probeunix(void);
323 /*
324  * Returns whether UNIX domain sockets are supported.
325  */
326
327 isc_result_t
328 isc_net_getudpportrange(int af, in_port_t *low, in_port_t *high);
329 /*%<
330  * Returns system's default range of ephemeral UDP ports, if defined.
331  * If the range is not available or unknown, ISC_NET_PORTRANGELOW and
332  * ISC_NET_PORTRANGEHIGH will be returned.
333  *
334  * Requires:
335  *
336  *\li   'low' and 'high' must be non NULL.
337  *
338  * Returns:
339  *
340  *\li   *low and *high will be the ports specifying the low and high ends of
341  *      the range.
342  */
343
344 #ifdef ISC_PLATFORM_NEEDNTOP
345 const char *
346 isc_net_ntop(int af, const void *src, char *dst, size_t size);
347 #define inet_ntop isc_net_ntop
348 #endif
349
350 #ifdef ISC_PLATFORM_NEEDPTON
351 int
352 isc_net_pton(int af, const char *src, void *dst);
353 #undef inet_pton
354 #define inet_pton isc_net_pton
355 #endif
356
357 int
358 isc_net_aton(const char *cp, struct in_addr *addr);
359 #undef inet_aton
360 #define inet_aton isc_net_aton
361
362 ISC_LANG_ENDDECLS
363
364 #endif /* ISC_NET_H */