libm reentrancy

Jeff Johnston jjohnstn@redhat.com
Wed Jan 9 17:28:00 GMT 2013


Let me clarify here.

There are two thread reentrancy models.  The original model has the code 
creating new reentrancy structures for each thread (other than the main 
thread) and manually specifying the reentrancy structure and calling _r 
versions of function or else redefining _impure_ptr on the fly.  The 
_REENT_ONLY flag can be used to restrict all calls to the _r versions.

A while back I added a newer model which looks for a flag: 
__DYNAMIC_REENT__ (see libc/include/sys/reent.h) which can be set up in 
config.h, etc... for a platfrom.  This flag signals to define the _REENT 
macro (which in the old model is defined to point to the default 
reentrancy structure) to instead call the __getreent() function.  This 
function needs to be defined by the platform and needs to returns the 
reentrancy structure for the current thread (e.g. you could implement 
this using thread-specific storage as is done in the case of 
libc/sys/linux/linuxthreads/getreent.c).

Using the newer model, code can just use the regular C interfaces and 
everything will be handled automatically since the __getreent() function 
switches to the appropriate reentrancy structure as needed.  This 
includes errno references with errno.h included.

Now, that said, libm was never set up with the old thread reentrancy 
model in the same manner as libc was.  In particular this affects the 
use of errno which is thread-specific.  The current libm refers to errno 
via errno.h which eventually uses the structure defined for _REENT.  So, 
one would need to redefine _impure_ptr manually around libm calls.

To be proper, I should fix libm so one does not have to manually fool 
around with _impure_ptr.  However, I would recommend using the new model 
is you really want to support threads as it is far superior and allows 
code to use the regular C interfaces instead of a bunch of 
newlib-created ones.

-- Jeff J.

On 01/09/2013 10:55 AM, Craig Howland wrote:
> errno is not a problem, as it is transparently taken care of--see
> sys/errno.h.
> errno is not really a global, but calls a function that returns a
> pointer to
> the thread's individual errno within the reentrancy structure.
> Craig
>
> On 01/09/2013 09:06 AM, Gregory Pietsch wrote:
>> Oh yeah, forgot about errno. I guess the best way to avoid that is to
>> make sure
>> the number you are taking the square root of isn't negative. -- Gregory
>>
>> On 1/9/2013 4:37 AM, Marcus Hult wrote:
>>> Hello,
>>>
>>> Thanks for your reply Gregory.
>>>
>>> The sqrt function for instance, may set the errno variable according
>>> to the manual. ShouldnÂ’t this function then have a reentrant version?
>>> Or do I always need to use the _impure_ptr when using libm, to be
>>> thread safe?
>>>
>>> /Marcus
>>>



More information about the Newlib mailing list