• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (c) 2003, 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 sigpause() restores sig to the signal mask before
9  returning.
10 
11  Steps:
12  1. From the main() function, create a new thread. Give the new thread a
13     a second to set up for receiving a signal, add SIGTOTEST to its signal
14     mask and to suspend itself using sigpause(SIGTOTEST).
15  2. Have main() send the signal indicated by SIGTOTEST to the new thread,
16     using pthread_kill(), and using the concept of semaphores, have the main()
17  3. Once the new thread returns from sigpause, have the new thread raise
18     SIGTOTEST. At this point, SIGTOTEST should be restored to the signal mask,
19     so the signal handler should not be called yet, and the signal should be
20     pending.
21     If it is not, set the variable return_value to 1, indicating a test failure.
22  4. Now, from the new thread, set sem back to INMAIN to allow main to continue
23     running.
24  5. The PTS exit code that main() will return with will depend on the value of
25     return_value:
26 	PTS_UNRESOLVED if return value is 2
27 	PTS_PASS if return value is 0
28 	PTS_FAIL if return value is 1
29  */
30 
31 #define _XOPEN_SOURCE 600
32 
33 #include <pthread.h>
34 #include <stdio.h>
35 #include <signal.h>
36 #include <errno.h>
37 #include <unistd.h>
38 #include "posixtest.h"
39 
40 #define SIGTOTEST SIGABRT
41 #define INMAIN 0
42 #define INTHREAD 1
43 
44 static int handler_called;
45 static int return_value = 2;
46 static int sem = INMAIN;
47 
handler()48 static void handler()
49 {
50 	printf("signal was called\n");
51 	handler_called = 1;
52 	return;
53 }
54 
a_thread_func()55 static void *a_thread_func()
56 {
57 	struct sigaction act;
58 	sigset_t pendingset;
59 
60 	act.sa_flags = 0;
61 	act.sa_handler = handler;
62 	sigemptyset(&act.sa_mask);
63 	sigaction(SIGTOTEST, &act, 0);
64 	sighold(SIGTOTEST);
65 
66 	if ((sigpause(SIGTOTEST) != -1) || (errno != EINTR)) {
67 		printf("Test UNRESOLVED: sigpause didn't return -1 "
68 		       "and/or didn't set errno correctly.");
69 		return_value = 2;
70 		return NULL;
71 	}
72 
73 	sleep(1);
74 
75 	raise(SIGTOTEST);
76 	sigpending(&pendingset);
77 	if (sigismember(&pendingset, SIGTOTEST) == 1) {
78 		printf("Test PASSED: signal mask was restored when "
79 		       "sigpause returned.");
80 		return_value = 0;
81 	}
82 
83 	sem = INMAIN;
84 	return NULL;
85 }
86 
main(void)87 int main(void)
88 {
89 	pthread_t new_th;
90 
91 	if (pthread_create(&new_th, NULL, a_thread_func, NULL) != 0) {
92 		perror("Error creating thread\n");
93 		return PTS_UNRESOLVED;
94 	}
95 
96 	sleep(1);
97 
98 	if (pthread_kill(new_th, SIGTOTEST) != 0) {
99 		printf("Test UNRESOLVED: Couldn't send signal to thread\n");
100 		return PTS_UNRESOLVED;
101 	}
102 
103 	sem = INTHREAD;
104 	while (sem == INTHREAD)
105 		sleep(1);
106 
107 	if (handler_called != 1) {
108 		printf("Test UNRESOLVED: signal wasn't removed from "
109 		       "signal mask\n");
110 		return PTS_UNRESOLVED;
111 	}
112 
113 	if (return_value != 0) {
114 		if (return_value == 1)
115 			return PTS_FAIL;
116 		if (return_value == 2)
117 			return PTS_UNRESOLVED;
118 		return PTS_UNRESOLVED;
119 	}
120 
121 	printf("Test PASSED\n");
122 	return PTS_PASS;
123 }
124