1*2874c5fdSThomas Gleixner // SPDX-License-Identifier: GPL-2.0-or-later
2ef186331SCyril Bur /*
3ef186331SCyril Bur * Copyright 2016, Cyril Bur, IBM Corp.
4ef186331SCyril Bur *
5ef186331SCyril Bur * Sending one self a signal should always get delivered.
6ef186331SCyril Bur */
7ef186331SCyril Bur
8ef186331SCyril Bur #include <signal.h>
9ef186331SCyril Bur #include <stdio.h>
10ef186331SCyril Bur #include <stdlib.h>
11ef186331SCyril Bur #include <string.h>
12ef186331SCyril Bur #include <sys/types.h>
13ef186331SCyril Bur #include <sys/wait.h>
14ef186331SCyril Bur #include <unistd.h>
15ef186331SCyril Bur
16ef186331SCyril Bur #include <altivec.h>
17ef186331SCyril Bur
18ef186331SCyril Bur #include "utils.h"
19ef186331SCyril Bur
20ef186331SCyril Bur #define MAX_ATTEMPT 500000
21ef186331SCyril Bur #define TIMEOUT 5
22ef186331SCyril Bur
23ef186331SCyril Bur extern long signal_self(pid_t pid, int sig);
24ef186331SCyril Bur
25ef186331SCyril Bur static sig_atomic_t signaled;
26ef186331SCyril Bur static sig_atomic_t fail;
27ef186331SCyril Bur
signal_handler(int sig)28ef186331SCyril Bur static void signal_handler(int sig)
29ef186331SCyril Bur {
30ef186331SCyril Bur if (sig == SIGUSR1)
31ef186331SCyril Bur signaled = 1;
32ef186331SCyril Bur else
33ef186331SCyril Bur fail = 1;
34ef186331SCyril Bur }
35ef186331SCyril Bur
test_signal()36ef186331SCyril Bur static int test_signal()
37ef186331SCyril Bur {
38ef186331SCyril Bur int i;
39ef186331SCyril Bur struct sigaction act;
40ef186331SCyril Bur pid_t ppid = getpid();
41ef186331SCyril Bur pid_t pid;
42ef186331SCyril Bur
43ef186331SCyril Bur act.sa_handler = signal_handler;
44ef186331SCyril Bur act.sa_flags = 0;
45ef186331SCyril Bur sigemptyset(&act.sa_mask);
46ef186331SCyril Bur if (sigaction(SIGUSR1, &act, NULL) < 0) {
47ef186331SCyril Bur perror("sigaction SIGUSR1");
48ef186331SCyril Bur exit(1);
49ef186331SCyril Bur }
50ef186331SCyril Bur if (sigaction(SIGALRM, &act, NULL) < 0) {
51ef186331SCyril Bur perror("sigaction SIGALRM");
52ef186331SCyril Bur exit(1);
53ef186331SCyril Bur }
54ef186331SCyril Bur
55ef186331SCyril Bur /* Don't do this for MAX_ATTEMPT, its simply too long */
56ef186331SCyril Bur for(i = 0; i < 1000; i++) {
57ef186331SCyril Bur pid = fork();
58ef186331SCyril Bur if (pid == -1) {
59ef186331SCyril Bur perror("fork");
60ef186331SCyril Bur exit(1);
61ef186331SCyril Bur }
62ef186331SCyril Bur if (pid == 0) {
63ef186331SCyril Bur signal_self(ppid, SIGUSR1);
64ef186331SCyril Bur exit(1);
65ef186331SCyril Bur } else {
66ef186331SCyril Bur alarm(0); /* Disable any pending */
67ef186331SCyril Bur alarm(2);
68ef186331SCyril Bur while (!signaled && !fail)
69ef186331SCyril Bur asm volatile("": : :"memory");
70ef186331SCyril Bur if (!signaled) {
71ef186331SCyril Bur fprintf(stderr, "Didn't get signal from child\n");
72ef186331SCyril Bur FAIL_IF(1); /* For the line number */
73ef186331SCyril Bur }
74ef186331SCyril Bur /* Otherwise we'll loop too fast and fork() will eventually fail */
75ef186331SCyril Bur waitpid(pid, NULL, 0);
76ef186331SCyril Bur }
77ef186331SCyril Bur }
78ef186331SCyril Bur
79ef186331SCyril Bur for (i = 0; i < MAX_ATTEMPT; i++) {
80ef186331SCyril Bur long rc;
81ef186331SCyril Bur
82ef186331SCyril Bur alarm(0); /* Disable any pending */
83ef186331SCyril Bur signaled = 0;
84ef186331SCyril Bur alarm(TIMEOUT);
85ef186331SCyril Bur rc = signal_self(ppid, SIGUSR1);
86ef186331SCyril Bur if (rc) {
87ef186331SCyril Bur fprintf(stderr, "(%d) Fail reason: %d rc=0x%lx",
88ef186331SCyril Bur i, fail, rc);
89ef186331SCyril Bur FAIL_IF(1); /* For the line number */
90ef186331SCyril Bur }
91ef186331SCyril Bur while (!signaled && !fail)
92ef186331SCyril Bur asm volatile("": : :"memory");
93ef186331SCyril Bur if (!signaled) {
94ef186331SCyril Bur fprintf(stderr, "(%d) Fail reason: %d rc=0x%lx",
95ef186331SCyril Bur i, fail, rc);
96ef186331SCyril Bur FAIL_IF(1); /* For the line number */
97ef186331SCyril Bur }
98ef186331SCyril Bur }
99ef186331SCyril Bur
100ef186331SCyril Bur return 0;
101ef186331SCyril Bur }
102ef186331SCyril Bur
main(void)103ef186331SCyril Bur int main(void)
104ef186331SCyril Bur {
105ef186331SCyril Bur test_harness_set_timeout(300);
106ef186331SCyril Bur return test_harness(test_signal, "signal");
107ef186331SCyril Bur }
108