From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: Received: from phobos.denx.de (phobos.denx.de [85.214.62.61]) by sourceware.org (Postfix) with ESMTPS id 6C7053857C48 for ; Wed, 19 May 2021 08:36:16 +0000 (GMT) DMARC-Filter: OpenDMARC Filter v1.3.2 sourceware.org 6C7053857C48 Authentication-Results: sourceware.org; dmarc=none (p=none dis=none) header.from=denx.de Authentication-Results: sourceware.org; spf=pass smtp.mailfrom=lukma@denx.de Received: from ktm (85-222-111-42.dynamic.chello.pl [85.222.111.42]) (using TLSv1.3 with cipher TLS_AES_256_GCM_SHA384 (256/256 bits)) (No client certificate requested) (Authenticated sender: lukma@denx.de) by phobos.denx.de (Postfix) with ESMTPSA id 2B8B782B78; Wed, 19 May 2021 10:36:15 +0200 (CEST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=denx.de; s=phobos-20191101; t=1621413375; bh=/mZAuN1T45AfUBaNgFWjFF73j2icfHCC4EdPXAkF76I=; h=Date:From:To:Cc:Subject:In-Reply-To:References:From; b=yQ26BSBHKpGbgs8dmu1viDoDzqRVdp+Sa56h0iC3vWlnFnDTCBBj+5Hbpy04c0sGD Lo94ZpBumTghXOKwip7QfU9iG7QF0rH+2zGgcdL5rsW0pwEbliBWUuM8SXZF8X+kd6 nf+Fcy62Yybw1yvfenX5fpHfSWCgrRfzo7GgsCagJoEjdEc5cBWL6Q46euqZQNrzeN 4io0A+//Pm7f4yfSCkMYVG3Hyqx4CVN4YFqumFjXPun8wYvYxPV8L7sqWySzuIrXw8 gm3BGh/6SXYaczswO3uXFkhY27JyavlscIj5+GMt+pE1UqTwYuj/i08tDf3nqyqHwI ev2wFPkF+YuOQ== Date: Wed, 19 May 2021 10:36:14 +0200 From: Lukasz Majewski To: Adhemerval Zanella Cc: libc-alpha@sourceware.org, Carlos O'Donell Subject: Re: [PATCH v2 05/25] linux: Add fallback for 64-bit time_t SO_{RCV,SND}TIMEO Message-ID: <20210519103614.3aed2230@ktm> In-Reply-To: <20210518205613.1487824-6-adhemerval.zanella@linaro.org> References: <20210518205613.1487824-1-adhemerval.zanella@linaro.org> <20210518205613.1487824-6-adhemerval.zanella@linaro.org> Organization: denx.de X-Mailer: Claws Mail 3.17.8 (GTK+ 2.24.32; x86_64-pc-linux-gnu) MIME-Version: 1.0 Content-Type: multipart/signed; micalg=pgp-sha512; boundary="Sig_/XtbwvAYCPR=.j7FXNT73J5H"; protocol="application/pgp-signature" X-Virus-Scanned: clamav-milter 0.102.4 at phobos.denx.de X-Virus-Status: Clean X-Spam-Status: No, score=-12.1 required=5.0 tests=BAYES_00, DKIM_SIGNED, DKIM_VALID, DKIM_VALID_AU, DKIM_VALID_EF, GIT_PATCH_0, KAM_SHORT, RCVD_IN_BARRACUDACENTRAL, SPF_HELO_NONE, SPF_PASS, TXREP autolearn=ham autolearn_force=no version=3.4.2 X-Spam-Checker-Version: SpamAssassin 3.4.2 (2018-09-13) on server2.sourceware.org X-BeenThere: libc-alpha@sourceware.org X-Mailman-Version: 2.1.29 Precedence: list List-Id: Libc-alpha mailing list List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , X-List-Received-Date: Wed, 19 May 2021 08:36:19 -0000 --Sig_/XtbwvAYCPR=.j7FXNT73J5H Content-Type: text/plain; charset=US-ASCII Content-Transfer-Encoding: quoted-printable On Tue, 18 May 2021 17:55:53 -0300 Adhemerval Zanella wrote: > The constant values will be changed for __TIMESIZE=3D64, so binaries > built with 64-bit time support might fail to work properly on old > kernels. Both {get,set}sockopt will retry the syscall with the old > constant values and the timeout value adjusted when kernel returns > ENOTPROTOPT. >=20 > It also adds an internal only SO_{RCV,SND}TIMEO where > COMPAT_SO_{RCV,SND}TIMEO_OLD indicates pre 32 bit time support and > COMPAT_SO_{RCV,SND}TIMEO_NEW indicates time64 support. It allows to > refer to constant independently of the time_t ABI and kernel version > used. >=20 > Checked on x86_64-linux-gnu and i686-linux-gnu (on 5.4 and on 4.15 > kernel). Reviewed-by: Lukasz Majewski > --- > sysdeps/unix/sysv/linux/getsockopt.c | 67 +++++++++++++++-- > .../sysv/linux/hppa/socket-constants-time64.h | 30 ++++++++ > .../sysv/linux/mips/socket-constants-time64.h | 30 ++++++++ > .../linux/powerpc/socket-constants-time64.h | 30 ++++++++ > sysdeps/unix/sysv/linux/setsockopt.c | 71 > ++++++++++++++++--- .../unix/sysv/linux/socket-constants-time64.h | > 30 ++++++++ .../linux/sparc/socket-constants-time64.h | 30 > ++++++++ 7 files changed, 273 insertions(+), 15 deletions(-) > create mode 100644 > sysdeps/unix/sysv/linux/hppa/socket-constants-time64.h create mode > 100644 sysdeps/unix/sysv/linux/mips/socket-constants-time64.h create > mode 100644 sysdeps/unix/sysv/linux/powerpc/socket-constants-time64.h > create mode 100644 sysdeps/unix/sysv/linux/socket-constants-time64.h > create mode 100644 > sysdeps/unix/sysv/linux/sparc/socket-constants-time64.h >=20 > diff --git a/sysdeps/unix/sysv/linux/getsockopt.c > b/sysdeps/unix/sysv/linux/getsockopt.c index 76ee8a94d6..c8e502d976 > 100644 --- a/sysdeps/unix/sysv/linux/getsockopt.c > +++ b/sysdeps/unix/sysv/linux/getsockopt.c > @@ -15,16 +15,15 @@ > License along with the GNU C Library; if not, see > . */ > =20 > -#include > -#include > #include > - > +#include > +#include > #include > -#include > -#include > +#include > =20 > -int > -__getsockopt (int fd, int level, int optname, void *optval, > socklen_t *len) +static int > +getsockopt_syscall (int fd, int level, int optname, void *optval, > + socklen_t *len) > { > #ifdef __ASSUME_GETSOCKOPT_SYSCALL > return INLINE_SYSCALL (getsockopt, 5, fd, level, optname, optval, > len); @@ -32,4 +31,58 @@ __getsockopt (int fd, int level, int > optname, void *optval, socklen_t *len) return SOCKETCALL (getsockopt, > fd, level, optname, optval, len); #endif > } > + > +#ifndef __ASSUME_TIME64_SYSCALLS > +static int > +getsockopt32 (int fd, int level, int optname, void *optval, > + socklen_t *len) > +{ > + int r =3D -1; > + > + if (level !=3D SOL_SOCKET) > + return r; > + > + switch (optname) > + { > + case COMPAT_SO_RCVTIMEO_NEW: > + case COMPAT_SO_SNDTIMEO_NEW: > + { > + if (*len < sizeof (struct __timeval64)) > + { > + __set_errno (EINVAL); > + break; > + } > + > + if (optname =3D=3D COMPAT_SO_RCVTIMEO_NEW) > + optname =3D COMPAT_SO_RCVTIMEO_OLD; > + if (optname =3D=3D COMPAT_SO_SNDTIMEO_NEW) > + optname =3D COMPAT_SO_SNDTIMEO_OLD; > + > + struct __timeval32 tv32; > + r =3D getsockopt_syscall (fd, level, optname, &tv32, > + (socklen_t[]) { sizeof tv32 }); > + if (r < 0) > + break; > + struct __timeval64 *tv64 =3D (struct __timeval64 *) optval; > + *tv64 =3D valid_timeval32_to_timeval64 (tv32); > + *len =3D sizeof (*tv64); > + } > + } > + > + return r; > +} > +#endif > + > +int > +__getsockopt (int fd, int level, int optname, void *optval, > socklen_t *len) +{ > + int r =3D getsockopt_syscall (fd, level, optname, optval, len); > + > +#ifndef __ASSUME_TIME64_SYSCALLS > + if (r =3D=3D -1 && errno =3D=3D ENOPROTOOPT) > + r =3D getsockopt32 (fd, level, optname, optval, len); > +#endif > + > + return r; > +} > weak_alias (__getsockopt, getsockopt) > diff --git a/sysdeps/unix/sysv/linux/hppa/socket-constants-time64.h > b/sysdeps/unix/sysv/linux/hppa/socket-constants-time64.h new file > mode 100644 index 0000000000..ea721e0fc2 > --- /dev/null > +++ b/sysdeps/unix/sysv/linux/hppa/socket-constants-time64.h > @@ -0,0 +1,30 @@ > +/* Compat socket constants used in 64 bit compat code. > + Copyright (C) 2021 Free Software Foundation, Inc. > + This file is part of the GNU C Library. > + > + The GNU C Library is free software; you can redistribute it and/or > + modify it under the terms of the GNU Lesser General Public > + License as published by the Free Software Foundation; either > + version 2.1 of the License, or (at your option) any later version. > + > + The GNU C Library 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. See the GNU > + Lesser General Public License for more details. > + > + You should have received a copy of the GNU Lesser General Public > + License along with the GNU C Library; if not, see > + . */ > + > +#ifndef _SOCKET_CONSTANTS_TIME64_H > +#define _SOCKET_CONSTANTS_TIME64_H > + > +/* The compat code requires the SO_* constants used for both 32 and > 64 bit > + time_t, however they were only added on v5.1 kernel. */ > + > +#define COMPAT_SO_RCVTIMEO_OLD 4102 > +#define COMPAT_SO_SNDTIMEO_OLD 4101 > +#define COMPAT_SO_RCVTIMEO_NEW 16448 > +#define COMPAT_SO_SNDTIMEO_NEW 16449 > + > +#endif > diff --git a/sysdeps/unix/sysv/linux/mips/socket-constants-time64.h > b/sysdeps/unix/sysv/linux/mips/socket-constants-time64.h new file > mode 100644 index 0000000000..ab8bd62853 > --- /dev/null > +++ b/sysdeps/unix/sysv/linux/mips/socket-constants-time64.h > @@ -0,0 +1,30 @@ > +/* Compat socket constants used in 64 bit compat code. > + Copyright (C) 2021 Free Software Foundation, Inc. > + This file is part of the GNU C Library. > + > + The GNU C Library is free software; you can redistribute it and/or > + modify it under the terms of the GNU Lesser General Public > + License as published by the Free Software Foundation; either > + version 2.1 of the License, or (at your option) any later version. > + > + The GNU C Library 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. See the GNU > + Lesser General Public License for more details. > + > + You should have received a copy of the GNU Lesser General Public > + License along with the GNU C Library; if not, see > + . */ > + > +#ifndef _SOCKET_CONSTANTS_TIME64_H > +#define _SOCKET_CONSTANTS_TIME64_H > + > +/* The compat code requires the SO_* constants used for both 32 and > 64 bit > + time_t, however they were only added on v5.1 kernel. */ > + > +#define COMPAT_SO_RCVTIMEO_OLD 4102 > +#define COMPAT_SO_SNDTIMEO_OLD 4101 > +#define COMPAT_SO_RCVTIMEO_NEW 66 > +#define COMPAT_SO_SNDTIMEO_NEW 67 > + > +#endif > diff --git > a/sysdeps/unix/sysv/linux/powerpc/socket-constants-time64.h > b/sysdeps/unix/sysv/linux/powerpc/socket-constants-time64.h new file > mode 100644 index 0000000000..1e48dcca8d --- /dev/null > +++ b/sysdeps/unix/sysv/linux/powerpc/socket-constants-time64.h > @@ -0,0 +1,30 @@ > +/* Compat socket constants used in 64 bit compat code. > + Copyright (C) 2021 Free Software Foundation, Inc. > + This file is part of the GNU C Library. > + > + The GNU C Library is free software; you can redistribute it and/or > + modify it under the terms of the GNU Lesser General Public > + License as published by the Free Software Foundation; either > + version 2.1 of the License, or (at your option) any later version. > + > + The GNU C Library 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. See the GNU > + Lesser General Public License for more details. > + > + You should have received a copy of the GNU Lesser General Public > + License along with the GNU C Library; if not, see > + . */ > + > +#ifndef _SOCKET_CONSTANTS_TIME64_H > +#define _SOCKET_CONSTANTS_TIME64_H > + > +/* The compat code requires the SO_* constants used for both 32 and > 64 bit > + time_t, however they were only added on v5.1 kernel. */ > + > +#define COMPAT_SO_RCVTIMEO_OLD 18 > +#define COMPAT_SO_SNDTIMEO_OLD 19 > +#define COMPAT_SO_RCVTIMEO_NEW 66 > +#define COMPAT_SO_SNDTIMEO_NEW 67 > + > +#endif > diff --git a/sysdeps/unix/sysv/linux/setsockopt.c > b/sysdeps/unix/sysv/linux/setsockopt.c index 12fd7bdcde..6505202265 > 100644 --- a/sysdeps/unix/sysv/linux/setsockopt.c > +++ b/sysdeps/unix/sysv/linux/setsockopt.c > @@ -15,21 +15,76 @@ > License along with the GNU C Library; if not, see > . */ > =20 > -#include > -#include > #include > - > +#include > +#include > #include > -#include > -#include > +#include > =20 > -int > -setsockopt (int fd, int level, int optname, const void *optval, > socklen_t len) +static int > +setsockopt_syscall (int fd, int level, int optname, const void > *optval, > + socklen_t len) > { > #ifdef __ASSUME_SETSOCKOPT_SYSCALL > - return INLINE_SYSCALL (setsockopt, 5, fd, level, optname, optval, > len); > + return INLINE_SYSCALL_CALL (setsockopt, fd, level, optname, > optval, len); #else > return SOCKETCALL (setsockopt, fd, level, optname, optval, len); > #endif > } > + > +#ifndef __ASSUME_TIME64_SYSCALLS > +static int > +setsockopt32 (int fd, int level, int optname, const void *optval, > + socklen_t len) > +{ > + int r =3D -1; > + > + if (level !=3D SOL_SOCKET) > + return r; > + > + switch (optname) > + { > + case COMPAT_SO_RCVTIMEO_NEW: > + case COMPAT_SO_SNDTIMEO_NEW: > + { > + if (len < sizeof (struct __timeval64)) > + { > + __set_errno (EINVAL); > + break; > + } > + > + struct __timeval64 *tv64 =3D (struct __timeval64 *) optval; > + if (! in_time_t_range (tv64->tv_sec)) > + { > + __set_errno (EOVERFLOW); > + break; > + } > + > + if (optname =3D=3D COMPAT_SO_RCVTIMEO_NEW) > + optname =3D COMPAT_SO_RCVTIMEO_OLD; > + if (optname =3D=3D COMPAT_SO_SNDTIMEO_NEW) > + optname =3D COMPAT_SO_SNDTIMEO_OLD; > + > + struct __timeval32 tv32 =3D valid_timeval64_to_timeval32 > (*tv64); + > + r =3D setsockopt_syscall (fd, level, optname, &tv32, sizeof > (tv32)); > + } > + } > + > + return r; > +} > +#endif > + > +int > +setsockopt (int fd, int level, int optname, const void *optval, > socklen_t len) +{ > + int r =3D setsockopt_syscall (fd, level, optname, optval, len); > + > +#ifndef __ASSUME_TIME64_SYSCALLS > + if (r =3D=3D -1 && errno =3D=3D ENOPROTOOPT) > + r =3D setsockopt32 (fd, level, optname, optval, len); > +#endif > + > + return r; > +} > weak_alias (setsockopt, __setsockopt) > diff --git a/sysdeps/unix/sysv/linux/socket-constants-time64.h > b/sysdeps/unix/sysv/linux/socket-constants-time64.h new file mode > 100644 index 0000000000..e5a3777f28 > --- /dev/null > +++ b/sysdeps/unix/sysv/linux/socket-constants-time64.h > @@ -0,0 +1,30 @@ > +/* Compat socket constants used in 64 bit compat code. > + Copyright (C) 2021 Free Software Foundation, Inc. > + This file is part of the GNU C Library. > + > + The GNU C Library is free software; you can redistribute it and/or > + modify it under the terms of the GNU Lesser General Public > + License as published by the Free Software Foundation; either > + version 2.1 of the License, or (at your option) any later version. > + > + The GNU C Library 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. See the GNU > + Lesser General Public License for more details. > + > + You should have received a copy of the GNU Lesser General Public > + License along with the GNU C Library; if not, see > + . */ > + > +#ifndef _SOCKET_CONSTANTS_TIME64_H > +#define _SOCKET_CONSTANTS_TIME64_H > + > +/* The compat code requires the SO_* constants used for both 32 and > 64 bit > + time_t, however they were only added on v5.1 kernel. */ > + > +#define COMPAT_SO_RCVTIMEO_OLD 20 > +#define COMPAT_SO_SNDTIMEO_OLD 21 > +#define COMPAT_SO_RCVTIMEO_NEW 66 > +#define COMPAT_SO_SNDTIMEO_NEW 67 > + > +#endif > diff --git a/sysdeps/unix/sysv/linux/sparc/socket-constants-time64.h > b/sysdeps/unix/sysv/linux/sparc/socket-constants-time64.h new file > mode 100644 index 0000000000..b137abdeea > --- /dev/null > +++ b/sysdeps/unix/sysv/linux/sparc/socket-constants-time64.h > @@ -0,0 +1,30 @@ > +/* Compat socket constants used in 64 bit compat code. > + Copyright (C) 2021 Free Software Foundation, Inc. > + This file is part of the GNU C Library. > + > + The GNU C Library is free software; you can redistribute it and/or > + modify it under the terms of the GNU Lesser General Public > + License as published by the Free Software Foundation; either > + version 2.1 of the License, or (at your option) any later version. > + > + The GNU C Library 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. See the GNU > + Lesser General Public License for more details. > + > + You should have received a copy of the GNU Lesser General Public > + License along with the GNU C Library; if not, see > + . */ > + > +#ifndef _SOCKET_CONSTANTS_TIME64_H > +#define _SOCKET_CONSTANTS_TIME64_H > + > +/* The compat code requires the SO_* constants used for both 32 and > 64 bit > + time_t, however they were only added on v5.1 kernel. */ > + > +#define COMPAT_SO_RCVTIMEO_OLD 8192 > +#define COMPAT_SO_SNDTIMEO_OLD 16384 > +#define COMPAT_SO_RCVTIMEO_NEW 68 > +#define COMPAT_SO_SNDTIMEO_NEW 69 > + > +#endif Best regards, Lukasz Majewski -- DENX Software Engineering GmbH, Managing Director: Wolfgang Denk HRB 165235 Munich, Office: Kirchenstr.5, D-82194 Groebenzell, Germany Phone: (+49)-8142-66989-59 Fax: (+49)-8142-66989-80 Email: lukma@denx.de --Sig_/XtbwvAYCPR=.j7FXNT73J5H Content-Type: application/pgp-signature Content-Description: OpenPGP digital signature -----BEGIN PGP SIGNATURE----- iQEzBAEBCgAdFiEEgAyFJ+N6uu6+XupJAR8vZIA0zr0FAmCkzf4ACgkQAR8vZIA0 zr2/zwf/UNWhQBWL4G46mbJS3tjUG7iG8kUG8ZsZcACpyaNupUtpb3N7CHC0FPsB 7FnS0Kr22yYVGxjm2YWY0xjVkN/bB+a+gaZ9FLX/0+UJCS1HEwrdRIuz6Z3WtttB trRRsS8Nj+L+4hg48yDKioVTZl9e1wDP1AzrNBhDuU12D7Qe/dObEm7vBkNGP2rT teOYRYzRHu3zveY+TmoAiFrL7CKNYSyevkF2+jG5gPnufQrC/kCFoSdKN9j4UmvN FfXYCLLJPVbFhVllGQWWL7FGP0WPR6v3z9/msZeu/g0T9ZEAS+AU/OeLHX1gYF3I aIBSGgHBLQXzBlzCneilbL5B+CAaWg== =YG+i -----END PGP SIGNATURE----- --Sig_/XtbwvAYCPR=.j7FXNT73J5H--