ThreadDestroy & printf problem

Hi All,

I have a problem with dynamic creation and destruction of threads. It
seems it is not safe to call ThreadDestroy. The following little program
hangs on the last line:

#include <unistd.h>
#include <stdio.h>
#include <stdlib.h>
#include <pthread.h>
#include <errno.h>
#include <sys/neutrino.h>

void * func( void *arg )
{
delay(1);
printf(“Thread\n”);
return NULL;
}

int main( int argc, char* argv[] )
{
pthread_t thread;

if (pthread_create(&thread, NULL, &func, NULL) != EOK)
{
printf(“Failed to create.\n”);
}

delay(1);

if (ThreadDestroy(thread, -1, NULL) == -1)
{
printf(“Failed to destroy.\n”);
}

printf(“Destroyed the thread.\n”);
}

I guess it is a problem of killing the thread inside printf call. printf
is thread safe, nevertheless it doesn’t seem to be ThreadDestroy safe.

Is this a bug, a feature, or a misunderstanding ? May ThreadDestroy be
used at all with libc functions ?

Thanks for any advice.

Best regards
Lukas Kunc

Lukas Kunc <Lukas.Kunc@soft-gate.de> wrote:

if (ThreadDestroy(thread, -1, NULL) == -1)

I suspect that the last argument shouldn’t be NULL. Here’s what the
docs say this argument is:

The value to make available to a to a thread that joins a nondetached
thread that’s destroyed.

The docs for pthread_exit() – which calls ThreadDestroy() – say:

A pointer to a value that you want to be made available to any thread
joining the thread that you’re terminating.


Steve Reid stever@qnx.com
Technical Editor
QNX Software Systems

Steve Reid wrote:

Lukas Kunc <> Lukas.Kunc@soft-gate.de> > wrote:

if (ThreadDestroy(thread, -1, NULL) == -1)

ThreadDestroy() just causes the thread to disappear, without calling any
cancellation handlers. If the thread holds any mutexes when you destroy
it, they won’t be unlocked. In particular, if you destroy a thread
while it’s running printf(), you’re likely to leave stdout locked by a
non-existent thread, causing any other thread that calls printf() to
block indefinitely.

In short, a ThreadDestroy() call has pretty much the same result as
pthread_abort(). There are a few warnings and disclaimers on the
pthread_abort() page that also apply to ThreadDestroy() (and maybe
should be mentioned there, Steve!).

If you want a safer way to destroy a thread, use the POSIX
pthread_cancel() call. It will ensure that any cleanup handlers get
called before the thread disappears, which will leave the standard
library in a sane state. One caveat here is that by default, a thread
only notices a pending cancellation request during certain library calls
(check for functions flagged as “cancellation points”). You can change
the thread to be cancellable asynchronously, but it’s not safe for such
a thread to call most library functions (including printf()).


I suspect that the last argument shouldn’t be NULL. Here’s what the
docs say this argument is:

The value to make available to a to a thread that joins a nondetached
thread that’s destroyed.

The docs for pthread_exit() – which calls ThreadDestroy() – say:

A pointer to a value that you want to be made available to any thread
joining the thread that you’re terminating.


Steve Reid > stever@qnx.com
Technical Editor
QNX Software Systems

Thank you for reply. That’s what I thought, although I remember I read
an article which said, that when a thread terminates, all mutexes held
by the thread are released. Probably it was article about another OS.

Best regards
Lukas Kunc

Wojtek Lerch wrote:

Steve Reid wrote:

Lukas Kunc <> Lukas.Kunc@soft-gate.de> > wrote:

if (ThreadDestroy(thread, -1, NULL) == -1)


ThreadDestroy() just causes the thread to disappear, without calling any
cancellation handlers. If the thread holds any mutexes when you destroy
it, they won’t be unlocked. In particular, if you destroy a thread
while it’s running printf(), you’re likely to leave stdout locked by a
non-existent thread, causing any other thread that calls printf() to
block indefinitely.

In short, a ThreadDestroy() call has pretty much the same result as
pthread_abort(). There are a few warnings and disclaimers on the
pthread_abort() page that also apply to ThreadDestroy() (and maybe
should be mentioned there, Steve!).

If you want a safer way to destroy a thread, use the POSIX
pthread_cancel() call. It will ensure that any cleanup handlers get
called before the thread disappears, which will leave the standard
library in a sane state. One caveat here is that by default, a thread
only notices a pending cancellation request during certain library calls
(check for functions flagged as “cancellation points”). You can change
the thread to be cancellable asynchronously, but it’s not safe for such
a thread to call most library functions (including printf()).


I suspect that the last argument shouldn’t be NULL. Here’s what the
docs say this argument is:

The value to make available to a to a thread that joins a
nondetached thread that’s destroyed.
The docs for pthread_exit() – which calls ThreadDestroy() – say:

A pointer to a value that you want to be made available to any
thread joining the thread that you’re terminating.

Steve Reid > stever@qnx.com
Technical Editor
QNX Software Systems