Hi
I saw that there are known problems with linux-threads and asynchronous
signals, but I could not find a matching error-report at
www-gnats.gnu.org.
So I am posting my observations of the problem. Maybe this helps
debugging the problems.
I also heard that this could be a kernel problem. This is the reason why
I'm posting this also to the kernel-list.
Please CC me answers because I'm not subscribed to all the
mailing-lists.
Thank you for your help
Reto
--------------------------------
Environment:
------------
Redhat 6.1, Kernel 2.2.14
SMP and UP on Alpha
C-Library: libc-2.1.3.so
Kernel modules 2.3.10-pre1
Gnu C egcs-2.91.66
Binutils 2.9.1.0.24
Dynamic linker ldd (GNU libc) 2.1.3
Linux C++ Library ..
Procps 2.0.5
Mount 2.9o
Net-tools 1.51
Console-tools 1999.03.02
Sh-utils 1.16
Modules Loaded eip elan rms qsw nfsd
Synopsis:
---------
Sending sigterm to a signal handler can cause pthread_cond_wait to
return.
Description:
------------
See attached example.
The threads are waiting for a condition. When I press CTRL-C, sometimes
the
threads waiting for the condition "wake up". This happens almost
everytime on
Alpha SMP and happens sometime on Alpha UP. I could not try Intel SMP
yet. Intel UP seems to work fine (but one never knows ;-)
Testcode:
---------
/*
* thread.c
*
* compile with:
* gcc -g -O2 -D_REENTRANT -o thread thread.c -lpthread
*
* run ./thread
* press b to broadcast condition
* press s to signal condition
* press ctrl-c to call signal handler and set terminate variable
* press b after ctrl-c to broadcast condition -> threads terminate
*
* Strange behaviour on alpha (UP ,SMP even worse), linux 2.2.14:
* pressing ctrl-c sometimes lets foo come out of the
* pthread_cond_wait(&cond, &mutex); condition
*
* On intel UP, this seems to work...
*
* Reto Baettig ( baettig@scs.ch )
* 5-23-00
*
*/
#include <pthread.h>
#include <unistd.h>
#include <stdio.h>
#include <signal.h>
#include <asm/atomic.h>
#define NUM_THREADS 10
pthread_cond_t cond = PTHREAD_COND_INITIALIZER;
pthread_mutex_t mutex = PTHREAD_MUTEX_INITIALIZER;
int terminate = 0;
int numthreads = 0;
void *foo(void *arg)
{
for (;;) {
pthread_mutex_lock(&mutex);
if (terminate) {
goto terminate;
}
pthread_cond_wait(&cond, &mutex);
if (terminate) {
goto terminate;
}
pthread_mutex_unlock(&mutex);
printf("I got the signal!!!! 0x%Lx\n", pthread_self());
}
terminate:
numthreads--;
pthread_mutex_unlock(&mutex);
printf("I'm leaving now...\n");
return NULL;
}
void bar(int signo)
{
terminate++; /* Nobody decrements that variable, and we just
check it to be != 0, so I think that this is
safe and
that we do not need a mutex here */
/*
* we can also remove the next line. The strange behaviour
* occurs less often but still occurs...
*/
printf("%i: Got sigint!!! %i threads living...\n",
pthread_self(),numthreads);
}
int main(int argc, char *argv[])
{
pthread_t threads[NUM_THREADS];
pthread_attr_t attr;
int i;
char buffer[80];
pthread_attr_init(&attr);
for (i=0; i < NUM_THREADS; i++) {
if (pthread_create(&threads[i], &attr, foo, NULL) < 0) {
perror("pthread_create");
exit(1);
}
pthread_mutex_lock(&mutex);
numthreads++;
pthread_mutex_unlock(&mutex);
}
signal(SIGINT, bar);
while (fgets(buffer, 80, stdin)) {
switch (toupper(*buffer)) {
case 'B' :
pthread_cond_broadcast(&cond);
break;
case 'S' :
pthread_cond_signal(&cond);
break;
default :
printf("Not an option.\n");
break;
}
pthread_mutex_lock(&mutex);
if (!numthreads)
return 0; /* All the threads we had terminated
*/
pthread_mutex_unlock(&mutex);
}
return 0;
}
-
To unsubscribe from this list: send the line "unsubscribe linux-kernel" in
the body of a message to majordomo@vger.rutgers.edu
Please read the FAQ at http://www.tux.org/lkml/
This archive was generated by hypermail 2b29 : Tue May 23 2000 - 21:00:25 EST