2 * Copyright (c) 2007-2012 Zmanda, Inc. All Rights Reserved.
4 * This program is free software; you can redistribute it and/or
5 * modify it under the terms of the GNU General Public License
6 * as published by the Free Software Foundation; either version 2
7 * of the License, or (at your option) any later version.
9 * This program is distributed in the hope that it will be useful, but
10 * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
11 * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
14 * You should have received a copy of the GNU General Public License along
15 * with this program; if not, write to the Free Software Foundation, Inc.,
16 * 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
18 * Contact information: Zmanda Inc, 465 S. Mathilda Ave., Suite 300
19 * Sunnyvale, CA 94086, USA, or: http://www.zmanda.com
21 * Author: Dustin J. Mitchell <dustin@zmanda.com>
24 * Utility routines for handling sockaddrs
27 #ifndef SOCKADDR_UTIL_H
28 #define SOCKADDR_UTIL_H
32 /* Dump a sockaddr_union using dbprintf
34 * @param sa: the sockaddr to dump
36 void dump_sockaddr(sockaddr_union * sa);
38 /* Convert a sockaddr_union to a string.
40 * NOTE: this function is not threadsafe!
42 * @param sa: the sockaddr_union to dump
43 * @returns: pointer to statically allocated string
45 char * str_sockaddr(sockaddr_union *sa);
46 char * str_sockaddr_no_port(sockaddr_union *sa);
48 /* Compare two sockaddr_union objects, optionally comparing
49 * only the address (and thus ignoring port, flow info, etc.).
51 * @param su1: one sockaddr_union to compare
52 * @param su2: the other sockaddr_union to compare
53 * @param addr_only: if true, ignore port, flow info, etc.
54 * @returns: -1, 0, or 1 for <, ==, >, respectively
56 int cmp_sockaddr(sockaddr_union *su1,
60 /* Parse a string into a sockaddr. This will try all available address
63 * @param src: the string representation of the address
64 * @param dst: the sockaddr_union in which to store the result
65 * @returns: 1 on success, -1 on error, or 0 if unparseable
71 /* Copy a sockaddr object.
73 * @param dest: destination
76 #define copy_sockaddr(dest, src) memcpy((dest), (src), SS_LEN((src)))
78 /* The "best" address family we support.
82 #define AF_NATIVE AF_INET6
84 #define AF_NATIVE AF_INET
87 /* Get the family for a sockaddr_union.
89 * @param su: the sockaddr_union to examine
91 #define SU_GET_FAMILY(su) ((su)->sa.sa_family)
92 /* Calculate the length of the data in a sockaddr_union.
94 * @param su: the sockaddr_union to examine
95 * @returns: length of the data in the object
99 # define SS_LEN(su) (SU_GET_FAMILY(su)==AF_INET6? sizeof(struct sockaddr_in6):sizeof(struct sockaddr_in))
101 # define SS_LEN(su) (sizeof(struct sockaddr_in))
104 /* Initialize a sockaddr_union to all zeroes (as directed by RFC),
105 * and set its address family as specified
107 * @param su: sockaddr_union object to initialize
108 * @param family: an AF_* constant
110 /* SU_INIT(su, family) */
111 #define SU_INIT(su, family) do { \
112 memset((su), 0, sizeof(*(su))); \
113 (su)->sa.sa_family = (family); \
116 /* set a sockaddr_union to the family-appropriate equivalent of
117 * INADDR_ANY -- a wildcard address and port. Call SU_INIT(su)
118 * first to initialize the object and set the family.
120 * @param su: the sockaddr_union to set
122 /* SU_SET_INADDR_ANY(su) */
124 #define SU_SET_INADDR_ANY(su) do { \
125 switch (SU_GET_FAMILY(su)) { \
127 (su)->sin6.sin6_flowinfo = 0; \
128 (su)->sin6.sin6_addr = in6addr_any; \
131 (su)->sin.sin_addr.s_addr = INADDR_ANY; \
136 #define SU_SET_INADDR_ANY(su) do { \
137 (su)->sin.sin_addr.s_addr = INADDR_ANY; \
141 /* Set the port in a sockaddr_union that already has an family
143 * @param su: the sockaddr_union to manipulate
144 * @param port: the port to insert (in host byte order)
146 /* SU_SET_PORT(su, port) */
148 #define SU_SET_PORT(su, port) \
149 switch (SU_GET_FAMILY(su)) { \
151 (su)->sin.sin_port = (in_port_t)htons((port)); \
154 (su)->sin6.sin6_port = (in_port_t)htons((port)); \
156 default: assert(0); \
159 #define SU_SET_PORT(su, port) \
160 (su)->sin.sin_port = (in_port_t)htons((port));
163 /* Get the port in a sockaddr_union object
165 * @param su: the sockaddr_union to manipulate
166 * @return: the port, in host byte horder
168 /* SU_GET_PORT(su) */
170 #define SU_GET_PORT(su) (ntohs(SU_GET_FAMILY(su) == AF_INET6? (su)->sin6.sin6_port:(su)->sin.sin_port))
172 #define SU_GET_PORT(su) (ntohs((su)->sin.sin_port))
175 #endif /* SOCKADDR_UTIL_H */