Remove building with NOCRYPTO option
[minix.git] / external / bsd / bind / dist / contrib / idn / idnkit-1.0-src / wsock / wsock20 / dllfunc.c
blobebe4b918d3ab5ebd397b45a0b2d854eb477eda95
1 /* $NetBSD: dllfunc.c,v 1.3 2014/12/10 04:37:56 christos Exp $ */
3 /*
4 * dllfunc.c - wrapper functions
5 */
7 /*
8 * Copyright (c) 2000,2002 Japan Network Information Center.
9 * All rights reserved.
11 * By using this file, you agree to the terms and conditions set forth bellow.
13 * LICENSE TERMS AND CONDITIONS
15 * The following License Terms and Conditions apply, unless a different
16 * license is obtained from Japan Network Information Center ("JPNIC"),
17 * a Japanese association, Kokusai-Kougyou-Kanda Bldg 6F, 2-3-4 Uchi-Kanda,
18 * Chiyoda-ku, Tokyo 101-0047, Japan.
20 * 1. Use, Modification and Redistribution (including distribution of any
21 * modified or derived work) in source and/or binary forms is permitted
22 * under this License Terms and Conditions.
24 * 2. Redistribution of source code must retain the copyright notices as they
25 * appear in each source code file, this License Terms and Conditions.
27 * 3. Redistribution in binary form must reproduce the Copyright Notice,
28 * this License Terms and Conditions, in the documentation and/or other
29 * materials provided with the distribution. For the purposes of binary
30 * distribution the "Copyright Notice" refers to the following language:
31 * "Copyright (c) 2000-2002 Japan Network Information Center. All rights reserved."
33 * 4. The name of JPNIC may not be used to endorse or promote products
34 * derived from this Software without specific prior written approval of
35 * JPNIC.
37 * 5. Disclaimer/Limitation of Liability: THIS SOFTWARE IS PROVIDED BY JPNIC
38 * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
39 * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A
40 * PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL JPNIC BE LIABLE
41 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
42 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
43 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR
44 * BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
45 * WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
46 * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
47 * ADVISED OF THE POSSIBILITY OF SUCH DAMAGES.
50 #include <windows.h>
51 #include <svcguid.h>
52 #include <stdio.h>
53 #include <stdlib.h>
54 #include <string.h>
55 #include <process.h>
57 #include "dlldef.h"
59 #ifndef EAI_MEMORY
60 #define EAI_MEMORY WSA_NOT_ENOUGH_MEMORY
61 #endif
62 #ifndef EAI_FAIL
63 #define EAI_FAIL WSANO_RECOVERY
64 #endif
66 static GUID guid_habn = SVCID_INET_HOSTADDRBYNAME;
67 static GUID guid_habis = SVCID_INET_HOSTADDRBYINETSTRING;
69 #define SVCID_IS_HABN(p) (memcmp(p, &guid_habn, sizeof(GUID)) == 0)
70 #define SVCID_IS_HABIS(p) (memcmp(p, &guid_habis, sizeof(GUID)) == 0)
73 * Rename addrinfo to my_addrinfo for avoiding possible name conflict.
75 struct my_addrinfo {
76 int ai_flags;
77 int ai_family;
78 int ai_socktype;
79 int ai_protocol;
80 size_t ai_addrlen;
81 char *ai_canonname;
82 struct sockaddr *ai_addr;
83 struct my_addrinfo *ai_next;
86 typedef struct obj_lock {
87 void *key;
88 struct obj_lock *next;
89 } obj_lock_t;
91 #define OBJLOCKHASH_SIZE 127
92 static obj_lock_t *obj_lock_hash[OBJLOCKHASH_SIZE];
94 static int obj_hash(void *key);
95 static int obj_islocked(void *key);
96 static void obj_lock(void *key);
97 static void obj_unlock(void *key);
98 static char *decode_name_dynamic(const char *name, idn_resconf_t idnctx);
99 static struct my_addrinfo
100 *copy_decode_addrinfo_dynamic(struct my_addrinfo *aip,
101 idn_resconf_t idnctx);
102 static void free_copied_addrinfo(struct my_addrinfo *aip);
104 WRAPPER_EXPORT int WSAAPI
105 gethostname(char FAR * name, int namelen) {
106 int ret;
108 TRACE("ENTER gethostname\n");
109 ret = _org_gethostname(name, namelen);
110 TRACE("LEAVE gethostname %d <%-.100s>\n", ret, name);
112 return (ret);
115 WRAPPER_EXPORT struct hostent FAR * WSAAPI
116 gethostbyname(const char FAR * name) {
117 struct hostent FAR *ret;
118 char nbuff[256];
119 char hbuff[256];
120 BOOL stat;
121 idn_resconf_t encodeCtx;
123 TRACE("ENTER gethostbyname <%-.100s>\n",
124 (name != NULL ? name : "NULL"));
126 encodeCtx = idnGetContext();
128 if (encodeCtx == NULL || name == NULL) {
129 ret = _org_gethostbyname(name);
130 } else {
131 stat = idnConvReq(encodeCtx, name, nbuff, sizeof(nbuff));
132 if (stat == FALSE) {
133 TRACE("idnConvReq failed\n");
134 ret = NULL;
135 } else {
136 TRACE("Converted Name <%s>\n",
137 dumpName(nbuff, hbuff, sizeof(hbuff)));
138 ret = _org_gethostbyname(nbuff);
142 if (ret != NULL && encodeCtx != NULL) {
143 TRACE("Resulting Name <%s>\n",
144 dumpName(ret->h_name, hbuff, sizeof(hbuff)));
145 stat = idnConvRsp(encodeCtx, ret->h_name,
146 nbuff, sizeof(nbuff));
147 if (stat == FALSE) {
148 TRACE("Decoding failed - return the name verbatim\n");
149 } else {
150 TRACE("Converted Back <%s>\n",
151 dumpName(nbuff, hbuff, sizeof(hbuff)));
152 strcpy(ret->h_name, nbuff);
156 if (ret == NULL) {
157 TRACE("LEAVE gethostbyname NULL\n");
158 } else {
159 TRACE("LEAVE gethostbyname <%s>\n",
160 dumpHost(ret, hbuff, sizeof(hbuff)));
162 return (ret);
165 WRAPPER_EXPORT struct hostent FAR * WSAAPI
166 gethostbyaddr(const char FAR * addr, int len, int type) {
167 struct hostent FAR *ret;
168 char nbuff[256];
169 char abuff[256];
170 char hbuff[256];
171 BOOL stat;
172 idn_resconf_t encodeCtx;
174 TRACE("ENTER gethostbyaddr <%s>\n",
175 dumpAddr(addr, len, abuff, sizeof(abuff)));
177 encodeCtx = idnGetContext();
179 ret = _org_gethostbyaddr(addr, len, type);
181 if (ret != NULL && encodeCtx != NULL) {
182 TRACE("Resulting Name <%s>\n",
183 dumpName(ret->h_name, hbuff, sizeof(hbuff)));
184 stat = idnConvRsp(encodeCtx, ret->h_name,
185 nbuff, sizeof(nbuff));
186 if (stat == FALSE) {
187 TRACE("Decoding failed - return the name verbatim\n");
188 } else {
189 TRACE("Converted Back <%s>\n",
190 dumpName(nbuff, hbuff, sizeof(hbuff)));
191 strcpy(ret->h_name, nbuff);
195 if (ret == NULL) {
196 TRACE("LEAVE gethostbyaddr NULL\n");
197 } else {
198 TRACE("LEAVE gethostbyaddr <%s>\n",
199 dumpHost(ret, hbuff, sizeof(hbuff)));
201 return (ret);
204 WRAPPER_EXPORT HANDLE WSAAPI
205 WSAAsyncGetHostByName(HWND hWnd, u_int wMsg,
206 const char FAR * name, char FAR * buf, int buflen)
208 HANDLE ret;
209 char nbuff[256];
210 char hbuff[256];
211 idn_resconf_t encodeCtx;
213 TRACE("ENTER WSAAsyncGetHostByName <%-.100s>\n", name);
215 encodeCtx = idnGetContext();
217 if (encodeCtx == NULL || name == NULL) {
218 ret = _org_WSAAsyncGetHostByName(hWnd, wMsg,
219 name, buf, buflen);
220 } else {
221 idnHook(hWnd, wMsg, buf, encodeCtx);
222 idnConvReq(encodeCtx, name, nbuff, sizeof(nbuff));
223 TRACE("Converted Name <%s>\n",
224 dumpName(nbuff, hbuff, sizeof(hbuff)));
225 ret = _org_WSAAsyncGetHostByName(hWnd, wMsg, nbuff,
226 buf, buflen);
229 TRACE("LEAVE WSAAsyncGetHostByName HANDLE %08x\n", ret);
231 return (ret);
234 WRAPPER_EXPORT HANDLE WSAAPI
235 WSAAsyncGetHostByAddr(HWND hWnd, u_int wMsg, const char FAR * addr,
236 int len, int type, char FAR * buf, int buflen)
238 HANDLE ret;
239 char abuff[256];
240 idn_resconf_t encodeCtx;
242 encodeCtx = idnGetContext();
244 if (encodeCtx != NULL) {
245 idnHook(hWnd, wMsg, buf, encodeCtx);
248 TRACE("ENTER WSAAsyncGetHostByAddr <%s>\n",
249 dumpAddr(addr, len, abuff, sizeof(abuff)));
250 ret = _org_WSAAsyncGetHostByAddr(hWnd, wMsg, addr, len, type,
251 buf, buflen);
252 TRACE("LEAVE WSAAsyncGetHostByAddr HANDLE %08x\n", ret);
254 return (ret);
257 WRAPPER_EXPORT INT WSAAPI
258 WSALookupServiceBeginA(LPWSAQUERYSETA lpqsRestrictions,
259 DWORD dwControlFlags, LPHANDLE lphLookup)
261 INT ret;
262 char nbuff[256];
263 char hbuff[256];
264 LPSTR name = lpqsRestrictions->lpszServiceInstanceName;
265 LPGUID class = lpqsRestrictions->lpServiceClassId;
266 idn_resconf_t encodeCtx;
268 TRACE("ENTER WSALookupServiceBeginA <%-.100s>\n",
269 name == NULL ? "<NULL>" : name);
271 encodeCtx = idnGetContext();
273 if (name != NULL && encodeCtx != NULL && SVCID_IS_HABN(class) == 0) {
274 idnConvReq(encodeCtx, name, nbuff, sizeof(nbuff));
275 TRACE("Converted Name <%s>\n",
276 dumpName(nbuff, hbuff, sizeof(hbuff)));
277 /* strcpy(lpqsRestrictions->lpszQueryString, nbuff); */
278 lpqsRestrictions->lpszServiceInstanceName = nbuff;
280 ret = _org_WSALookupServiceBeginA(lpqsRestrictions,
281 dwControlFlags, lphLookup);
282 TRACE("LEAVE WSALookupServiceBeginA %d\n", ret);
284 return (ret);
287 WRAPPER_EXPORT INT WSAAPI
288 WSALookupServiceNextA(HANDLE hLookup, DWORD dwControlFlags,
289 LPDWORD lpdwBufferLength, LPWSAQUERYSETA lpqsResults)
291 INT ret;
292 char nbuff[256];
293 char hbuff[256];
294 LPGUID class;
295 idn_resconf_t encodeCtx;
297 TRACE("ENTER WSALookupServiceNextA\n");
299 encodeCtx = idnGetContext();
301 ret = _org_WSALookupServiceNextA(hLookup, dwControlFlags,
302 lpdwBufferLength, lpqsResults);
303 class = lpqsResults->lpServiceClassId;
305 if (ret == 0 &&
306 encodeCtx != NULL &&
307 (dwControlFlags & LUP_RETURN_NAME) &&
308 (SVCID_IS_HABN(class) || SVCID_IS_HABIS(class))) {
309 TRACE("Resulting Name <%s>\n",
310 dumpName(lpqsResults->lpszServiceInstanceName,
311 hbuff, sizeof(hbuff)));
312 if (idnConvRsp(encodeCtx,
313 lpqsResults->lpszServiceInstanceName,
314 nbuff, sizeof(nbuff)) == FALSE) {
315 TRACE("Decoding failed - return the name verbatim\n");
316 } else {
317 TRACE("Converted Back <%s>\n",
318 dumpName(nbuff, hbuff, sizeof(hbuff)));
319 strcpy(lpqsResults->lpszServiceInstanceName, nbuff);
322 TRACE("LEAVE WSALookupServiceNextA %d <%s>\n", ret, nbuff);
324 return (ret);
327 WRAPPER_EXPORT INT WSAAPI
328 WSALookupServiceBeginW(LPWSAQUERYSETW lpqsRestrictions,
329 DWORD dwControlFlags, LPHANDLE lphLookup)
331 INT ret;
333 TRACE("ENTER WSALookupServiceBeginW\n");
334 ret = _org_WSALookupServiceBeginW(lpqsRestrictions,
335 dwControlFlags,lphLookup);
336 TRACE("LEAVE WSALookupServiceBeginW %d\n", ret);
338 return (ret);
341 WRAPPER_EXPORT INT WSAAPI
342 WSALookupServiceNextW(HANDLE hLookup, DWORD dwControlFlags,
343 LPDWORD lpdwBufferLength, LPWSAQUERYSETW lpqsResults)
345 INT ret;
347 TRACE("ENTER WSALookupServiceNextW\n");
348 ret = _org_WSALookupServiceNextW(hLookup, dwControlFlags,
349 lpdwBufferLength, lpqsResults);
350 TRACE("LEAVE WSALookupServiceNextW %d\n", ret);
352 return (ret);
355 WRAPPER_EXPORT INT WSAAPI
356 WSALookupServiceEnd(HANDLE hLookup) {
357 INT ret;
359 TRACE("ENTER WSALookupServiceEnd\n");
360 ret = _org_WSALookupServiceEnd(hLookup);
361 TRACE("LEAVE WSALookupServiceEnd %d\n", ret);
363 return (ret);
366 static int
367 obj_hash(void *key) {
369 * Hash function for obj_*.
370 * 'key' is supposed to be an address.
372 unsigned long v = (unsigned long)key;
374 return ((v >> 3) % OBJLOCKHASH_SIZE);
377 static int
378 obj_islocked(void *key)
381 * Check if the object specified by 'key' is locked.
382 * Return 1 if so, 0 otherwise.
384 int h = obj_hash(key);
385 obj_lock_t *olp = obj_lock_hash[h];
387 while (olp != NULL) {
388 if (olp->key == key)
389 return (1);
390 olp = olp->next;
392 return (0);
395 static void
396 obj_lock(void *key)
399 * Lock an object specified by 'key'.
401 int h = obj_hash(key);
402 obj_lock_t *olp;
404 olp = malloc(sizeof(obj_lock_t));
405 if (olp != NULL) {
406 olp->key = key;
407 olp->next = obj_lock_hash[h];
408 obj_lock_hash[h] = olp;
412 static void
413 obj_unlock(void *key)
416 * Unlock an object specified by 'key'.
418 int h = obj_hash(key);
419 obj_lock_t *olp, *olp0;
421 olp = obj_lock_hash[h];
422 olp0 = NULL;
423 while (olp != NULL) {
424 if (olp->key == key) {
425 if (olp0 == NULL)
426 obj_lock_hash[h] = olp->next;
427 else
428 olp0->next = olp->next;
429 free(olp);
430 return;
432 olp0 = olp;
433 olp = olp->next;
437 static char *
438 decode_name_dynamic(const char *name, idn_resconf_t idnctx) {
439 BOOL stat;
440 char buf[256], tmp[256];
441 char *s;
443 if (idnConvRsp(idnctx, name, buf, sizeof(buf)) == TRUE) {
444 TRACE("Converted Back <%s>\n",
445 dumpName(buf, tmp, sizeof(tmp)));
446 name = buf;
447 } else {
448 TRACE("Decoding failed - return the name verbatim\n");
450 s = malloc(strlen(name) + 1);
451 if (s == NULL)
452 return (NULL);
453 else
454 return (strcpy(s, name));
457 static struct my_addrinfo *
458 copy_decode_addrinfo_dynamic(struct my_addrinfo *aip, idn_resconf_t idnctx)
460 struct my_addrinfo *newaip;
462 if (aip == NULL)
463 return (NULL);
465 newaip = malloc(sizeof(struct my_addrinfo) + aip->ai_addrlen);
466 if (newaip == NULL)
467 return (NULL);
469 *newaip = *aip;
470 newaip->ai_addr = (struct sockaddr *)(newaip + 1);
471 memcpy(newaip->ai_addr, aip->ai_addr, aip->ai_addrlen);
473 if (newaip->ai_canonname != NULL)
474 newaip->ai_canonname = decode_name_dynamic(aip->ai_canonname,
475 idnctx);
477 newaip->ai_next = copy_decode_addrinfo_dynamic(aip->ai_next, idnctx);
478 return (newaip);
481 static void
482 free_copied_addrinfo(struct my_addrinfo *aip) {
483 while (aip != NULL) {
484 struct my_addrinfo *next = aip->ai_next;
486 if (aip->ai_canonname != NULL)
487 free(aip->ai_canonname);
488 free(aip);
489 aip = next;
493 WRAPPER_EXPORT int WSAAPI
494 getaddrinfo(const char *nodename, const char *servname,
495 const struct my_addrinfo *hints, struct my_addrinfo **res)
497 char namebuf[256];
498 BOOL stat;
499 struct my_addrinfo *aip;
500 int err;
501 idn_resconf_t encodeCtx;
503 TRACE("ENTER getaddrinfo <%-.100s>\n", nodename ? nodename : "NULL");
505 encodeCtx = idnGetContext();
507 if (nodename == NULL || encodeCtx == NULL) {
508 TRACE("conversion unnecessary\n");
509 err = _org_getaddrinfo(nodename, servname, hints, res);
510 } else {
511 stat = idnConvReq(encodeCtx, nodename,
512 namebuf, sizeof(namebuf));
513 if (stat == TRUE) {
514 nodename = namebuf;
515 TRACE("Converted Name <%-.100s>\n", namebuf);
518 err = _org_getaddrinfo(nodename, servname, hints, &aip);
519 if (err == 0 && aip != NULL) {
520 *res = copy_decode_addrinfo_dynamic(aip, encodeCtx);
521 if (*res == NULL)
522 err = EAI_FAIL;
523 else
524 obj_lock(*res);
525 if (aip != NULL)
526 _org_freeaddrinfo(aip);
530 TRACE("LEAVE getaddrinfo %d\n", err);
531 return (err);
534 WRAPPER_EXPORT void WSAAPI
535 freeaddrinfo(struct my_addrinfo *aip) {
536 TRACE("ENTER freeaddrinfo aip=%p\n", (void *)aip);
538 if (obj_islocked(aip)) {
540 * We allocated the data.
542 obj_unlock(aip);
543 free_copied_addrinfo(aip);
544 } else {
546 * It was allocated the original getaddrinfo().
548 TRACE("Not allocated by the wrapper\n");
549 _org_freeaddrinfo(aip);
551 TRACE("LEAVE freeaddrinfo\n");
554 WRAPPER_EXPORT int WSAAPI
555 getnameinfo(const struct sockaddr *sa, DWORD salen,
556 char *host, DWORD hostlen, char *serv,
557 DWORD servlen, int flags)
559 char name[256];
560 size_t namelen = sizeof(name);
561 int code;
562 BOOL stat;
563 idn_resconf_t encodeCtx;
565 TRACE("ENTER getnameinfo\n");
567 encodeCtx = idnGetContext();
569 if (host == NULL || hostlen == 0 || encodeCtx == NULL) {
570 TRACE("conversion unnecessary\n");
571 code = _org_getnameinfo(sa, salen, host, hostlen,
572 serv, servlen, flags);
573 } else {
574 code = _org_getnameinfo(sa, salen, name, namelen,
575 serv, servlen, flags);
576 if (code == 0 && name[0] != '\0') {
577 stat = idnConvRsp(encodeCtx, name, host, hostlen);
578 if (stat == FALSE) {
579 TRACE("Decoding failed - return the name verbatim\n");
580 if (strlen(name) >= hostlen) {
581 code = EAI_FAIL;
582 } else {
583 strcpy(host, name);
585 } else {
586 TRACE("Converted Back <%s>\n",
587 dumpName(host, name, sizeof(name)));
592 TRACE("LEAVE getnameinfo %d\n", code);
593 return (code);