Re: alx-0008 - Standardize strtoi(3) and strtou(3) from NetBSD
Alejandro Colomar <[email protected]> Wed, 19 Mar 2025 22:23:51 +0100
| Newsgroups | gmane.os.netbsd.devel.general |
|---|---|
| Message-ID | <2bk4qlhebhsgby4dda4fshocgoyixmqwqlnlgwcyzywkhpbeum@yr5ko5sv6ezy> |
--7fc6kx6in34552in Content-Type: text/plain; protected-headers=v1; charset=utf-8 Content-Disposition: inline Content-Transfer-Encoding: quoted-printable From: Alejandro Colomar <[email protected]> To: Paul Eggert <[email protected]> Cc: Bruno Haible <[email protected]>, [email protected], [email protected], [email protected], [email protected], christos <[email protected]>, =?utf-8?B?xJBvw6BuIFRy4bqnbiBDw7RuZw==?= Danh <[email protected]>, Eli Schwartz <[email protected]>, Guillem Jover <[email protected]>, Iker Pedrosa <[email protected]>, Michael Vetter <[email protected]>, Robert Elz <[email protected]>, [email protected], Sam James <[email protected]>, "Serge E. Hallyn" <[email protected]> Subject: Re: alx-0008 - Standardize strtoi(3) and strtou(3) from NetBSD References: <mgcfwxfmv3kpfnkkf6uj63kx5tdzl64p2zg2us4ntsu6q5xkwj@k52z5yyiywoo> <18739733.sWSEgdgrri@nimes> <mvwnrmk2xf45ivyk4kzxdxuwdk67666yt3kwafck6vo4vq2lru@wkqmoqsacqkf> <3237498.fEcJ0Lxnt5@nimes> <[email protected]> <azfxoxklec7hlxll52ocmjiooq7bahy7xgrplbzmfbdygbubxc@upuk7c6bckto> <[email protected]> MIME-Version: 1.0 In-Reply-To: <[email protected]> Hi Paul, On Wed, Mar 19, 2025 at 01:39:00PM -0700, Paul Eggert wrote: > On 2025-03-19 13:05, Alejandro Colomar wrote: > > Please comment on the subthread where Bruno mentioned a number of places > > in gnulib and gettext where you use strtoul(3). I found there a few > > bugs, plus some ways to just simplify with strtou(3). >=20 > I looked at the Gnulib commentary in <https://lore.kernel.org/liba2i/jx46= 64ishtl34eg2npdrv5fkfdiczqnlq3vjuacjrupjvh377x@gddcftzgwmfq/>, > as I assume that's what you're talking about. (I don't hack on gettext and > will leave Bruno to comment on that.) Yes, I was referring to those. > For Gnulib, I didn't see any bugs in the three areas mentioned. >=20 > The patch suggested to lib/getaddrinfo.c doesn't fix any bugs that I can > see, and needs an additional wrapper to work anyway, which is introducing > complexity. Agree. gnulib had dead code and not-very-readable code, but no misbehavior. Although, I think not reporting errors or warnings on saturation needs justification. > The patch suggested to lib/nproc.c is merely a minor clarity / performance > improvement (it removes three instructions), and does not fix any bugs. > Likewise for the patch to lib/omp-init.c. And these improvements (where t= he > code mistakenly worried about endptr =3D=3D NULL) fix a mistake that one = could > make with the proposed strtoi API, so I don't see strtoi helping there. The test =3D=3DNULL would never make sense in strtoi(3) because it guarantees setting *endp even on EINVAL. Some programmers are paranoid with strtol(3) and check for NULL, because in some systems it may keep it uninitialized on EINVAL, but that's not portable at all. So yes, strtoi(3) should remove that issue. >=20 > But thanks for the clarity / speedup idea; I installed a patch into Gnulib > here: >=20 > https://git.savannah.gnu.org/cgit/gnulib.git/commit/?id=3D2835ca01722fcd4= 1761383ef289d19797b13b2e8 Thanks, those changes look good. BTW, what do you think of using strspn(3) to simplify the c_isspace loop? However, would you mind clarifying why you don't diagnose huge values in the two places that you have updated? > > > > In particular, use a functional style, with > > > > no side effects (no pointers-to-results). Just return the result yo= u want, > > > > as a struct, and keep the struct simple. Two struct components shou= ld > > > > suffice: the scanned numeric value and a success/error indicator. > >=20 > > That's going to complicate usage significantly. >=20 > Please try it and see. You might be surprised at how clean and efficient > functional programming can be, if done right. Admittedly C doesn't always > make it easy. Here's an example of parsing a time_t: time_t t; if (a2i(time_t, &t, ...) =3D=3D -1) err(1, "a2i"); If you need to store it in a struct, you need to know what a time_t is in the first place: struct foo { long val; int err; } struct foo ret; ret =3D f(time_t, ...); if (ret.err !=3D 0) err(1, "f"); How do I know which variant of struct foo I need? Have a lovely night! Alex --=20 <https://www.alejandro-colomar.es/> --7fc6kx6in34552in Content-Type: application/pgp-signature; name="signature.asc" -----BEGIN PGP SIGNATURE----- iQIzBAABCgAdFiEES7Jt9u9GbmlWADAi64mZXMKQwqkFAmfbNeAACgkQ64mZXMKQ wqnHqA/9Ew5ugfmjrDl8aibX1nI3vtP+hK+VWQDfgtQ77mE8DH23i99XIyaLPdLz p/sJH5TszFQbStwvKSUyuz/CdJoukflP++Pi3RYUIFn+fsyCXnTOKSQu9phR01LM ZkYRfOWKxzafT5cRGJgnZAHr5BFuPsSlPsTs2bxpj0IRbCQqyQX1UE9eL+gxcL2y U1FzVoWTmkprUjCTMHjUf/zCUicwb4gP86/youzRal09SYXFr9mfWRiW3EmYjfii UZCTXd2xqaW0UufHz4sNQ6lWLfdB4JHdevQQy15snqgMfa+zn2NV91Ovl5e7pnD0 TV/wr5YYlfFCVv7XZ+Hb+18jDRCALF9vaY/j0nJAbQeMsb1lLspnK5DijNG1Cqqv 5/RQEHh2om77EUdjZcCjCf8dQRWw3uABATxraZ5bAT0P3zeccfpqnKcS7TGRhIq+ zqRNis0nH7VoySurxXT3yoWZsAReUXcvha8i+9Q/Dwt63cMAPbi0YFhpU/j2BvrX vf9WnfWWzN6nbYmcWEfaQRDsqabWgcbW7IR2oq/B0PmpS4if8EimNVmVJroZInGQ 9XQ+yEK2opeRtoLilL0uwC0bh1H83Cay1kPWU4rUhnMA2ePN03iTkADPACj2HrhM pp46PXvkem1B1CwJD6YreqIc3VrgiPHmhrkcMzwfBubceEeUfNM= =giKx -----END PGP SIGNATURE----- --7fc6kx6in34552in--