X-Git-Url: http://nsz.repo.hu/git/?a=blobdiff_plain;ds=inline;f=src%2Fnetwork%2Fgetsockopt.c;h=d3640d9c91f26e77360cfe3161902e198aaaa6c3;hb=ae388becb529428ac926da102f1d025b3c3968da;hp=a9e0a72dbe5565628b581ca5916513b701b515f8;hpb=03a2f3e48caec15b1a9cebccc85328e9b8169df0;p=musl diff --git a/src/network/getsockopt.c b/src/network/getsockopt.c index a9e0a72d..d3640d9c 100644 --- a/src/network/getsockopt.c +++ b/src/network/getsockopt.c @@ -1,7 +1,41 @@ #include +#include +#include #include "syscall.h" -int getsockopt(int fd, int level, int optname, void *optval, socklen_t *optlen) +int getsockopt(int fd, int level, int optname, void *restrict optval, socklen_t *restrict optlen) { - return socketcall(getsockopt, fd, level, optname, optval, optlen, 0); + long tv32[2]; + struct timeval *tv; + + int r = __socketcall(getsockopt, fd, level, optname, optval, optlen, 0); + + if (r==-ENOPROTOOPT) switch (level) { + case SOL_SOCKET: + switch (optname) { + case SO_RCVTIMEO: + case SO_SNDTIMEO: + if (SO_RCVTIMEO == SO_RCVTIMEO_OLD) break; + if (*optlen < sizeof *tv) return __syscall_ret(-EINVAL); + if (optname==SO_RCVTIMEO) optname=SO_RCVTIMEO_OLD; + if (optname==SO_SNDTIMEO) optname=SO_SNDTIMEO_OLD; + r = __socketcall(getsockopt, fd, level, optname, + tv32, (socklen_t[]){sizeof tv32}, 0); + if (r<0) break; + tv = optval; + tv->tv_sec = tv32[0]; + tv->tv_usec = tv32[1]; + *optlen = sizeof *tv; + break; + case SO_TIMESTAMP: + case SO_TIMESTAMPNS: + if (SO_TIMESTAMP == SO_TIMESTAMP_OLD) break; + if (optname==SO_TIMESTAMP) optname=SO_TIMESTAMP_OLD; + if (optname==SO_TIMESTAMPNS) optname=SO_TIMESTAMPNS_OLD; + r = __socketcall(getsockopt, fd, level, + optname, optval, optlen, 0); + break; + } + } + return __syscall_ret(r); }