1*0a6a1f1dSLionel Sambuc /* $NetBSD: util.h,v 1.3 2015/01/29 07:26:02 spz Exp $ */ 2e985b929SDavid van Moolenbroek /* 3e985b929SDavid van Moolenbroek * Copyright (c) 2007-2012 Niels Provos and Nick Mathewson 4e985b929SDavid van Moolenbroek * 5e985b929SDavid van Moolenbroek * Redistribution and use in source and binary forms, with or without 6e985b929SDavid van Moolenbroek * modification, are permitted provided that the following conditions 7e985b929SDavid van Moolenbroek * are met: 8e985b929SDavid van Moolenbroek * 1. Redistributions of source code must retain the above copyright 9e985b929SDavid van Moolenbroek * notice, this list of conditions and the following disclaimer. 10e985b929SDavid van Moolenbroek * 2. Redistributions in binary form must reproduce the above copyright 11e985b929SDavid van Moolenbroek * notice, this list of conditions and the following disclaimer in the 12e985b929SDavid van Moolenbroek * documentation and/or other materials provided with the distribution. 13e985b929SDavid van Moolenbroek * 3. The name of the author may not be used to endorse or promote products 14e985b929SDavid van Moolenbroek * derived from this software without specific prior written permission. 15e985b929SDavid van Moolenbroek * 16e985b929SDavid van Moolenbroek * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR 17e985b929SDavid van Moolenbroek * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES 18e985b929SDavid van Moolenbroek * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. 19e985b929SDavid van Moolenbroek * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, 20e985b929SDavid van Moolenbroek * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT 21e985b929SDavid van Moolenbroek * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 22e985b929SDavid van Moolenbroek * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 23e985b929SDavid van Moolenbroek * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 24e985b929SDavid van Moolenbroek * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF 25e985b929SDavid van Moolenbroek * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 26e985b929SDavid van Moolenbroek */ 27e985b929SDavid van Moolenbroek #ifndef _EVENT2_UTIL_H_ 28e985b929SDavid van Moolenbroek #define _EVENT2_UTIL_H_ 29e985b929SDavid van Moolenbroek 30e985b929SDavid van Moolenbroek /** @file event2/util.h 31e985b929SDavid van Moolenbroek 32e985b929SDavid van Moolenbroek Common convenience functions for cross-platform portability and 33e985b929SDavid van Moolenbroek related socket manipulations. 34e985b929SDavid van Moolenbroek 35e985b929SDavid van Moolenbroek */ 36e985b929SDavid van Moolenbroek 37e985b929SDavid van Moolenbroek #ifdef __cplusplus 38e985b929SDavid van Moolenbroek extern "C" { 39e985b929SDavid van Moolenbroek #endif 40e985b929SDavid van Moolenbroek 41e985b929SDavid van Moolenbroek #include <event2/event-config.h> 42e985b929SDavid van Moolenbroek #ifdef _EVENT_HAVE_SYS_TIME_H 43e985b929SDavid van Moolenbroek #include <sys/time.h> 44e985b929SDavid van Moolenbroek #endif 45e985b929SDavid van Moolenbroek #ifdef _EVENT_HAVE_STDINT_H 46e985b929SDavid van Moolenbroek #include <stdint.h> 47e985b929SDavid van Moolenbroek #elif defined(_EVENT_HAVE_INTTYPES_H) 48e985b929SDavid van Moolenbroek #include <inttypes.h> 49e985b929SDavid van Moolenbroek #endif 50e985b929SDavid van Moolenbroek #ifdef _EVENT_HAVE_SYS_TYPES_H 51e985b929SDavid van Moolenbroek #include <sys/types.h> 52e985b929SDavid van Moolenbroek #endif 53e985b929SDavid van Moolenbroek #ifdef _EVENT_HAVE_STDDEF_H 54e985b929SDavid van Moolenbroek #include <stddef.h> 55e985b929SDavid van Moolenbroek #endif 56e985b929SDavid van Moolenbroek #ifdef _MSC_VER 57e985b929SDavid van Moolenbroek #include <BaseTsd.h> 58e985b929SDavid van Moolenbroek #endif 59e985b929SDavid van Moolenbroek #include <stdarg.h> 60e985b929SDavid van Moolenbroek #ifdef _EVENT_HAVE_NETDB_H 61e985b929SDavid van Moolenbroek #if !defined(_GNU_SOURCE) 62e985b929SDavid van Moolenbroek #define _GNU_SOURCE 63e985b929SDavid van Moolenbroek #endif 64e985b929SDavid van Moolenbroek #include <netdb.h> 65e985b929SDavid van Moolenbroek #endif 66e985b929SDavid van Moolenbroek 67e985b929SDavid van Moolenbroek #ifdef WIN32 68e985b929SDavid van Moolenbroek #include <winsock2.h> 69e985b929SDavid van Moolenbroek #else 70e985b929SDavid van Moolenbroek #include <sys/socket.h> 71e985b929SDavid van Moolenbroek #endif 72e985b929SDavid van Moolenbroek 73e985b929SDavid van Moolenbroek /* Some openbsd autoconf versions get the name of this macro wrong. */ 74e985b929SDavid van Moolenbroek #if defined(_EVENT_SIZEOF_VOID__) && !defined(_EVENT_SIZEOF_VOID_P) 75e985b929SDavid van Moolenbroek #define _EVENT_SIZEOF_VOID_P _EVENT_SIZEOF_VOID__ 76e985b929SDavid van Moolenbroek #endif 77e985b929SDavid van Moolenbroek 78e985b929SDavid van Moolenbroek /** 79e985b929SDavid van Moolenbroek * @name Standard integer types. 80e985b929SDavid van Moolenbroek * 81e985b929SDavid van Moolenbroek * Integer type definitions for types that are supposed to be defined in the 82e985b929SDavid van Moolenbroek * C99-specified stdint.h. Shamefully, some platforms do not include 83e985b929SDavid van Moolenbroek * stdint.h, so we need to replace it. (If you are on a platform like this, 84e985b929SDavid van Moolenbroek * your C headers are now over 10 years out of date. You should bug them to 85e985b929SDavid van Moolenbroek * do something about this.) 86e985b929SDavid van Moolenbroek * 87e985b929SDavid van Moolenbroek * We define: 88e985b929SDavid van Moolenbroek * 89e985b929SDavid van Moolenbroek * <dl> 90e985b929SDavid van Moolenbroek * <dt>ev_uint64_t, ev_uint32_t, ev_uint16_t, ev_uint8_t</dt> 91e985b929SDavid van Moolenbroek * <dd>unsigned integer types of exactly 64, 32, 16, and 8 bits 92e985b929SDavid van Moolenbroek * respectively.</dd> 93e985b929SDavid van Moolenbroek * <dt>ev_int64_t, ev_int32_t, ev_int16_t, ev_int8_t</dt> 94e985b929SDavid van Moolenbroek * <dd>signed integer types of exactly 64, 32, 16, and 8 bits 95e985b929SDavid van Moolenbroek * respectively.</dd> 96e985b929SDavid van Moolenbroek * <dt>ev_uintptr_t, ev_intptr_t</dt> 97e985b929SDavid van Moolenbroek * <dd>unsigned/signed integers large enough 98e985b929SDavid van Moolenbroek * to hold a pointer without loss of bits.</dd> 99e985b929SDavid van Moolenbroek * <dt>ev_ssize_t</dt> 100e985b929SDavid van Moolenbroek * <dd>A signed type of the same size as size_t</dd> 101e985b929SDavid van Moolenbroek * <dt>ev_off_t</dt> 102e985b929SDavid van Moolenbroek * <dd>A signed type typically used to represent offsets within a 103e985b929SDavid van Moolenbroek * (potentially large) file</dd> 104e985b929SDavid van Moolenbroek * 105e985b929SDavid van Moolenbroek * @{ 106e985b929SDavid van Moolenbroek */ 107e985b929SDavid van Moolenbroek #ifdef _EVENT_HAVE_UINT64_T 108e985b929SDavid van Moolenbroek #define ev_uint64_t uint64_t 109e985b929SDavid van Moolenbroek #define ev_int64_t int64_t 110e985b929SDavid van Moolenbroek #elif defined(WIN32) 111e985b929SDavid van Moolenbroek #define ev_uint64_t unsigned __int64 112e985b929SDavid van Moolenbroek #define ev_int64_t signed __int64 113e985b929SDavid van Moolenbroek #elif _EVENT_SIZEOF_LONG_LONG == 8 114e985b929SDavid van Moolenbroek #define ev_uint64_t unsigned long long 115e985b929SDavid van Moolenbroek #define ev_int64_t long long 116e985b929SDavid van Moolenbroek #elif _EVENT_SIZEOF_LONG == 8 117e985b929SDavid van Moolenbroek #define ev_uint64_t unsigned long 118e985b929SDavid van Moolenbroek #define ev_int64_t long 119e985b929SDavid van Moolenbroek #elif defined(_EVENT_IN_DOXYGEN) 120e985b929SDavid van Moolenbroek #define ev_uint64_t ... 121e985b929SDavid van Moolenbroek #define ev_int64_t ... 122e985b929SDavid van Moolenbroek #else 123e985b929SDavid van Moolenbroek #error "No way to define ev_uint64_t" 124e985b929SDavid van Moolenbroek #endif 125e985b929SDavid van Moolenbroek 126e985b929SDavid van Moolenbroek #ifdef _EVENT_HAVE_UINT32_T 127e985b929SDavid van Moolenbroek #define ev_uint32_t uint32_t 128e985b929SDavid van Moolenbroek #define ev_int32_t int32_t 129e985b929SDavid van Moolenbroek #elif defined(WIN32) 130e985b929SDavid van Moolenbroek #define ev_uint32_t unsigned int 131e985b929SDavid van Moolenbroek #define ev_int32_t signed int 132e985b929SDavid van Moolenbroek #elif _EVENT_SIZEOF_LONG == 4 133e985b929SDavid van Moolenbroek #define ev_uint32_t unsigned long 134e985b929SDavid van Moolenbroek #define ev_int32_t signed long 135e985b929SDavid van Moolenbroek #elif _EVENT_SIZEOF_INT == 4 136e985b929SDavid van Moolenbroek #define ev_uint32_t unsigned int 137e985b929SDavid van Moolenbroek #define ev_int32_t signed int 138e985b929SDavid van Moolenbroek #elif defined(_EVENT_IN_DOXYGEN) 139e985b929SDavid van Moolenbroek #define ev_uint32_t ... 140e985b929SDavid van Moolenbroek #define ev_int32_t ... 141e985b929SDavid van Moolenbroek #else 142e985b929SDavid van Moolenbroek #error "No way to define ev_uint32_t" 143e985b929SDavid van Moolenbroek #endif 144e985b929SDavid van Moolenbroek 145e985b929SDavid van Moolenbroek #ifdef _EVENT_HAVE_UINT16_T 146e985b929SDavid van Moolenbroek #define ev_uint16_t uint16_t 147e985b929SDavid van Moolenbroek #define ev_int16_t int16_t 148e985b929SDavid van Moolenbroek #elif defined(WIN32) 149e985b929SDavid van Moolenbroek #define ev_uint16_t unsigned short 150e985b929SDavid van Moolenbroek #define ev_int16_t signed short 151e985b929SDavid van Moolenbroek #elif _EVENT_SIZEOF_INT == 2 152e985b929SDavid van Moolenbroek #define ev_uint16_t unsigned int 153e985b929SDavid van Moolenbroek #define ev_int16_t signed int 154e985b929SDavid van Moolenbroek #elif _EVENT_SIZEOF_SHORT == 2 155e985b929SDavid van Moolenbroek #define ev_uint16_t unsigned short 156e985b929SDavid van Moolenbroek #define ev_int16_t signed short 157e985b929SDavid van Moolenbroek #elif defined(_EVENT_IN_DOXYGEN) 158e985b929SDavid van Moolenbroek #define ev_uint16_t ... 159e985b929SDavid van Moolenbroek #define ev_int16_t ... 160e985b929SDavid van Moolenbroek #else 161e985b929SDavid van Moolenbroek #error "No way to define ev_uint16_t" 162e985b929SDavid van Moolenbroek #endif 163e985b929SDavid van Moolenbroek 164e985b929SDavid van Moolenbroek #ifdef _EVENT_HAVE_UINT8_T 165e985b929SDavid van Moolenbroek #define ev_uint8_t uint8_t 166e985b929SDavid van Moolenbroek #define ev_int8_t int8_t 167e985b929SDavid van Moolenbroek #elif defined(_EVENT_IN_DOXYGEN) 168e985b929SDavid van Moolenbroek #define ev_uint8_t ... 169e985b929SDavid van Moolenbroek #define ev_int8_t ... 170e985b929SDavid van Moolenbroek #else 171e985b929SDavid van Moolenbroek #define ev_uint8_t unsigned char 172e985b929SDavid van Moolenbroek #define ev_int8_t signed char 173e985b929SDavid van Moolenbroek #endif 174e985b929SDavid van Moolenbroek 175e985b929SDavid van Moolenbroek #ifdef _EVENT_HAVE_UINTPTR_T 176e985b929SDavid van Moolenbroek #define ev_uintptr_t uintptr_t 177e985b929SDavid van Moolenbroek #define ev_intptr_t intptr_t 178e985b929SDavid van Moolenbroek #elif _EVENT_SIZEOF_VOID_P <= 4 179e985b929SDavid van Moolenbroek #define ev_uintptr_t ev_uint32_t 180e985b929SDavid van Moolenbroek #define ev_intptr_t ev_int32_t 181e985b929SDavid van Moolenbroek #elif _EVENT_SIZEOF_VOID_P <= 8 182e985b929SDavid van Moolenbroek #define ev_uintptr_t ev_uint64_t 183e985b929SDavid van Moolenbroek #define ev_intptr_t ev_int64_t 184e985b929SDavid van Moolenbroek #elif defined(_EVENT_IN_DOXYGEN) 185e985b929SDavid van Moolenbroek #define ev_uintptr_t ... 186e985b929SDavid van Moolenbroek #define ev_intptr_t ... 187e985b929SDavid van Moolenbroek #else 188e985b929SDavid van Moolenbroek #error "No way to define ev_uintptr_t" 189e985b929SDavid van Moolenbroek #endif 190e985b929SDavid van Moolenbroek 191e985b929SDavid van Moolenbroek #ifdef _EVENT_ssize_t 192e985b929SDavid van Moolenbroek #define ev_ssize_t _EVENT_ssize_t 193e985b929SDavid van Moolenbroek #else 194e985b929SDavid van Moolenbroek #define ev_ssize_t ssize_t 195e985b929SDavid van Moolenbroek #endif 196e985b929SDavid van Moolenbroek 197e985b929SDavid van Moolenbroek #ifdef WIN32 198e985b929SDavid van Moolenbroek #define ev_off_t ev_int64_t 199e985b929SDavid van Moolenbroek #else 200e985b929SDavid van Moolenbroek #define ev_off_t off_t 201e985b929SDavid van Moolenbroek #endif 202e985b929SDavid van Moolenbroek /**@}*/ 203e985b929SDavid van Moolenbroek 204e985b929SDavid van Moolenbroek /* Limits for integer types. 205e985b929SDavid van Moolenbroek 206e985b929SDavid van Moolenbroek We're making two assumptions here: 207e985b929SDavid van Moolenbroek - The compiler does constant folding properly. 208e985b929SDavid van Moolenbroek - The platform does signed arithmetic in two's complement. 209e985b929SDavid van Moolenbroek */ 210e985b929SDavid van Moolenbroek 211e985b929SDavid van Moolenbroek /** 212e985b929SDavid van Moolenbroek @name Limits for integer types 213e985b929SDavid van Moolenbroek 214e985b929SDavid van Moolenbroek These macros hold the largest or smallest values possible for the 215e985b929SDavid van Moolenbroek ev_[u]int*_t types. 216e985b929SDavid van Moolenbroek 217e985b929SDavid van Moolenbroek @{ 218e985b929SDavid van Moolenbroek */ 219*0a6a1f1dSLionel Sambuc #define EV_UINT64_MAX ((((ev_uint64_t)0xffffffffUL) << 32) | 0xffffffffUL) 220*0a6a1f1dSLionel Sambuc #define EV_INT64_MAX ((((ev_int64_t) 0x7fffffffL) << 32) | 0xffffffffL) 221*0a6a1f1dSLionel Sambuc #define EV_INT64_MIN ((-EV_INT64_MAX) - 1) 222*0a6a1f1dSLionel Sambuc #define EV_UINT32_MAX ((ev_uint32_t)0xffffffffUL) 223*0a6a1f1dSLionel Sambuc #define EV_INT32_MAX ((ev_int32_t) 0x7fffffffL) 224*0a6a1f1dSLionel Sambuc #define EV_INT32_MIN ((-EV_INT32_MAX) - 1) 225*0a6a1f1dSLionel Sambuc #define EV_UINT16_MAX ((ev_uint16_t)0xffffUL) 226*0a6a1f1dSLionel Sambuc #define EV_INT16_MAX ((ev_int16_t) 0x7fffL) 227*0a6a1f1dSLionel Sambuc #define EV_INT16_MIN ((-EV_INT16_MAX) - 1) 228*0a6a1f1dSLionel Sambuc #define EV_UINT8_MAX 255 229*0a6a1f1dSLionel Sambuc #define EV_INT8_MAX 127 230*0a6a1f1dSLionel Sambuc #define EV_INT8_MIN ((-EV_INT8_MAX) - 1) 231e985b929SDavid van Moolenbroek /** @} */ 232e985b929SDavid van Moolenbroek 233e985b929SDavid van Moolenbroek /** 234e985b929SDavid van Moolenbroek @name Limits for SIZE_T and SSIZE_T 235e985b929SDavid van Moolenbroek 236e985b929SDavid van Moolenbroek @{ 237e985b929SDavid van Moolenbroek */ 238*0a6a1f1dSLionel Sambuc #if _EVENT_SIZEOF_SIZE_T == 8 239*0a6a1f1dSLionel Sambuc #define EV_SIZE_MAX EV_UINT64_MAX 240*0a6a1f1dSLionel Sambuc #define EV_SSIZE_MAX EV_INT64_MAX 241*0a6a1f1dSLionel Sambuc #elif _EVENT_SIZEOF_SIZE_T == 4 242*0a6a1f1dSLionel Sambuc #define EV_SIZE_MAX EV_UINT32_MAX 243*0a6a1f1dSLionel Sambuc #define EV_SSIZE_MAX EV_INT32_MAX 244*0a6a1f1dSLionel Sambuc #elif defined(_EVENT_IN_DOXYGEN) 245*0a6a1f1dSLionel Sambuc #define EV_SIZE_MAX ... 246*0a6a1f1dSLionel Sambuc #define EV_SSIZE_MAX ... 247*0a6a1f1dSLionel Sambuc #else 248*0a6a1f1dSLionel Sambuc #error "No way to define SIZE_MAX" 249*0a6a1f1dSLionel Sambuc #endif 250*0a6a1f1dSLionel Sambuc 251*0a6a1f1dSLionel Sambuc #define EV_SSIZE_MIN ((-EV_SSIZE_MAX) - 1) 252e985b929SDavid van Moolenbroek /**@}*/ 253e985b929SDavid van Moolenbroek 254e985b929SDavid van Moolenbroek #ifdef WIN32 255e985b929SDavid van Moolenbroek #define ev_socklen_t int 256e985b929SDavid van Moolenbroek #elif defined(_EVENT_socklen_t) 257e985b929SDavid van Moolenbroek #define ev_socklen_t _EVENT_socklen_t 258e985b929SDavid van Moolenbroek #else 259e985b929SDavid van Moolenbroek #define ev_socklen_t socklen_t 260e985b929SDavid van Moolenbroek #endif 261e985b929SDavid van Moolenbroek 262e985b929SDavid van Moolenbroek #ifdef _EVENT_HAVE_STRUCT_SOCKADDR_STORAGE___SS_FAMILY 263e985b929SDavid van Moolenbroek #if !defined(_EVENT_HAVE_STRUCT_SOCKADDR_STORAGE_SS_FAMILY) \ 264e985b929SDavid van Moolenbroek && !defined(ss_family) 265e985b929SDavid van Moolenbroek #define ss_family __ss_family 266e985b929SDavid van Moolenbroek #endif 267e985b929SDavid van Moolenbroek #endif 268e985b929SDavid van Moolenbroek 269e985b929SDavid van Moolenbroek /** 270e985b929SDavid van Moolenbroek * A type wide enough to hold the output of "socket()" or "accept()". On 271e985b929SDavid van Moolenbroek * Windows, this is an intptr_t; elsewhere, it is an int. */ 272e985b929SDavid van Moolenbroek #ifdef WIN32 273e985b929SDavid van Moolenbroek #define evutil_socket_t intptr_t 274e985b929SDavid van Moolenbroek #else 275e985b929SDavid van Moolenbroek #define evutil_socket_t int 276e985b929SDavid van Moolenbroek #endif 277e985b929SDavid van Moolenbroek 278e985b929SDavid van Moolenbroek /** Create two new sockets that are connected to each other. 279e985b929SDavid van Moolenbroek 280e985b929SDavid van Moolenbroek On Unix, this simply calls socketpair(). On Windows, it uses the 281e985b929SDavid van Moolenbroek loopback network interface on 127.0.0.1, and only 282e985b929SDavid van Moolenbroek AF_INET,SOCK_STREAM are supported. 283e985b929SDavid van Moolenbroek 284e985b929SDavid van Moolenbroek (This may fail on some Windows hosts where firewall software has cleverly 285e985b929SDavid van Moolenbroek decided to keep 127.0.0.1 from talking to itself.) 286e985b929SDavid van Moolenbroek 287e985b929SDavid van Moolenbroek Parameters and return values are as for socketpair() 288e985b929SDavid van Moolenbroek */ 289e985b929SDavid van Moolenbroek int evutil_socketpair(int d, int type, int protocol, evutil_socket_t sv[2]); 290e985b929SDavid van Moolenbroek /** Do platform-specific operations as needed to make a socket nonblocking. 291e985b929SDavid van Moolenbroek 292e985b929SDavid van Moolenbroek @param sock The socket to make nonblocking 293e985b929SDavid van Moolenbroek @return 0 on success, -1 on failure 294e985b929SDavid van Moolenbroek */ 295e985b929SDavid van Moolenbroek int evutil_make_socket_nonblocking(evutil_socket_t sock); 296e985b929SDavid van Moolenbroek 297e985b929SDavid van Moolenbroek /** Do platform-specific operations to make a listener socket reusable. 298e985b929SDavid van Moolenbroek 299e985b929SDavid van Moolenbroek Specifically, we want to make sure that another program will be able 300e985b929SDavid van Moolenbroek to bind this address right after we've closed the listener. 301e985b929SDavid van Moolenbroek 302e985b929SDavid van Moolenbroek This differs from Windows's interpretation of "reusable", which 303e985b929SDavid van Moolenbroek allows multiple listeners to bind the same address at the same time. 304e985b929SDavid van Moolenbroek 305e985b929SDavid van Moolenbroek @param sock The socket to make reusable 306e985b929SDavid van Moolenbroek @return 0 on success, -1 on failure 307e985b929SDavid van Moolenbroek */ 308e985b929SDavid van Moolenbroek int evutil_make_listen_socket_reuseable(evutil_socket_t sock); 309e985b929SDavid van Moolenbroek 310e985b929SDavid van Moolenbroek /** Do platform-specific operations as needed to close a socket upon a 311e985b929SDavid van Moolenbroek successful execution of one of the exec*() functions. 312e985b929SDavid van Moolenbroek 313e985b929SDavid van Moolenbroek @param sock The socket to be closed 314e985b929SDavid van Moolenbroek @return 0 on success, -1 on failure 315e985b929SDavid van Moolenbroek */ 316e985b929SDavid van Moolenbroek int evutil_make_socket_closeonexec(evutil_socket_t sock); 317e985b929SDavid van Moolenbroek 318e985b929SDavid van Moolenbroek /** Do the platform-specific call needed to close a socket returned from 319e985b929SDavid van Moolenbroek socket() or accept(). 320e985b929SDavid van Moolenbroek 321e985b929SDavid van Moolenbroek @param sock The socket to be closed 322e985b929SDavid van Moolenbroek @return 0 on success, -1 on failure 323e985b929SDavid van Moolenbroek */ 324e985b929SDavid van Moolenbroek int evutil_closesocket(evutil_socket_t sock); 325e985b929SDavid van Moolenbroek #define EVUTIL_CLOSESOCKET(s) evutil_closesocket(s) 326e985b929SDavid van Moolenbroek 327e985b929SDavid van Moolenbroek 328e985b929SDavid van Moolenbroek #ifdef WIN32 329e985b929SDavid van Moolenbroek /** Return the most recent socket error. Not idempotent on all platforms. */ 330e985b929SDavid van Moolenbroek #define EVUTIL_SOCKET_ERROR() WSAGetLastError() 331e985b929SDavid van Moolenbroek /** Replace the most recent socket error with errcode */ 332e985b929SDavid van Moolenbroek #define EVUTIL_SET_SOCKET_ERROR(errcode) \ 333*0a6a1f1dSLionel Sambuc do { WSASetLastError(errcode); } while (0) 334e985b929SDavid van Moolenbroek /** Return the most recent socket error to occur on sock. */ 335e985b929SDavid van Moolenbroek int evutil_socket_geterror(evutil_socket_t sock); 336e985b929SDavid van Moolenbroek /** Convert a socket error to a string. */ 337e985b929SDavid van Moolenbroek const char *evutil_socket_error_to_string(int errcode); 338e985b929SDavid van Moolenbroek #elif defined(_EVENT_IN_DOXYGEN) 339e985b929SDavid van Moolenbroek /** 340e985b929SDavid van Moolenbroek @name Socket error functions 341e985b929SDavid van Moolenbroek 342e985b929SDavid van Moolenbroek These functions are needed for making programs compatible between 343e985b929SDavid van Moolenbroek Windows and Unix-like platforms. 344e985b929SDavid van Moolenbroek 345e985b929SDavid van Moolenbroek You see, Winsock handles socket errors differently from the rest of 346e985b929SDavid van Moolenbroek the world. Elsewhere, a socket error is like any other error and is 347e985b929SDavid van Moolenbroek stored in errno. But winsock functions require you to retrieve the 348e985b929SDavid van Moolenbroek error with a special function, and don't let you use strerror for 349e985b929SDavid van Moolenbroek the error codes. And handling EWOULDBLOCK is ... different. 350e985b929SDavid van Moolenbroek 351e985b929SDavid van Moolenbroek @{ 352e985b929SDavid van Moolenbroek */ 353e985b929SDavid van Moolenbroek /** Return the most recent socket error. Not idempotent on all platforms. */ 354e985b929SDavid van Moolenbroek #define EVUTIL_SOCKET_ERROR() ... 355e985b929SDavid van Moolenbroek /** Replace the most recent socket error with errcode */ 356e985b929SDavid van Moolenbroek #define EVUTIL_SET_SOCKET_ERROR(errcode) ... 357e985b929SDavid van Moolenbroek /** Return the most recent socket error to occur on sock. */ 358e985b929SDavid van Moolenbroek #define evutil_socket_geterror(sock) ... 359e985b929SDavid van Moolenbroek /** Convert a socket error to a string. */ 360e985b929SDavid van Moolenbroek #define evutil_socket_error_to_string(errcode) ... 361e985b929SDavid van Moolenbroek /**@}*/ 362e985b929SDavid van Moolenbroek #else 363e985b929SDavid van Moolenbroek #define EVUTIL_SOCKET_ERROR() (errno) 364e985b929SDavid van Moolenbroek #define EVUTIL_SET_SOCKET_ERROR(errcode) \ 365*0a6a1f1dSLionel Sambuc do { errno = (errcode); } while (0) 366e985b929SDavid van Moolenbroek #define evutil_socket_geterror(sock) (errno) 367e985b929SDavid van Moolenbroek #define evutil_socket_error_to_string(errcode) (strerror(errcode)) 368e985b929SDavid van Moolenbroek #endif 369e985b929SDavid van Moolenbroek 370e985b929SDavid van Moolenbroek 371e985b929SDavid van Moolenbroek /** 372e985b929SDavid van Moolenbroek * @name Manipulation macros for struct timeval. 373e985b929SDavid van Moolenbroek * 374e985b929SDavid van Moolenbroek * We define replacements 375e985b929SDavid van Moolenbroek * for timeradd, timersub, timerclear, timercmp, and timerisset. 376e985b929SDavid van Moolenbroek * 377e985b929SDavid van Moolenbroek * @{ 378e985b929SDavid van Moolenbroek */ 379e985b929SDavid van Moolenbroek #ifdef _EVENT_HAVE_TIMERADD 380e985b929SDavid van Moolenbroek #define evutil_timeradd(tvp, uvp, vvp) timeradd((tvp), (uvp), (vvp)) 381e985b929SDavid van Moolenbroek #define evutil_timersub(tvp, uvp, vvp) timersub((tvp), (uvp), (vvp)) 382e985b929SDavid van Moolenbroek #else 383e985b929SDavid van Moolenbroek #define evutil_timeradd(tvp, uvp, vvp) \ 384e985b929SDavid van Moolenbroek do { \ 385e985b929SDavid van Moolenbroek (vvp)->tv_sec = (tvp)->tv_sec + (uvp)->tv_sec; \ 386e985b929SDavid van Moolenbroek (vvp)->tv_usec = (tvp)->tv_usec + (uvp)->tv_usec; \ 387e985b929SDavid van Moolenbroek if ((vvp)->tv_usec >= 1000000) { \ 388e985b929SDavid van Moolenbroek (vvp)->tv_sec++; \ 389e985b929SDavid van Moolenbroek (vvp)->tv_usec -= 1000000; \ 390e985b929SDavid van Moolenbroek } \ 391*0a6a1f1dSLionel Sambuc } while (0) 392e985b929SDavid van Moolenbroek #define evutil_timersub(tvp, uvp, vvp) \ 393e985b929SDavid van Moolenbroek do { \ 394e985b929SDavid van Moolenbroek (vvp)->tv_sec = (tvp)->tv_sec - (uvp)->tv_sec; \ 395e985b929SDavid van Moolenbroek (vvp)->tv_usec = (tvp)->tv_usec - (uvp)->tv_usec; \ 396e985b929SDavid van Moolenbroek if ((vvp)->tv_usec < 0) { \ 397e985b929SDavid van Moolenbroek (vvp)->tv_sec--; \ 398e985b929SDavid van Moolenbroek (vvp)->tv_usec += 1000000; \ 399e985b929SDavid van Moolenbroek } \ 400*0a6a1f1dSLionel Sambuc } while (0) 401e985b929SDavid van Moolenbroek #endif /* !_EVENT_HAVE_HAVE_TIMERADD */ 402e985b929SDavid van Moolenbroek 403e985b929SDavid van Moolenbroek #ifdef _EVENT_HAVE_TIMERCLEAR 404e985b929SDavid van Moolenbroek #define evutil_timerclear(tvp) timerclear(tvp) 405e985b929SDavid van Moolenbroek #else 406e985b929SDavid van Moolenbroek #define evutil_timerclear(tvp) (tvp)->tv_sec = (tvp)->tv_usec = 0 407e985b929SDavid van Moolenbroek #endif 408e985b929SDavid van Moolenbroek /**@}*/ 409e985b929SDavid van Moolenbroek 410e985b929SDavid van Moolenbroek /** Return true iff the tvp is related to uvp according to the relational 411e985b929SDavid van Moolenbroek * operator cmp. Recognized values for cmp are ==, <=, <, >=, and >. */ 412e985b929SDavid van Moolenbroek #define evutil_timercmp(tvp, uvp, cmp) \ 413e985b929SDavid van Moolenbroek (((tvp)->tv_sec == (uvp)->tv_sec) ? \ 414e985b929SDavid van Moolenbroek ((tvp)->tv_usec cmp (uvp)->tv_usec) : \ 415e985b929SDavid van Moolenbroek ((tvp)->tv_sec cmp (uvp)->tv_sec)) 416e985b929SDavid van Moolenbroek 417e985b929SDavid van Moolenbroek #ifdef _EVENT_HAVE_TIMERISSET 418e985b929SDavid van Moolenbroek #define evutil_timerisset(tvp) timerisset(tvp) 419e985b929SDavid van Moolenbroek #else 420e985b929SDavid van Moolenbroek #define evutil_timerisset(tvp) ((tvp)->tv_sec || (tvp)->tv_usec) 421e985b929SDavid van Moolenbroek #endif 422e985b929SDavid van Moolenbroek 423e985b929SDavid van Moolenbroek /** Replacement for offsetof on platforms that don't define it. */ 424e985b929SDavid van Moolenbroek #ifdef offsetof 425e985b929SDavid van Moolenbroek #define evutil_offsetof(type, field) offsetof(type, field) 426e985b929SDavid van Moolenbroek #else 427e985b929SDavid van Moolenbroek #define evutil_offsetof(type, field) ((off_t)(&((type *)0)->field)) 428e985b929SDavid van Moolenbroek #endif 429e985b929SDavid van Moolenbroek 430e985b929SDavid van Moolenbroek /* big-int related functions */ 431e985b929SDavid van Moolenbroek /** Parse a 64-bit value from a string. Arguments are as for strtol. */ 432e985b929SDavid van Moolenbroek ev_int64_t evutil_strtoll(const char *s, char **endptr, int base); 433e985b929SDavid van Moolenbroek 434e985b929SDavid van Moolenbroek /** Replacement for gettimeofday on platforms that lack it. */ 435e985b929SDavid van Moolenbroek #ifdef _EVENT_HAVE_GETTIMEOFDAY 436e985b929SDavid van Moolenbroek #define evutil_gettimeofday(tv, tz) gettimeofday((tv), (tz)) 437e985b929SDavid van Moolenbroek #else 438e985b929SDavid van Moolenbroek struct timezone; 439e985b929SDavid van Moolenbroek int evutil_gettimeofday(struct timeval *tv, struct timezone *tz); 440e985b929SDavid van Moolenbroek #endif 441e985b929SDavid van Moolenbroek 442e985b929SDavid van Moolenbroek /** Replacement for snprintf to get consistent behavior on platforms for 443e985b929SDavid van Moolenbroek which the return value of snprintf does not conform to C99. 444e985b929SDavid van Moolenbroek */ 445e985b929SDavid van Moolenbroek int evutil_snprintf(char *buf, size_t buflen, const char *format, ...) 446e985b929SDavid van Moolenbroek #ifdef __GNUC__ 447e985b929SDavid van Moolenbroek __attribute__((format(printf, 3, 4))) 448e985b929SDavid van Moolenbroek #endif 449e985b929SDavid van Moolenbroek ; 450e985b929SDavid van Moolenbroek /** Replacement for vsnprintf to get consistent behavior on platforms for 451e985b929SDavid van Moolenbroek which the return value of snprintf does not conform to C99. 452e985b929SDavid van Moolenbroek */ 453e985b929SDavid van Moolenbroek int evutil_vsnprintf(char *buf, size_t buflen, const char *format, va_list ap) 454e985b929SDavid van Moolenbroek #ifdef __GNUC__ 455e985b929SDavid van Moolenbroek __attribute__((format(printf, 3, 0))) 456e985b929SDavid van Moolenbroek #endif 457e985b929SDavid van Moolenbroek ; 458e985b929SDavid van Moolenbroek 459e985b929SDavid van Moolenbroek /** Replacement for inet_ntop for platforms which lack it. */ 460e985b929SDavid van Moolenbroek const char *evutil_inet_ntop(int af, const void *src, char *dst, size_t len); 461e985b929SDavid van Moolenbroek /** Replacement for inet_pton for platforms which lack it. */ 462e985b929SDavid van Moolenbroek int evutil_inet_pton(int af, const char *src, void *dst); 463e985b929SDavid van Moolenbroek struct sockaddr; 464e985b929SDavid van Moolenbroek 465e985b929SDavid van Moolenbroek /** Parse an IPv4 or IPv6 address, with optional port, from a string. 466e985b929SDavid van Moolenbroek 467e985b929SDavid van Moolenbroek Recognized formats are: 468e985b929SDavid van Moolenbroek - [IPv6Address]:port 469e985b929SDavid van Moolenbroek - [IPv6Address] 470e985b929SDavid van Moolenbroek - IPv6Address 471e985b929SDavid van Moolenbroek - IPv4Address:port 472e985b929SDavid van Moolenbroek - IPv4Address 473e985b929SDavid van Moolenbroek 474e985b929SDavid van Moolenbroek If no port is specified, the port in the output is set to 0. 475e985b929SDavid van Moolenbroek 476e985b929SDavid van Moolenbroek @param str The string to parse. 477e985b929SDavid van Moolenbroek @param out A struct sockaddr to hold the result. This should probably be 478e985b929SDavid van Moolenbroek a struct sockaddr_storage. 479e985b929SDavid van Moolenbroek @param outlen A pointer to the number of bytes that that 'out' can safely 480e985b929SDavid van Moolenbroek hold. Set to the number of bytes used in 'out' on success. 481e985b929SDavid van Moolenbroek @return -1 if the address is not well-formed, if the port is out of range, 482e985b929SDavid van Moolenbroek or if out is not large enough to hold the result. Otherwise returns 483e985b929SDavid van Moolenbroek 0 on success. 484e985b929SDavid van Moolenbroek */ 485e985b929SDavid van Moolenbroek int evutil_parse_sockaddr_port(const char *str, struct sockaddr *out, int *outlen); 486e985b929SDavid van Moolenbroek 487e985b929SDavid van Moolenbroek /** Compare two sockaddrs; return 0 if they are equal, or less than 0 if sa1 488e985b929SDavid van Moolenbroek * preceeds sa2, or greater than 0 if sa1 follows sa2. If include_port is 489e985b929SDavid van Moolenbroek * true, consider the port as well as the address. Only implemented for 490e985b929SDavid van Moolenbroek * AF_INET and AF_INET6 addresses. The ordering is not guaranteed to remain 491e985b929SDavid van Moolenbroek * the same between Libevent versions. */ 492e985b929SDavid van Moolenbroek int evutil_sockaddr_cmp(const struct sockaddr *sa1, const struct sockaddr *sa2, 493e985b929SDavid van Moolenbroek int include_port); 494e985b929SDavid van Moolenbroek 495e985b929SDavid van Moolenbroek /** As strcasecmp, but always compares the characters in locale-independent 496e985b929SDavid van Moolenbroek ASCII. That's useful if you're handling data in ASCII-based protocols. 497e985b929SDavid van Moolenbroek */ 498e985b929SDavid van Moolenbroek int evutil_ascii_strcasecmp(const char *str1, const char *str2); 499e985b929SDavid van Moolenbroek /** As strncasecmp, but always compares the characters in locale-independent 500e985b929SDavid van Moolenbroek ASCII. That's useful if you're handling data in ASCII-based protocols. 501e985b929SDavid van Moolenbroek */ 502e985b929SDavid van Moolenbroek int evutil_ascii_strncasecmp(const char *str1, const char *str2, size_t n); 503e985b929SDavid van Moolenbroek 504e985b929SDavid van Moolenbroek /* Here we define evutil_addrinfo to the native addrinfo type, or redefine it 505e985b929SDavid van Moolenbroek * if this system has no getaddrinfo(). */ 506e985b929SDavid van Moolenbroek #ifdef _EVENT_HAVE_STRUCT_ADDRINFO 507e985b929SDavid van Moolenbroek #define evutil_addrinfo addrinfo 508e985b929SDavid van Moolenbroek #else 509e985b929SDavid van Moolenbroek /** A definition of struct addrinfo for systems that lack it. 510e985b929SDavid van Moolenbroek 511e985b929SDavid van Moolenbroek (This is just an alias for struct addrinfo if the system defines 512e985b929SDavid van Moolenbroek struct addrinfo.) 513e985b929SDavid van Moolenbroek */ 514e985b929SDavid van Moolenbroek struct evutil_addrinfo { 515e985b929SDavid van Moolenbroek int ai_flags; /* AI_PASSIVE, AI_CANONNAME, AI_NUMERICHOST */ 516e985b929SDavid van Moolenbroek int ai_family; /* PF_xxx */ 517e985b929SDavid van Moolenbroek int ai_socktype; /* SOCK_xxx */ 518e985b929SDavid van Moolenbroek int ai_protocol; /* 0 or IPPROTO_xxx for IPv4 and IPv6 */ 519e985b929SDavid van Moolenbroek size_t ai_addrlen; /* length of ai_addr */ 520e985b929SDavid van Moolenbroek char *ai_canonname; /* canonical name for nodename */ 521e985b929SDavid van Moolenbroek struct sockaddr *ai_addr; /* binary address */ 522e985b929SDavid van Moolenbroek struct evutil_addrinfo *ai_next; /* next structure in linked list */ 523e985b929SDavid van Moolenbroek }; 524e985b929SDavid van Moolenbroek #endif 525e985b929SDavid van Moolenbroek /** @name evutil_getaddrinfo() error codes 526e985b929SDavid van Moolenbroek 527e985b929SDavid van Moolenbroek These values are possible error codes for evutil_getaddrinfo() and 528e985b929SDavid van Moolenbroek related functions. 529e985b929SDavid van Moolenbroek 530e985b929SDavid van Moolenbroek @{ 531e985b929SDavid van Moolenbroek */ 532e985b929SDavid van Moolenbroek #ifdef EAI_ADDRFAMILY 533e985b929SDavid van Moolenbroek #define EVUTIL_EAI_ADDRFAMILY EAI_ADDRFAMILY 534e985b929SDavid van Moolenbroek #else 535e985b929SDavid van Moolenbroek #define EVUTIL_EAI_ADDRFAMILY -901 536e985b929SDavid van Moolenbroek #endif 537e985b929SDavid van Moolenbroek #ifdef EAI_AGAIN 538e985b929SDavid van Moolenbroek #define EVUTIL_EAI_AGAIN EAI_AGAIN 539e985b929SDavid van Moolenbroek #else 540e985b929SDavid van Moolenbroek #define EVUTIL_EAI_AGAIN -902 541e985b929SDavid van Moolenbroek #endif 542e985b929SDavid van Moolenbroek #ifdef EAI_BADFLAGS 543e985b929SDavid van Moolenbroek #define EVUTIL_EAI_BADFLAGS EAI_BADFLAGS 544e985b929SDavid van Moolenbroek #else 545e985b929SDavid van Moolenbroek #define EVUTIL_EAI_BADFLAGS -903 546e985b929SDavid van Moolenbroek #endif 547e985b929SDavid van Moolenbroek #ifdef EAI_FAIL 548e985b929SDavid van Moolenbroek #define EVUTIL_EAI_FAIL EAI_FAIL 549e985b929SDavid van Moolenbroek #else 550e985b929SDavid van Moolenbroek #define EVUTIL_EAI_FAIL -904 551e985b929SDavid van Moolenbroek #endif 552e985b929SDavid van Moolenbroek #ifdef EAI_FAMILY 553e985b929SDavid van Moolenbroek #define EVUTIL_EAI_FAMILY EAI_FAMILY 554e985b929SDavid van Moolenbroek #else 555e985b929SDavid van Moolenbroek #define EVUTIL_EAI_FAMILY -905 556e985b929SDavid van Moolenbroek #endif 557e985b929SDavid van Moolenbroek #ifdef EAI_MEMORY 558e985b929SDavid van Moolenbroek #define EVUTIL_EAI_MEMORY EAI_MEMORY 559e985b929SDavid van Moolenbroek #else 560e985b929SDavid van Moolenbroek #define EVUTIL_EAI_MEMORY -906 561e985b929SDavid van Moolenbroek #endif 562e985b929SDavid van Moolenbroek /* This test is a bit complicated, since some MS SDKs decide to 563e985b929SDavid van Moolenbroek * remove NODATA or redefine it to be the same as NONAME, in a 564e985b929SDavid van Moolenbroek * fun interpretation of RFC 2553 and RFC 3493. */ 565e985b929SDavid van Moolenbroek #if defined(EAI_NODATA) && (!defined(EAI_NONAME) || EAI_NODATA != EAI_NONAME) 566e985b929SDavid van Moolenbroek #define EVUTIL_EAI_NODATA EAI_NODATA 567e985b929SDavid van Moolenbroek #else 568e985b929SDavid van Moolenbroek #define EVUTIL_EAI_NODATA -907 569e985b929SDavid van Moolenbroek #endif 570e985b929SDavid van Moolenbroek #ifdef EAI_NONAME 571e985b929SDavid van Moolenbroek #define EVUTIL_EAI_NONAME EAI_NONAME 572e985b929SDavid van Moolenbroek #else 573e985b929SDavid van Moolenbroek #define EVUTIL_EAI_NONAME -908 574e985b929SDavid van Moolenbroek #endif 575e985b929SDavid van Moolenbroek #ifdef EAI_SERVICE 576e985b929SDavid van Moolenbroek #define EVUTIL_EAI_SERVICE EAI_SERVICE 577e985b929SDavid van Moolenbroek #else 578e985b929SDavid van Moolenbroek #define EVUTIL_EAI_SERVICE -909 579e985b929SDavid van Moolenbroek #endif 580e985b929SDavid van Moolenbroek #ifdef EAI_SOCKTYPE 581e985b929SDavid van Moolenbroek #define EVUTIL_EAI_SOCKTYPE EAI_SOCKTYPE 582e985b929SDavid van Moolenbroek #else 583e985b929SDavid van Moolenbroek #define EVUTIL_EAI_SOCKTYPE -910 584e985b929SDavid van Moolenbroek #endif 585e985b929SDavid van Moolenbroek #ifdef EAI_SYSTEM 586e985b929SDavid van Moolenbroek #define EVUTIL_EAI_SYSTEM EAI_SYSTEM 587e985b929SDavid van Moolenbroek #else 588e985b929SDavid van Moolenbroek #define EVUTIL_EAI_SYSTEM -911 589e985b929SDavid van Moolenbroek #endif 590e985b929SDavid van Moolenbroek 591e985b929SDavid van Moolenbroek #define EVUTIL_EAI_CANCEL -90001 592e985b929SDavid van Moolenbroek 593e985b929SDavid van Moolenbroek #ifdef AI_PASSIVE 594e985b929SDavid van Moolenbroek #define EVUTIL_AI_PASSIVE AI_PASSIVE 595e985b929SDavid van Moolenbroek #else 596e985b929SDavid van Moolenbroek #define EVUTIL_AI_PASSIVE 0x1000 597e985b929SDavid van Moolenbroek #endif 598e985b929SDavid van Moolenbroek #ifdef AI_CANONNAME 599e985b929SDavid van Moolenbroek #define EVUTIL_AI_CANONNAME AI_CANONNAME 600e985b929SDavid van Moolenbroek #else 601e985b929SDavid van Moolenbroek #define EVUTIL_AI_CANONNAME 0x2000 602e985b929SDavid van Moolenbroek #endif 603e985b929SDavid van Moolenbroek #ifdef AI_NUMERICHOST 604e985b929SDavid van Moolenbroek #define EVUTIL_AI_NUMERICHOST AI_NUMERICHOST 605e985b929SDavid van Moolenbroek #else 606e985b929SDavid van Moolenbroek #define EVUTIL_AI_NUMERICHOST 0x4000 607e985b929SDavid van Moolenbroek #endif 608e985b929SDavid van Moolenbroek #ifdef AI_NUMERICSERV 609e985b929SDavid van Moolenbroek #define EVUTIL_AI_NUMERICSERV AI_NUMERICSERV 610e985b929SDavid van Moolenbroek #else 611e985b929SDavid van Moolenbroek #define EVUTIL_AI_NUMERICSERV 0x8000 612e985b929SDavid van Moolenbroek #endif 613e985b929SDavid van Moolenbroek #ifdef AI_V4MAPPED 614e985b929SDavid van Moolenbroek #define EVUTIL_AI_V4MAPPED AI_V4MAPPED 615e985b929SDavid van Moolenbroek #else 616e985b929SDavid van Moolenbroek #define EVUTIL_AI_V4MAPPED 0x10000 617e985b929SDavid van Moolenbroek #endif 618e985b929SDavid van Moolenbroek #ifdef AI_ALL 619e985b929SDavid van Moolenbroek #define EVUTIL_AI_ALL AI_ALL 620e985b929SDavid van Moolenbroek #else 621e985b929SDavid van Moolenbroek #define EVUTIL_AI_ALL 0x20000 622e985b929SDavid van Moolenbroek #endif 623e985b929SDavid van Moolenbroek #ifdef AI_ADDRCONFIG 624e985b929SDavid van Moolenbroek #define EVUTIL_AI_ADDRCONFIG AI_ADDRCONFIG 625e985b929SDavid van Moolenbroek #else 626e985b929SDavid van Moolenbroek #define EVUTIL_AI_ADDRCONFIG 0x40000 627e985b929SDavid van Moolenbroek #endif 628e985b929SDavid van Moolenbroek /**@}*/ 629e985b929SDavid van Moolenbroek 630e985b929SDavid van Moolenbroek struct evutil_addrinfo; 631e985b929SDavid van Moolenbroek /** 632e985b929SDavid van Moolenbroek * This function clones getaddrinfo for systems that don't have it. For full 633e985b929SDavid van Moolenbroek * details, see RFC 3493, section 6.1. 634e985b929SDavid van Moolenbroek * 635e985b929SDavid van Moolenbroek * Limitations: 636e985b929SDavid van Moolenbroek * - When the system has no getaddrinfo, we fall back to gethostbyname_r or 637e985b929SDavid van Moolenbroek * gethostbyname, with their attendant issues. 638e985b929SDavid van Moolenbroek * - The AI_V4MAPPED and AI_ALL flags are not currently implemented. 639e985b929SDavid van Moolenbroek * 640e985b929SDavid van Moolenbroek * For a nonblocking variant, see evdns_getaddrinfo. 641e985b929SDavid van Moolenbroek */ 642e985b929SDavid van Moolenbroek int evutil_getaddrinfo(const char *nodename, const char *servname, 643e985b929SDavid van Moolenbroek const struct evutil_addrinfo *hints_in, struct evutil_addrinfo **res); 644e985b929SDavid van Moolenbroek 645e985b929SDavid van Moolenbroek /** Release storage allocated by evutil_getaddrinfo or evdns_getaddrinfo. */ 646e985b929SDavid van Moolenbroek void evutil_freeaddrinfo(struct evutil_addrinfo *ai); 647e985b929SDavid van Moolenbroek 648e985b929SDavid van Moolenbroek const char *evutil_gai_strerror(int err); 649e985b929SDavid van Moolenbroek 650e985b929SDavid van Moolenbroek /** Generate n bytes of secure pseudorandom data, and store them in buf. 651e985b929SDavid van Moolenbroek * 652*0a6a1f1dSLionel Sambuc * Current versions of Libevent use an ARC4-based random number generator, 653*0a6a1f1dSLionel Sambuc * seeded using the platform's entropy source (/dev/urandom on Unix-like 654*0a6a1f1dSLionel Sambuc * systems; CryptGenRandom on Windows). This is not actually as secure as it 655*0a6a1f1dSLionel Sambuc * should be: ARC4 is a pretty lousy cipher, and the current implementation 656*0a6a1f1dSLionel Sambuc * provides only rudimentary prediction- and backtracking-resistance. Don't 657*0a6a1f1dSLionel Sambuc * use this for serious cryptographic applications. 658e985b929SDavid van Moolenbroek */ 659e985b929SDavid van Moolenbroek void evutil_secure_rng_get_bytes(void *buf, size_t n); 660e985b929SDavid van Moolenbroek 661e985b929SDavid van Moolenbroek /** 662e985b929SDavid van Moolenbroek * Seed the secure random number generator if needed, and return 0 on 663e985b929SDavid van Moolenbroek * success or -1 on failure. 664e985b929SDavid van Moolenbroek * 665e985b929SDavid van Moolenbroek * It is okay to call this function more than once; it will still return 666e985b929SDavid van Moolenbroek * 0 if the RNG has been successfully seeded and -1 if it can't be 667e985b929SDavid van Moolenbroek * seeded. 668e985b929SDavid van Moolenbroek * 669e985b929SDavid van Moolenbroek * Ordinarily you don't need to call this function from your own code; 670e985b929SDavid van Moolenbroek * Libevent will seed the RNG itself the first time it needs good random 671e985b929SDavid van Moolenbroek * numbers. You only need to call it if (a) you want to double-check 672e985b929SDavid van Moolenbroek * that one of the seeding methods did succeed, or (b) you plan to drop 673e985b929SDavid van Moolenbroek * the capability to seed (by chrooting, or dropping capabilities, or 674e985b929SDavid van Moolenbroek * whatever), and you want to make sure that seeding happens before your 675e985b929SDavid van Moolenbroek * program loses the ability to do it. 676e985b929SDavid van Moolenbroek */ 677e985b929SDavid van Moolenbroek int evutil_secure_rng_init(void); 678e985b929SDavid van Moolenbroek 679*0a6a1f1dSLionel Sambuc /** 680*0a6a1f1dSLionel Sambuc * Set a filename to use in place of /dev/urandom for seeding the secure 681*0a6a1f1dSLionel Sambuc * PRNG. Return 0 on success, -1 on failure. 682*0a6a1f1dSLionel Sambuc * 683*0a6a1f1dSLionel Sambuc * Call this function BEFORE calling any other initialization or RNG 684*0a6a1f1dSLionel Sambuc * functions. 685*0a6a1f1dSLionel Sambuc * 686*0a6a1f1dSLionel Sambuc * (This string will _NOT_ be copied internally. Do not free it while any 687*0a6a1f1dSLionel Sambuc * user of the secure RNG might be running. Don't pass anything other than a 688*0a6a1f1dSLionel Sambuc * real /dev/...random device file here, or you might lose security.) 689*0a6a1f1dSLionel Sambuc * 690*0a6a1f1dSLionel Sambuc * This API is unstable, and might change in a future libevent version. 691*0a6a1f1dSLionel Sambuc */ 692*0a6a1f1dSLionel Sambuc int evutil_secure_rng_set_urandom_device_file(char *fname); 693*0a6a1f1dSLionel Sambuc 694e985b929SDavid van Moolenbroek /** Seed the random number generator with extra random bytes. 695e985b929SDavid van Moolenbroek 696e985b929SDavid van Moolenbroek You should almost never need to call this function; it should be 697e985b929SDavid van Moolenbroek sufficient to invoke evutil_secure_rng_init(), or let Libevent take 698e985b929SDavid van Moolenbroek care of calling evutil_secure_rng_init() on its own. 699e985b929SDavid van Moolenbroek 700e985b929SDavid van Moolenbroek If you call this function as a _replacement_ for the regular 701e985b929SDavid van Moolenbroek entropy sources, then you need to be sure that your input 702e985b929SDavid van Moolenbroek contains a fairly large amount of strong entropy. Doing so is 703e985b929SDavid van Moolenbroek notoriously hard: most people who try get it wrong. Watch out! 704e985b929SDavid van Moolenbroek 705e985b929SDavid van Moolenbroek @param dat a buffer full of a strong source of random numbers 706e985b929SDavid van Moolenbroek @param datlen the number of bytes to read from datlen 707e985b929SDavid van Moolenbroek */ 708e985b929SDavid van Moolenbroek void evutil_secure_rng_add_bytes(const char *dat, size_t datlen); 709e985b929SDavid van Moolenbroek 710e985b929SDavid van Moolenbroek #ifdef __cplusplus 711e985b929SDavid van Moolenbroek } 712e985b929SDavid van Moolenbroek #endif 713e985b929SDavid van Moolenbroek 714e985b929SDavid van Moolenbroek #endif /* _EVUTIL_H_ */ 715