OpenTTD
os_abstraction.h
Go to the documentation of this file.
1 /* $Id$ */
2 
3 /*
4  * This file is part of OpenTTD.
5  * OpenTTD is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation, version 2.
6  * OpenTTD is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
7  * See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with OpenTTD. If not, see <http://www.gnu.org/licenses/>.
8  */
9 
16 #ifndef NETWORK_CORE_OS_ABSTRACTION_H
17 #define NETWORK_CORE_OS_ABSTRACTION_H
18 
19 /* Include standard stuff per OS */
20 
21 /* Windows stuff */
22 #if defined(_WIN32)
23 #include <errno.h>
24 #include <winsock2.h>
25 #include <ws2tcpip.h>
26 #include <windows.h>
27 
28 #define GET_LAST_ERROR() WSAGetLastError()
29 #undef EWOULDBLOCK
30 #define EWOULDBLOCK WSAEWOULDBLOCK
31 /* Windows has some different names for some types */
32 typedef unsigned long in_addr_t;
33 
34 /* Handle cross-compilation with --build=*-*-cygwin --host=*-*-mingw32 */
35 #if defined(__MINGW32__) && !defined(AI_ADDRCONFIG)
36 # define AI_ADDRCONFIG 0x00000400
37 #endif
38 
39 #if !(defined(__MINGW32__) || defined(__CYGWIN__))
40  /* Windows has some different names for some types */
41  typedef SSIZE_T ssize_t;
42  typedef int socklen_t;
43 # define IPPROTO_IPV6 41
44 #endif /* !(__MINGW32__ && __CYGWIN__) */
45 #endif /* _WIN32 */
46 
47 /* UNIX stuff */
48 #if defined(UNIX) && !defined(__OS2__)
49 # if defined(OPENBSD) || defined(__NetBSD__)
50 # define AI_ADDRCONFIG 0
51 # endif
52 # define SOCKET int
53 # define INVALID_SOCKET -1
54 # define ioctlsocket ioctl
55 # define closesocket close
56 # define GET_LAST_ERROR() (errno)
57 /* Need this for FIONREAD on solaris */
58 # define BSD_COMP
59 
60 /* Includes needed for UNIX-like systems */
61 # include <unistd.h>
62 # include <sys/ioctl.h>
63 # include <sys/socket.h>
64 # include <netinet/in.h>
65 # include <netinet/tcp.h>
66 # include <arpa/inet.h>
67 # include <net/if.h>
68 /* According to glibc/NEWS, <ifaddrs.h> appeared in glibc-2.3. */
69 # if !defined(__sgi__) && !defined(SUNOS) && !defined(__INNOTEK_LIBC__) \
70  && !(defined(__GLIBC__) && (__GLIBC__ <= 2) && (__GLIBC_MINOR__ <= 2)) && !defined(__dietlibc__) && !defined(HPUX)
71 /* If for any reason ifaddrs.h does not exist on your system, comment out
72  * the following two lines and an alternative way will be used to fetch
73  * the list of IPs from the system. */
74 # include <ifaddrs.h>
75 # define HAVE_GETIFADDRS
76 # endif
77 # if !defined(INADDR_NONE)
78 # define INADDR_NONE 0xffffffff
79 # endif
80 
81 # if defined(__GLIBC__) && (__GLIBC__ <= 2) && (__GLIBC_MINOR__ <= 1)
82  typedef uint32_t in_addr_t;
83 # endif
84 
85 # include <errno.h>
86 # include <sys/time.h>
87 # include <netdb.h>
88 #endif /* UNIX */
89 
90 /* OS/2 stuff */
91 #if defined(__OS2__)
92 # define SOCKET int
93 # define INVALID_SOCKET -1
94 # define ioctlsocket ioctl
95 # define closesocket close
96 # define GET_LAST_ERROR() (sock_errno())
97 
98 /* Includes needed for OS/2 systems */
99 # include <types.h>
100 # include <unistd.h>
101 # include <sys/ioctl.h>
102 # include <sys/socket.h>
103 # include <netinet/in.h>
104 # include <netinet/tcp.h>
105 # include <arpa/inet.h>
106 # include <net/if.h>
107 # include <errno.h>
108 # include <sys/time.h>
109 # include <netdb.h>
110 # include <nerrno.h>
111 # define INADDR_NONE 0xffffffff
112 # include "../../3rdparty/os2/getaddrinfo.h"
113 # include "../../3rdparty/os2/getnameinfo.h"
114 
115 #define IPV6_V6ONLY 27
116 
117 /*
118  * IPv6 address
119  */
120 struct in6_addr {
121  union {
122  uint8_t __u6_addr8[16];
123  uint16_t __u6_addr16[8];
124  uint32_t __u6_addr32[4];
125  } __u6_addr; /* 128-bit IP6 address */
126 };
127 
128 #define s6_addr __u6_addr.__u6_addr8
129 
130 struct sockaddr_in6 {
131  uint8_t sin6_len; /* length of this struct */
132  sa_family_t sin6_family; /* AF_INET6 */
133  in_port_t sin6_port; /* Transport layer port # */
134  uint32_t sin6_flowinfo; /* IP6 flow information */
135  struct in6_addr sin6_addr; /* IP6 address */
136  uint32_t sin6_scope_id; /* scope zone index */
137 };
138 
139 typedef int socklen_t;
140 #if !defined(__INNOTEK_LIBC__)
141 typedef unsigned long in_addr_t;
142 #endif /* __INNOTEK_LIBC__ */
143 
144 #endif /* OS/2 */
145 
151 static inline bool SetNonBlocking(SOCKET d)
152 {
153 #ifdef _WIN32
154  u_long nonblocking = 1;
155 #else
156  int nonblocking = 1;
157 #endif
158  return ioctlsocket(d, FIONBIO, &nonblocking) == 0;
159 }
160 
166 static inline bool SetNoDelay(SOCKET d)
167 {
168  /* XXX should this be done at all? */
169  int b = 1;
170  /* The (const char*) cast is needed for windows */
171  return setsockopt(d, IPPROTO_TCP, TCP_NODELAY, (const char*)&b, sizeof(b)) == 0;
172 }
173 
174 /* Make sure these structures have the size we expect them to be */
175 assert_compile(sizeof(in_addr) == 4);
176 assert_compile(sizeof(in6_addr) == 16);
177 
178 #endif /* NETWORK_CORE_OS_ABSTRACTION_H */
static bool SetNonBlocking(SOCKET d)
Try to set the socket into non-blocking mode.
assert_compile(sizeof(in_addr)==4)
IPv4 addresses should be 4 bytes.
static bool SetNoDelay(SOCKET d)
Try to set the socket to not delay sending.