From 8581b74a84aefc43aa3491f38a8cd5516d4527b4 Mon Sep 17 00:00:00 2001 From: leitner Date: Sat, 19 Apr 2014 17:45:14 +0000 Subject: [PATCH] on FreeBSD, on a PF_INET6 socket, recvfrom and friends can actually return a sockaddr with family PF_INET. WTF? Work around that. --- array/array_allocate.3 | 6 ++++++ socket/socket_accept6.c | 2 +- socket/socket_local6.c | 2 +- socket/socket_recv6.c | 2 +- socket/socket_remote6.c | 2 +- 5 files changed, 10 insertions(+), 4 deletions(-) diff --git a/array/array_allocate.3 b/array/array_allocate.3 index 2a13c0a..c9edb4b 100644 --- a/array/array_allocate.3 +++ b/array/array_allocate.3 @@ -47,5 +47,11 @@ not enough memory is available. array_allocate does \fInot\fR change \fIx\fR to have failed; if you want to do that, use array_fail. +.SH PERFORMANCE +This function can call realloc when the array needs to be enlarged. +Under exceptional circumstances, this can lead to blocking the current thread. +It will also zero-fill the newly enlarged part of the array, leading to +all pages being mapped in by the operating system. If a small array is +enlarged to a very large array, this can lead to swapping and blocking. .SH "SEE ALSO" array_get(3), array_start(3), array_fail(3) diff --git a/socket/socket_accept6.c b/socket/socket_accept6.c index cad1c37..9aa2dcb 100644 --- a/socket/socket_accept6.c +++ b/socket/socket_accept6.c @@ -87,7 +87,7 @@ incoming: #endif #ifdef LIBC_HAS_IP6 - if (sa.sin6_family==AF_INET) { + if (noipv6 || sa.sin6_family==AF_INET || sa.sin6_family==PF_INET) { struct sockaddr_in *sa4=(struct sockaddr_in*)&sa; if (ip) { byte_copy(ip,12,V4mappedprefix); diff --git a/socket/socket_local6.c b/socket/socket_local6.c index a3a1719..83f11e6 100644 --- a/socket/socket_local6.c +++ b/socket/socket_local6.c @@ -24,7 +24,7 @@ int socket_local6(int s,char ip[16],uint16 *port,uint32 *scope_id) if (getsockname(s,(void*) &si,&len) == -1) return winsock2errno(-1); #ifdef LIBC_HAS_IP6 - if (si.sin6_family==AF_INET) { + if (noipv6 || si.sin6_family==AF_INET || si.sin6_family==PF_INET) { struct sockaddr_in *si4=(void*)&si; if (ip) { byte_copy(ip,12,V4mappedprefix); diff --git a/socket/socket_recv6.c b/socket/socket_recv6.c index 7b1a94c..418fc61 100644 --- a/socket/socket_recv6.c +++ b/socket/socket_recv6.c @@ -26,7 +26,7 @@ ssize_t socket_recv6(int s,char *buf,size_t len,char ip[16],uint16 *port,uint32 if ((r = recvfrom(s,buf,len,0,(struct sockaddr *) &si,&Len))<0) return winsock2errno(-1); #ifdef LIBC_HAS_IP6 - if (noipv6) { + if (noipv6 || si.sin6_family==AF_INET || si.sin6_family==PF_INET) { struct sockaddr_in *si4=(struct sockaddr_in *)&si; if (ip) { byte_copy(ip,12,V4mappedprefix); diff --git a/socket/socket_remote6.c b/socket/socket_remote6.c index 8b91488..a6311c1 100644 --- a/socket/socket_remote6.c +++ b/socket/socket_remote6.c @@ -24,7 +24,7 @@ int socket_remote6(int s,char ip[16],uint16 *port,uint32 *scope_id) if (getpeername(s,(struct sockaddr *) &si,&len) == -1) return winsock2errno(-1); #ifdef LIBC_HAS_IP6 - if (si.sin6_family==AF_INET) { + if (noipv6 || si.sin6_family==AF_INET || si.sin6_family==PF_INET) { struct sockaddr_in *si4=(struct sockaddr_in*)&si; if (ip) { byte_copy(ip,12,V4mappedprefix);