Home | History | Annotate | Download | only in pthread_kill
      1 /*
      2  * Copyright (c) 2002, Intel Corporation. All rights reserved.
      3  * Created by:  salwan.searty REMOVE-THIS AT intel DOT com
      4  * This file is licensed under the GPL license.  For the full content
      5  * of this license, see the COPYING file at the top level of this
      6  * source tree.
      7 
      8  This program verifies that the pthread_kill() function requests from the
      9  kernel to deliver a specified signal to a specified thread.
     10 
     11  Using two global values of sem1 (INTHREAD and INMAIN), we are going to
     12  control  when we want execution to be in main() and when we want
     13  execution to be a_thread_func(). When the main() function sets sem1 to
     14  INTHREAD and keeps looping until sem1 gets changed back to INMAIN, the
     15  a_thread_func() will be exclusively running. Similarly, when the
     16  a_thread_func() sets sem1 to INMAIN and keeps looping until sem1 gets
     17  changed back to INTHREAD, the main() function will be exclusively
     18  running.
     19 
     20  Steps:
     21  1. From the main() function, create a new thread. Using the above
     22     methodology, let the new thread run "exclusively."
     23  2. Inside the new thread, prepare for catching the signal indicated by
     24     SIGTOTEST, and calling a handler that sets handler_called to 1. Now
     25     let the main() thread run "exclusively".
     26  3. Have main() send the signal indicated by SIGTOTEST to the new thread,
     27     using pthread_kill(). Let the new thread continue running,
     28     and from the main function, wait until handler_called is set to
     29     something other than 0.
     30  4. In the new thread, if the handler wasn't called for more than 5
     31     seconds, then set handler_called to -1, otherwise set it to 1.
     32  5. In either case, the main() function will continue execution and return
     33     a PTS_PASS if handler_called was 1, and a PTS_FAIL if handler_called
     34     was -1.
     35  */
     36 
     37 #include <pthread.h>
     38 #include <stdio.h>
     39 #include <signal.h>
     40 #include <errno.h>
     41 #include <unistd.h>
     42 #include "posixtest.h"
     43 
     44 #define INTHREAD 0
     45 #define INMAIN 1
     46 #define SIGTOTEST SIGABRT
     47 
     48 int sem1;			/* Manual semaphore */
     49 int handler_called = 0;
     50 
     51 void handler()
     52 {
     53 	printf("signal was called\n");
     54 	handler_called = 1;
     55 	return;
     56 }
     57 
     58 void *a_thread_func()
     59 {
     60 	struct sigaction act;
     61 	act.sa_flags = 0;
     62 	act.sa_handler = handler;
     63 	sigemptyset(&act.sa_mask);
     64 	sigaction(SIGTOTEST, &act, 0);
     65 
     66 	sem1 = INMAIN;
     67 
     68 	while (sem1 == INMAIN)
     69 		sleep(1);
     70 
     71 	sleep(5);
     72 
     73 	handler_called = -1;
     74 	pthread_exit(0);
     75 	return NULL;
     76 }
     77 
     78 int main(void)
     79 {
     80 	pthread_t new_th;
     81 
     82 	sem1 = INTHREAD;
     83 
     84 	if (pthread_create(&new_th, NULL, a_thread_func, NULL) != 0) {
     85 		perror("Error creating thread\n");
     86 		return PTS_UNRESOLVED;
     87 	}
     88 
     89 	while (sem1 == INTHREAD)
     90 		sleep(1);
     91 
     92 	if (pthread_kill(new_th, SIGTOTEST) != 0) {
     93 		printf("Test FAILED: Couldn't send signal to thread\n");
     94 		return PTS_FAIL;
     95 	}
     96 
     97 	sem1 = INTHREAD;
     98 
     99 	while (handler_called == 0)
    100 		sleep(1);
    101 
    102 	if (handler_called == -1) {
    103 		printf("Test FAILED: Kill request timed out\n");
    104 		return PTS_FAIL;
    105 	} else if (handler_called == 0) {
    106 		printf("Test FAILED: Thread did not recieve or handle\n");
    107 		return PTS_FAIL;
    108 	}
    109 
    110 	printf("Test PASSED\n");
    111 	return PTS_PASS;
    112 }
    113