Message ID | 20240911004315.167590-1-amerey@redhat.com |
---|---|
State | New |
Headers | show |
Series | Test that errno is set to 0 at program startup | expand |
On Sep 10 2024, Aaron Merey wrote: > +static int > +do_test (void) > +{ > + TEST_COMPARE (errno, 0); > + TEST_COMPARE (get_ctor_errno (), 0); > + > + return 0; > +} > + > +#include <support/test-driver.c> That only tests that the test driver does not modify errno, which is uninteresting.
On Wed, 11 Sep 2024, Andreas Schwab wrote: > > +static int > > +do_test (void) > > +{ > > + TEST_COMPARE (errno, 0); > > + TEST_COMPARE (get_ctor_errno (), 0); > > + > > + return 0; > > +} > > + > > +#include <support/test-driver.c> > > That only tests that the test driver does not modify errno, which is > uninteresting. Good point. The test is so simple that I think it does not need to use the driver as there's hardly if anything that could hang here so that it would require the driver's intervention (and if it did hang, so could the test driver anyway). Alternatively with some macro trickery we could arrange for test driver's `main' to be called second from test's local `main', so that things like TEST_COMPARE work as expected (and `do_test' only checks copies of `errno' values recorded previously). Maciej
On 9/11/24 7:31 AM, Maciej W. Rozycki wrote: > On Wed, 11 Sep 2024, Andreas Schwab wrote: > >>> +static int >>> +do_test (void) >>> +{ >>> + TEST_COMPARE (errno, 0); >>> + TEST_COMPARE (get_ctor_errno (), 0); >>> + >>> + return 0; >>> +} >>> + >>> +#include <support/test-driver.c> >> >> That only tests that the test driver does not modify errno, which is >> uninteresting. > > Good point. The test is so simple that I think it does not need to use > the driver as there's hardly if anything that could hang here so that it > would require the driver's intervention (and if it did hang, so could the > test driver anyway). Yes, I forgot the test driver gets entirely in the way. I suggest we simplify the test then: * Drop "#include <support/test-driver.c>" * Use "int main()" directly. * Directly check the values and exit(1) if they are not zero. > Alternatively with some macro trickery we could arrange for test driver's > `main' to be called second from test's local `main', so that things like > TEST_COMPARE work as expected (and `do_test' only checks copies of `errno' > values recorded previously). No, I think a bare main() here is simplest, it shouldn't hang, if it does then we have much more complex problems.
On Tue, Sep 10, 2024, at 8:43 PM, Aaron Merey wrote: > Add new testcase elf/tst-startup-errno.c which tests that errno is set > to 0 at first ELF constructor execution and at the start of the > program's main function. If a C++ global constructor sets errno to a nonzero value, aren't we obliged to preserve that value, and thus have errno be nonzero on entry to main? zw
Hi Zack, On Fri, Sep 13, 2024 at 9:25 AM Zack Weinberg <zack@owlfolio.org> wrote: > > On Tue, Sep 10, 2024, at 8:43 PM, Aaron Merey wrote: > > Add new testcase elf/tst-startup-errno.c which tests that errno is set > > to 0 at first ELF constructor execution and at the start of the > > program's main function. > > If a C++ global constructor sets errno to a nonzero value, aren't we obliged to preserve that value, and thus have errno be nonzero on entry to main? Yes but this is just testing that errno stays set to zero when not modified by an ELF constructor. Aaron
On Thu, Sep 19, 2024, at 11:27 AM, Aaron Merey wrote: > On Fri, Sep 13, 2024 at 9:25 AM Zack Weinberg <zack@owlfolio.org> wrote: >> On Tue, Sep 10, 2024, at 8:43 PM, Aaron Merey wrote: >> > Add new testcase elf/tst-startup-errno.c which tests that errno is >> > set to 0 at first ELF constructor execution and at the start of the >> > program's main function. >> >> If a C++ global constructor sets errno to a nonzero value, aren't we >> obliged to preserve that value, and thus have errno be nonzero on >> entry to main? > > Yes but this is just testing that errno stays set to zero when not > modified by an ELF constructor. Ah, I misread your code, I thought it was testing that errno is zero on entry to main *even if* an ELF constructor sets it to nonzero. In that case I suggest that there should be an additional test with an ELF constructor that *does* set errno to nonzero and then we check in main that it still has the same value. zw
diff --git a/elf/Makefile b/elf/Makefile index 00622ace9d..be1a99ea26 100644 --- a/elf/Makefile +++ b/elf/Makefile @@ -457,6 +457,7 @@ tests += \ tst-single_threaded-pthread \ tst-sonamemove-dlopen \ tst-sonamemove-link \ + tst-startup-errno \ tst-thrlock \ tst-tls-dlinfo \ tst-tls-ie \ diff --git a/elf/tst-startup-errno.c b/elf/tst-startup-errno.c new file mode 100644 index 0000000000..0db72a60fa --- /dev/null +++ b/elf/tst-startup-errno.c @@ -0,0 +1,49 @@ +/* Test the value of errno at program startup. + Copyright (C) 2024 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 + <https://www.gnu.org/licenses/>. */ + +#include <errno.h> +#include <support/check.h> + +/* Verify that errno is 0 at first ELF constructor execution and at + the start of main. */ + +static void set_ctor_errno (void) __attribute__((constructor)); +static int ctor_errno = -1; + +static void +set_ctor_errno (void) +{ + ctor_errno = errno; +} + +static int +get_ctor_errno (void) +{ + return ctor_errno; +} + +static int +do_test (void) +{ + TEST_COMPARE (errno, 0); + TEST_COMPARE (get_ctor_errno (), 0); + + return 0; +} + +#include <support/test-driver.c>