Hi, Michael,
I don't know what the correct solution would be. TLS could work OK in
the kernel build mode, but not in the protected mode. It does not work
in the protected build because there is a common, physically addressed
user heap. This needs more explanation...
TLS works by putting the errno value (and other local data) in a
reserved area at the base of each thread's stack. The stacks must be
aligned to N bytes where N is a power of 2. Then the TLS can be
recovered from the current stack pointer like: tls = ((sp) & ~((N) -1).
But, in addition to alignment, the value of N limits the size of the
stack. Because the available SRAM in the heap is relatively small, the
alignment limits require a small value of N. But larger stacks require
a larger value of N. So there is typically no ideal alignment that
works properly in the protected build. This is because of smallish SRAM
sizes and physical addressing.
In the kernel build, we have the possibility of aligning the "virtual"
stack to large values of N, like 20 or so. So TLS could be made to work
well in that case. But I don't think it is a good solution in the
protected build.
That is why I created the set_errno() and get_errno() macros/functions.
They are less than ideal but will work without TLS.
Another thing I have thought about, mostly for getpid() support, is to
have a global region of memory that holds the current errno and pid.
This would be saved, restored on each context switch it works like TLS.
This, however, would be really awkward in SMP modes.
Greg