[fpc-pascal] GetCurrentThreadID under FreeBSD vs Linux

Marco van de Voort marcov at stack.nl
Fri Feb 8 21:34:20 CET 2013

In our previous episode, Graeme Geldenhuys said:
> Under Linux and Windows I have the following code which works fine.
> var
>   LThreadID: string;
> begin
>   FmtStr(LThreadID, '%.4d', [GetCurrentThreadID]);

Threadids are probably opague under Posix. So while it works, it is not
correct on Linux. You add implementation specific details (that it is an
integer type) that might change at any time.
> Under FreeBSD (64-bit) that failed with a EConvertError in the unit
> tests and the compiler gave a message of 'Invalid argument index in
> format "%.4d"'

That's correct.
> Navigating the code to see how TThreadID is defined, I found this for
> FreeBSD.
>   TThreadRec = record end;
>   TThreadID  = ^TThreadRec;
> So TThreadID is just a pointer to a record structure

This is a common construct to define opague types.

> Apparently gettinga a "real" thread ID/number is not as easy as under
> Linux. 

There is no thread id. See in GDB, you will probably see a pointer value,
not a nice increasing sequential number like e.g. PID.

> [Info from Google searches].  Under FreeBSD it seems that naming each
> thread with a string value is a more supported solution.

Note that under Windows threads can be named on API level too. VS and Delphi
(2010+ iirc) will show such threads in the debugger with a familiar name.

> So would it be safe if I did the following in my code? For the Windows,
> Linux and FreeBSD platforms at least.
>   FmtStr(LThreadID, '%.4d', [PtrUInt(GetCurrentThreadID)]);

I think while it is safe. Might throw warnings on some systems though
(signed vs unsigned conversions, if threadid is signed; or so)
> I've tested the PtrUInt() cast under FreeBSD, Linux and Windows, and it
> seems to work fine.
> BTW:
> This code is only used to supply a thread id/value to a logging function
> (file, GUI, console etc) to help with debugging, or at least show which
> thread wrote what debug log entries. So it's not critical code.

I would simply name the threads using a string, and forget the whole
threadid business. If only that the 64-bit pointer values can
get unwieldy large and hard to read.

More information about the fpc-pascal mailing list