Re: When/how is global "errno" variable from reent.c to be used?
Richard Damon <[email protected]>
| Newsgroups | gmane.comp.lib.newlib |
|---|---|
| Message-ID | <[email protected]> |
Software the explicitly declares errno as extern int errno; is broken, and violates the C standard, and creates explicitly stated Undefined Behavior. On 10/16/20 11:50 AM, Grant Edwards via Newlib wrote: > [Sorry for yet another errno vs. reentrancy thread.] > > I've been studying errno, __errno, _impure_ptr et alia, and I think I > understand how that's supposed to work. If you don't define > _REENT_ONLY, then errno is defined as *(__errno()), where __errno() > returns &_REENT->errno, and _REENT is #defined as _impure_ptr, and > thread context switches are supposed to set _impure_ptr to point to a > per-thread struct _reent. > > If you define _REENT_ONLY, then there is no 'errno' declared in > errno.h, and you've got to mannually pass a struct _reent pointer to > the _r versions of various lib[cm] functions. > > But, in the application source I've been given, the LWIP stack does > not include newlib's errno.h. Instead it declares "extern int errno" > and then uses errno as usual. That external declaration is satisfied > at link time by the global "errno" exported by libc/reent/reent.c. > > That seems to be non-thread-safe and won't interoperate correctly with > newlib's library calls or with application code that includes newlib's > errno.h. > > What is that global errno variable for and how is to be used? > > Is there a use case for single-threaded applications that I've missed > where newlib's library calls will set/check the global 'int errno' > variable instead of _impure_ptr->errno? > > Or is the LWIP configuration broken? > > Even if there is a single-threaded use case for newlib where everybody > uses the global 'int errno' variable, the application in question is > multi-threaded, so it's probably still broken. The RTOS in use does > not set _impure_ptr on context switches, so I believe that switching > to using the newlib errno.h which will define errno as *(__errno()) > still won't work as it should. > > FWIW, the toolchain I'm using is > > gcc-arm-none-eabi-9-2020-q2-update-x86_64-linux.tar.bz2 > > from > > https://developer.arm.com/tools-and-software/open-source-software/developer-tools/gnu-toolchain/gnu-rm/downloads > > It contains v3.3.0 newlib and newlib-nano built from > > git://sourceware.org/git/newlib-cygwin.git commit 6d79e0a58866548f435527798fbd4a6849d05bc7 > > The LWIP application I'm looking at uses newlib-nano. > > -- > Grant > > > > > -- Richard Damon