1 /*
2 * Copyright (c) 2023 Huawei Device Co., Ltd.
3 * Licensed under the Apache License, Version 2.0 (the "License");
4 * you may not use this file except in compliance with the License.
5 * You may obtain a copy of the License at
6 *
7 * http://www.apache.org/licenses/LICENSE-2.0
8 *
9 * Unless required by applicable law or agreed to in writing, software
10 * distributed under the License is distributed on an "AS IS" BASIS,
11 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12 * See the License for the specific language governing permissions and
13 * limitations under the License.
14 */
15
16 #include <sigchain.h>
17 #include <wchar.h>
18 #include <stdlib.h>
19 #include "test.h"
20 #include "functionalext.h"
21 #include "sigchain_util.h"
22
23 static int g_count = 0;
24 /**
25 * @brief the special handler
26 */
sigchain_special_sigabrt_handler1(int signo,siginfo_t * siginfo,void * ucontext_raw)27 static bool sigchain_special_sigabrt_handler1(int signo, siginfo_t *siginfo, void *ucontext_raw)
28 {
29 g_count++;
30 EXPECT_FALSE("sigchain_rm_special_handler_001", true);
31 return false;
32 }
33
34 /**
35 * @brief the special handler
36 */
sigchain_special_sigabrt_handler2(int signo,siginfo_t * siginfo,void * ucontext_raw)37 static bool sigchain_special_sigabrt_handler2(int signo, siginfo_t *siginfo, void *ucontext_raw)
38 {
39 g_count++;
40 EXPECT_FALSE("sigchain_rm_special_handler_001", true);
41 return true;
42 }
43
44 /**
45 * @tc.name : sigchain_rm_special_handler_001
46 * @tc.desc : The signal is not registered with the kernel, call remove_special_signal_handler to remove
47 * two special handlers
48 * @tc.level : Level 0
49 */
sigchain_rm_special_handler_001()50 static void sigchain_rm_special_handler_001()
51 {
52 struct signal_chain_action sigcont = {
53 .sca_sigaction = sigchain_special_sigabrt_handler1,
54 .sca_mask = {},
55 .sca_flags = 0,
56 };
57 add_special_signal_handler(SIGCONT, &sigcont);
58
59 struct signal_chain_action sigcont1 = {
60 .sca_sigaction = sigchain_special_sigabrt_handler2,
61 .sca_mask = {},
62 .sca_flags = SIGCHAIN_ALLOW_NORETURN,
63 };
64 add_special_signal_handler(SIGCONT, &sigcont1);
65
66 if (get_sigchain_mask_enable()) {
67 sigset_t set = {0};
68 int signo[SIGCHIAN_TEST_SIGNAL_NUM_1] = {SIGCONT};
69 SIGCHAIN_TEST_SET_MASK(set, "sigchain_rm_special_handler_001", signo, SIGCHIAN_TEST_SIGNAL_NUM_1);
70 }
71 remove_special_signal_handler(SIGCONT, sigchain_special_sigabrt_handler1);
72 remove_special_signal_handler(SIGCONT, sigchain_special_sigabrt_handler2);
73
74 raise(SIGCONT);
75 EXPECT_EQ("sigchain_rm_special_handler_001", g_count, 0);
76 }
77
78 /**
79 * @brief the special handler
80 */
sigchain_special_sighup_handler1(int signo,siginfo_t * siginfo,void * ucontext_raw)81 static bool sigchain_special_sighup_handler1(int signo, siginfo_t *siginfo, void *ucontext_raw)
82 {
83 g_count++;
84 EXPECT_FALSE("sigchain_rm_special_handler_002", true);
85 return false;
86 }
87
88 /**
89 * @brief the special handler
90 */
sigchain_special_sighup_handler2(int signo,siginfo_t * siginfo,void * ucontext_raw)91 static bool sigchain_special_sighup_handler2(int signo, siginfo_t *siginfo, void *ucontext_raw)
92 {
93 g_count++;
94 EXPECT_FALSE("sigchain_rm_special_handler_002", true);
95 return false;
96 }
97
98 /**
99 * @brief the signal handler
100 */
signal_sighup_handler(int signo)101 static void signal_sighup_handler(int signo)
102 {
103 g_count++;
104 EXPECT_EQ("sigchain_rm_special_handler_002", signo, SIGHUP);
105 }
106
107 /**
108 * @tc.name : sigchain_rm_special_handler_002
109 * @tc.desc : The signal is registered with the kernel(Using signal), call
110 * remove_special_signal_handler to remove two special handlers
111 * @tc.level : Level 0
112 */
sigchain_rm_special_handler_002()113 static void sigchain_rm_special_handler_002()
114 {
115 g_count = 0;
116 signal(SIGHUP, signal_sighup_handler);
117
118 struct signal_chain_action sighup = {
119 .sca_sigaction = sigchain_special_sighup_handler1,
120 .sca_mask = {},
121 .sca_flags = 0,
122 };
123 add_special_signal_handler(SIGHUP, &sighup);
124
125 struct signal_chain_action sighup1 = {
126 .sca_sigaction = sigchain_special_sighup_handler2,
127 .sca_mask = {},
128 .sca_flags = 0,
129 };
130 add_special_signal_handler(SIGHUP, &sighup1);
131
132 if (get_sigchain_mask_enable()) {
133 sigset_t set = {0};
134 int signo[SIGCHIAN_TEST_SIGNAL_NUM_1] = {SIGHUP};
135 SIGCHAIN_TEST_SET_MASK(set, "sigchain_rm_special_handler_002", signo, SIGCHIAN_TEST_SIGNAL_NUM_1);
136 }
137 remove_special_signal_handler(SIGHUP, sigchain_special_sighup_handler1);
138 remove_special_signal_handler(SIGHUP, sigchain_special_sighup_handler2);
139
140 raise(SIGHUP);
141 EXPECT_EQ("sigchain_rm_special_handler_002", g_count, SIGCHIAN_TEST_SIGNAL_NUM_1);
142 }
143
144 /**
145 * @brief the special handler
146 */
sigchain_special_sigusr2_handler1(int signo,siginfo_t * siginfo,void * ucontext_raw)147 static bool sigchain_special_sigusr2_handler1(int signo, siginfo_t *siginfo, void *ucontext_raw)
148 {
149 g_count++;
150 EXPECT_FALSE("sigchain_rm_special_handler_003", true);
151 return false;
152 }
153
154 /**
155 * @brief the special handler
156 */
sigchain_special_sigusr2_handler2(int signo,siginfo_t * siginfo,void * ucontext_raw)157 static bool sigchain_special_sigusr2_handler2(int signo, siginfo_t *siginfo, void *ucontext_raw)
158 {
159 g_count++;
160 EXPECT_FALSE("sigchain_rm_special_handler_003", true);
161 return false;
162 }
163
164 /**
165 * @brief the signal handler
166 */
signal_sigusr2_sigaction(int signo)167 static void signal_sigusr2_sigaction(int signo)
168 {
169 g_count++;
170 EXPECT_EQ("sigchain_rm_special_handler_003", signo, SIGUSR2);
171 }
172
173 /**
174 * @tc.name : sigchain_rm_special_handler_003
175 * @tc.desc : The signal is registered with the kernel(Using sigaction), call
176 * remove_special_signal_handler to remove two special handlers
177 * @tc.level : Level 0
178 */
sigchain_rm_special_handler_003()179 static void sigchain_rm_special_handler_003()
180 {
181 g_count = 0;
182 struct sigaction sigac = {
183 .sa_handler = signal_sigusr2_sigaction,
184 };
185 sigaction(SIGUSR2, &sigac, NULL);
186
187 struct signal_chain_action sigusr2 = {
188 .sca_sigaction = sigchain_special_sigusr2_handler1,
189 .sca_mask = {},
190 .sca_flags = 0,
191 };
192 add_special_signal_handler(SIGUSR2, &sigusr2);
193
194 struct signal_chain_action sigusr21 = {
195 .sca_sigaction = sigchain_special_sigusr2_handler2,
196 .sca_mask = {},
197 .sca_flags = 0,
198 };
199 add_special_signal_handler(SIGUSR2, &sigusr21);
200
201 if (get_sigchain_mask_enable()) {
202 sigset_t set = {0};
203 int signo[SIGCHIAN_TEST_SIGNAL_NUM_1] = {SIGUSR2};
204 SIGCHAIN_TEST_SET_MASK(set, "sigchain_rm_special_handler_003", signo, SIGCHIAN_TEST_SIGNAL_NUM_1);
205 }
206
207 remove_special_signal_handler(SIGUSR2, sigchain_special_sigusr2_handler1);
208 remove_special_signal_handler(SIGUSR2, sigchain_special_sigusr2_handler2);
209 raise(SIGUSR2);
210 EXPECT_EQ("sigchain_rm_special_handler_003", g_count, SIGCHIAN_TEST_SIGNAL_NUM_1);
211 }
212
213 /**
214 * @brief the special handler
215 */
sigchain_special_sigterm_handler(int signo,siginfo_t * siginfo,void * ucontext_raw)216 static bool sigchain_special_sigterm_handler(int signo, siginfo_t *siginfo, void *ucontext_raw)
217 {
218 g_count++;
219 EXPECT_FALSE("sigchain_rm_special_handler_004", true);
220 return true;
221 }
222
223 /**
224 * @tc.name : sigchain_rm_special_handler_004
225 * @tc.desc : The signal is not registered with the kernel, call remove_special_signal_handler to remove
226 * a special handler.
227 * @tc.level : Level 0
228 */
sigchain_rm_special_handler_004()229 static void sigchain_rm_special_handler_004()
230 {
231 g_count = 0;
232 struct signal_chain_action sigcont = {
233 .sca_sigaction = sigchain_special_sigterm_handler,
234 .sca_mask = {},
235 .sca_flags = 0,
236 };
237 add_special_signal_handler(SIGCONT, &sigcont);
238
239
240 if (get_sigchain_mask_enable()) {
241 sigset_t set = {0};
242 int signo[SIGCHIAN_TEST_SIGNAL_NUM_1] = {SIGCONT};
243 SIGCHAIN_TEST_SET_MASK(set, "sigchain_rm_special_handler_004", signo, SIGCHIAN_TEST_SIGNAL_NUM_1);
244 }
245 remove_special_signal_handler(SIGCONT, sigchain_special_sigterm_handler);
246
247 raise(SIGCONT);
248 EXPECT_EQ("sigchain_rm_special_handler_004", g_count, 0);
249 }
250
251 /**
252 * @brief the special handler
253 */
sigchain_special_64_handler(int signo,siginfo_t * siginfo,void * ucontext_raw)254 static bool sigchain_special_64_handler(int signo, siginfo_t *siginfo, void *ucontext_raw)
255 {
256 EXPECT_FALSE("sigchain_rm_special_handler_005", true);
257 g_count++;
258 return false;
259 }
260
261 /**
262 * @brief the signal handler
263 */
signal_64_handler(int signo)264 static void signal_64_handler(int signo)
265 {
266 g_count++;
267 EXPECT_EQ("sigchain_rm_special_handler_005", signo, SIGCHAIN_SIGNAL_64);
268 }
269
270 /**
271 * @tc.name : sigchain_rm_special_handler_005
272 * @tc.desc : The signal is registered with the kernel(Using signal), call remove_special_signal_handler to remove
273 * a special handler.
274 * @tc.level : Level 0
275 */
sigchain_rm_special_handler_005()276 static void sigchain_rm_special_handler_005()
277 {
278 g_count = 0;
279 signal(SIGCHAIN_SIGNAL_64, signal_64_handler);
280
281 struct signal_chain_action sighup = {
282 .sca_sigaction = sigchain_special_64_handler,
283 .sca_mask = {},
284 .sca_flags = 0,
285 };
286 add_special_signal_handler(SIGCHAIN_SIGNAL_64, &sighup);
287
288 if (get_sigchain_mask_enable()) {
289 sigset_t set = {0};
290 int signo[SIGCHIAN_TEST_SIGNAL_NUM_1] = {SIGCHAIN_SIGNAL_64};
291 SIGCHAIN_TEST_SET_MASK(set, "sigchain_rm_special_handler_005", signo, SIGCHIAN_TEST_SIGNAL_NUM_1);
292 }
293 remove_special_signal_handler(SIGCHAIN_SIGNAL_64, sigchain_special_64_handler);
294
295 raise(SIGCHAIN_SIGNAL_64);
296 EXPECT_EQ("sigchain_rm_special_handler_005", g_count, SIGCHIAN_TEST_SIGNAL_NUM_1);
297 }
298
299 /**
300 * @brief the special handler
301 */
sigchain_special_37_handler(int signo,siginfo_t * siginfo,void * ucontext_raw)302 static bool sigchain_special_37_handler(int signo, siginfo_t *siginfo, void *ucontext_raw)
303 {
304 g_count++;
305 EXPECT_FALSE("sigchain_rm_special_handler_006", true);
306 return false;
307 }
308
309 /**
310 * @brief the signal handler
311 */
signal_37_sigaction(int signo)312 static void signal_37_sigaction(int signo)
313 {
314 g_count++;
315 EXPECT_EQ("sigchain_rm_special_handler_006", signo, SIGCHAIN_SIGNAL_37);
316 }
317
318 /**
319 * @tc.name : sigchain_rm_special_handler_006
320 * @tc.desc : The signal is registered with the kernel(Using sigaction), call remove_special_signal_handler
321 * to remove a special handler.
322 * @tc.level : Level 0
323 */
sigchain_rm_special_handler_006()324 static void sigchain_rm_special_handler_006()
325 {
326 g_count = 0;
327 struct sigaction sigac = {
328 .sa_handler = signal_37_sigaction,
329 };
330 sigaction(SIGCHAIN_SIGNAL_37, &sigac, NULL);
331
332 struct signal_chain_action sig37 = {
333 .sca_sigaction = sigchain_special_37_handler,
334 .sca_mask = {},
335 .sca_flags = 0,
336 };
337 add_special_signal_handler(SIGCHAIN_SIGNAL_37, &sig37);
338
339 if (get_sigchain_mask_enable()) {
340 sigset_t set = {0};
341 int signo[SIGCHIAN_TEST_SIGNAL_NUM_1] = {SIGCHAIN_SIGNAL_37};
342 SIGCHAIN_TEST_SET_MASK(set, "sigchain_rm_special_handler_006", signo, SIGCHIAN_TEST_SIGNAL_NUM_1);
343 }
344 remove_special_signal_handler(SIGCHAIN_SIGNAL_37, sigchain_special_37_handler);
345
346 raise(SIGCHAIN_SIGNAL_37);
347 EXPECT_EQ("sigchain_rm_special_handler_006", g_count, SIGCHIAN_TEST_SIGNAL_NUM_1);
348 }
349
350 /**
351 * @brief the special handler
352 */
sigchain_special_quit_handler(int signo,siginfo_t * siginfo,void * ucontext_raw)353 static bool sigchain_special_quit_handler(int signo, siginfo_t *siginfo, void *ucontext_raw)
354 {
355 g_count++;
356 EXPECT_FALSE("sigchain_rm_all_special_handler_007", true);
357 return false;
358 }
359
sigchain_special_quit_handler1(int signo,siginfo_t * siginfo,void * ucontext_raw)360 static bool sigchain_special_quit_handler1(int signo, siginfo_t *siginfo, void *ucontext_raw)
361 {
362 g_count++;
363 EXPECT_FALSE("sigchain_rm_all_special_handler_007", true);
364 return false;
365 }
366
367 /**
368 * @brief the signal handler
369 */
signal_quit_sigaction(int signo)370 static void signal_quit_sigaction(int signo)
371 {
372 g_count++;
373 EXPECT_EQ("sigchain_rm_all_special_handler_007", signo, SIGQUIT);
374 }
375
376 /**
377 * @tc.name : sigchain_rm_all_special_handler_007
378 * @tc.desc : The signal is registered with the kernel(Using sigaction), call remove_special_signal_handler
379 * to remove a special handler.
380 * @tc.level : Level 0
381 */
sigchain_rm_all_special_handler_007()382 static void sigchain_rm_all_special_handler_007()
383 {
384 g_count = 0;
385 struct sigaction sigac = {
386 .sa_handler = signal_quit_sigaction,
387 };
388 sigaction(SIGQUIT, &sigac, NULL);
389
390 struct signal_chain_action sigquit = {
391 .sca_sigaction = sigchain_special_quit_handler,
392 .sca_mask = {},
393 .sca_flags = 0,
394 };
395 add_special_signal_handler(SIGQUIT, &sigquit);
396
397 struct signal_chain_action sigquit1 = {
398 .sca_sigaction = sigchain_special_quit_handler1,
399 .sca_mask = {},
400 .sca_flags = 0,
401 };
402 add_special_signal_handler(SIGQUIT, &sigquit1);
403
404 if (get_sigchain_mask_enable()) {
405 sigset_t set = {0};
406 int signo[SIGCHIAN_TEST_SIGNAL_NUM_1] = {SIGQUIT};
407 SIGCHAIN_TEST_SET_MASK(set, "sigchain_rm_all_special_handler_007", signo, SIGCHIAN_TEST_SIGNAL_NUM_1);
408 }
409 remove_all_special_handler(SIGQUIT);
410
411 raise(SIGQUIT);
412 EXPECT_EQ("sigchain_rm_all_special_handler_007", g_count, SIGCHIAN_TEST_SIGNAL_NUM_1);
413 }
414
main(void)415 int main(void)
416 {
417 sigchain_rm_special_handler_001();
418 sigchain_rm_special_handler_002();
419 sigchain_rm_special_handler_003();
420 sigchain_rm_special_handler_004();
421 sigchain_rm_special_handler_005();
422 sigchain_rm_special_handler_006();
423 sigchain_rm_all_special_handler_007();
424 return t_status;
425 }