2 * WSOCK32 specific functions
4 * Copyright (C) 2001 Stefan Leichter
6 * This library is free software; you can redistribute it and/or
7 * modify it under the terms of the GNU Lesser General Public
8 * License as published by the Free Software Foundation; either
9 * version 2.1 of the License, or (at your option) any later version.
11 * This library is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
14 * Lesser General Public License for more details.
16 * You should have received a copy of the GNU Lesser General Public
17 * License along with this library; if not, write to the Free Software
18 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
21 /* All we need are a couple constants for EnumProtocols. Once it is
22 * moved to ws2_32 we may no longer need it
32 #include <sys/types.h>
33 #ifdef HAVE_SYS_SOCKET_H
34 #include <sys/socket.h>
36 #ifdef HAVE_NETINET_IN_H
37 # include <netinet/in.h>
39 #ifdef HAVE_ARPA_INET_H
40 #include <arpa/inet.h>
55 #include "wine/unicode.h"
56 #include "wine/debug.h"
58 WINE_DEFAULT_DEBUG_CHANNEL(winsock);
60 /* name of the protocols
62 static WCHAR NameIpx[] = {'I', 'P', 'X', '\0'};
63 static WCHAR NameSpx[] = {'S', 'P', 'X', '\0'};
64 static WCHAR NameSpxII[] = {'S', 'P', 'X', ' ', 'I', 'I', '\0'};
65 static WCHAR NameTcp[] = {'T', 'C', 'P', '/', 'I', 'P', '\0'};
66 static WCHAR NameUdp[] = {'U', 'D', 'P', '/', 'I', 'P', '\0'};
68 /*****************************************************************************
69 * WSOCK32_EnterSingleProtocol [internal]
71 * enters the protocol informations of one given protocol into the
72 * given buffer. If the given buffer is too small only the required size for
73 * the protocols are returned.
76 * The number of protocols entered into the buffer
79 * - only implemented for IPX, SPX, SPXII, TCP, UDP
80 * - there is no check that the operating system supports the returned
83 static INT WSOCK32_EnterSingleProtocol( INT iProtocol,
84 PROTOCOL_INFOA* lpBuffer,
85 LPDWORD lpSize, BOOL unicode)
86 { DWORD dwLength = 0, dwOldSize = *lpSize;
88 WCHAR *lpProtName = NULL;
90 *lpSize = sizeof( PROTOCOL_INFOA);
93 dwLength = (unicode) ? sizeof(WCHAR) * (strlenW(NameTcp)+1) :
94 WideCharToMultiByte( CP_ACP, 0, NameTcp, -1,
98 dwLength = (unicode) ? sizeof(WCHAR) * (strlenW(NameUdp)+1) :
99 WideCharToMultiByte( CP_ACP, 0, NameUdp, -1,
100 NULL, 0, NULL, NULL);
103 dwLength = (unicode) ? sizeof(WCHAR) * (strlenW(NameIpx)+1) :
104 WideCharToMultiByte( CP_ACP, 0, NameIpx, -1,
105 NULL, 0, NULL, NULL);
108 dwLength = (unicode) ? sizeof(WCHAR) * (strlenW(NameSpx)+1) :
109 WideCharToMultiByte( CP_ACP, 0, NameSpx, -1,
110 NULL, 0, NULL, NULL);
113 dwLength = (unicode) ? sizeof(WCHAR) * (strlenW(NameSpxII)+1) :
114 WideCharToMultiByte( CP_ACP, 0, NameSpxII, -1,
115 NULL, 0, NULL, NULL);
119 if ((iProtocol == ISOPROTO_TP4) || (iProtocol == NSPROTO_SPX))
120 FIXME("Protocol <%s> not implemented\n",
121 (iProtocol == ISOPROTO_TP4) ? "ISOPROTO_TP4" : "NSPROTO_SPX");
123 FIXME("unknown Protocol <0x%08x>\n", iProtocol);
128 if ( !lpBuffer || !*lpSize || (*lpSize > dwOldSize))
131 memset( lpBuffer, 0, dwOldSize);
133 lpBuffer->lpProtocol = (LPSTR) &lpBuffer[ iAnz];
134 lpBuffer->iProtocol = iProtocol;
137 case WS_IPPROTO_TCP :
138 lpBuffer->dwServiceFlags = XP_FRAGMENTATION | XP_EXPEDITED_DATA |
139 XP_GRACEFUL_CLOSE | XP_GUARANTEED_ORDER |
140 XP_GUARANTEED_DELIVERY;
141 lpBuffer->iAddressFamily = WS_AF_INET;
142 lpBuffer->iMaxSockAddr = 0x10; /* NT4 SP5 */
143 lpBuffer->iMinSockAddr = 0x10; /* NT4 SP5 */
144 lpBuffer->iSocketType = SOCK_STREAM;
145 lpBuffer->dwMessageSize = 0;
146 lpProtName = NameTcp;
148 case WS_IPPROTO_UDP :
149 lpBuffer->dwServiceFlags = XP_FRAGMENTATION | XP_SUPPORTS_BROADCAST |
150 XP_SUPPORTS_MULTICAST | XP_MESSAGE_ORIENTED |
152 lpBuffer->iAddressFamily = WS_AF_INET;
153 lpBuffer->iMaxSockAddr = 0x10; /* NT4 SP5 */
154 lpBuffer->iMinSockAddr = 0x10; /* NT4 SP5 */
155 lpBuffer->iSocketType = SOCK_DGRAM;
156 lpBuffer->dwMessageSize = 65457; /* NT4 SP5 */
157 lpProtName = NameUdp;
160 lpBuffer->dwServiceFlags = XP_FRAGMENTATION | XP_SUPPORTS_BROADCAST |
161 XP_SUPPORTS_MULTICAST | XP_MESSAGE_ORIENTED |
163 lpBuffer->iAddressFamily = WS_AF_IPX;
164 lpBuffer->iMaxSockAddr = 0x10; /* NT4 SP5 */
165 lpBuffer->iMinSockAddr = 0x0e; /* NT4 SP5 */
166 lpBuffer->iSocketType = SOCK_DGRAM;
167 lpBuffer->dwMessageSize = 576; /* NT4 SP5 */
168 lpProtName = NameIpx;
171 lpBuffer->dwServiceFlags = XP_FRAGMENTATION |
172 XP_PSEUDO_STREAM | XP_MESSAGE_ORIENTED |
173 XP_GUARANTEED_ORDER | XP_GUARANTEED_DELIVERY;
174 lpBuffer->iAddressFamily = WS_AF_IPX;
175 lpBuffer->iMaxSockAddr = 0x10; /* NT4 SP5 */
176 lpBuffer->iMinSockAddr = 0x0e; /* NT4 SP5 */
177 lpBuffer->iSocketType = 5;
178 lpBuffer->dwMessageSize = -1; /* NT4 SP5 */
179 lpProtName = NameSpx;
182 lpBuffer->dwServiceFlags = XP_FRAGMENTATION | XP_GRACEFUL_CLOSE |
183 XP_PSEUDO_STREAM | XP_MESSAGE_ORIENTED |
184 XP_GUARANTEED_ORDER | XP_GUARANTEED_DELIVERY;
185 lpBuffer->iAddressFamily = WS_AF_IPX;
186 lpBuffer->iMaxSockAddr = 0x10; /* NT4 SP5 */
187 lpBuffer->iMinSockAddr = 0x0e; /* NT4 SP5 */
188 lpBuffer->iSocketType = 5;
189 lpBuffer->dwMessageSize = -1; /* NT4 SP5 */
190 lpProtName = NameSpxII;
194 strcpyW( (LPWSTR)lpBuffer->lpProtocol, lpProtName);
196 WideCharToMultiByte( CP_ACP, 0, lpProtName, -1, lpBuffer->lpProtocol,
197 dwOldSize - iAnz * sizeof( PROTOCOL_INFOA), NULL, NULL);
202 /* FIXME: EnumProtocols should be moved to winsock2, and this should be
203 * implemented by calling out to WSAEnumProtocols. See:
204 * http://support.microsoft.com/support/kb/articles/Q129/3/15.asp
206 /*****************************************************************************
207 * WSOCK32_EnumProtocol [internal]
209 * Enters the information about installed protocols into a given buffer
212 * SOCKET_ERROR if the buffer is to small for the requested protocol infos
213 * on success the number of protocols inside the buffer
216 * NT4SP5 does not return SPX if lpiProtocols == NULL
219 * - NT4SP5 returns in addition these list of NETBIOS protocols
220 * (address family 17), each entry two times one for socket type 2 and 5
222 * iProtocol lpProtocol
223 * 0x80000000 \Device\NwlnkNb
224 * 0xfffffffa \Device\NetBT_CBENT7
225 * 0xfffffffb \Device\Nbf_CBENT7
226 * 0xfffffffc \Device\NetBT_NdisWan5
227 * 0xfffffffd \Device\NetBT_El9202
228 * 0xfffffffe \Device\Nbf_El9202
229 * 0xffffffff \Device\Nbf_NdisWan4
231 * - there is no check that the operating system supports the returned
234 static INT WSOCK32_EnumProtocol( LPINT lpiProtocols, PROTOCOL_INFOA* lpBuffer,
235 LPDWORD lpdwLength, BOOL unicode)
236 { DWORD dwCurSize, dwOldSize = *lpdwLength, dwTemp;
238 INT iLocal[] = { WS_IPPROTO_TCP, WS_IPPROTO_UDP, NSPROTO_IPX, NSPROTO_SPXII, 0};
240 if (!lpiProtocols) lpiProtocols = iLocal;
243 while ( *lpiProtocols )
245 WSOCK32_EnterSingleProtocol( *lpiProtocols, NULL, &dwCurSize, unicode);
247 if ( lpBuffer && dwCurSize && ((*lpdwLength + dwCurSize) <= dwOldSize))
248 { /* reserve the required space for the current protocol_info after the
249 * last protocol_info before the start of the string buffer and adjust
250 * the references into the string buffer
252 memmove( &((char*)&lpBuffer[ anz])[dwCurSize],
254 *lpdwLength - anz * sizeof( PROTOCOL_INFOA));
255 for (i=0; i < anz; i++)
256 lpBuffer[i].lpProtocol += dwCurSize;
259 anz += WSOCK32_EnterSingleProtocol( *lpiProtocols, &lpBuffer[anz],
263 *lpdwLength += dwCurSize;
267 if (dwOldSize < *lpdwLength) anz = SOCKET_ERROR;
272 /*****************************************************************************
273 * EnumProtocolsA [WSOCK32.1111]
275 * see function WSOCK32_EnumProtocol for RETURNS, BUGS
277 INT WINAPI EnumProtocolsA( LPINT lpiProtocols, LPVOID lpBuffer,
280 return WSOCK32_EnumProtocol( lpiProtocols, (PROTOCOL_INFOA*) lpBuffer,
284 /*****************************************************************************
285 * EnumProtocolsW [WSOCK32.1112]
287 * see function WSOCK32_EnumProtocol for RETURNS, BUGS
289 INT WINAPI EnumProtocolsW( LPINT lpiProtocols, LPVOID lpBuffer,
292 return WSOCK32_EnumProtocol( lpiProtocols, (PROTOCOL_INFOA*) lpBuffer,
296 /*****************************************************************************
297 * inet_network [WSOCK32.1100]
299 UINT WINAPI WSOCK32_inet_network(const char *cp)
301 #ifdef HAVE_INET_NETWORK
302 return inet_network(cp);
308 /*****************************************************************************
309 * getnetbyname [WSOCK32.1101]
311 struct netent * WINAPI WSOCK32_getnetbyname(const char *name)
313 #ifdef HAVE_GETNETBYNAME
314 return getnetbyname(name);