S/390: Add hwcap value for transactional execution.
[platform/upstream/glibc.git] / misc / tst-pselect.c
1 #include <errno.h>
2 #include <signal.h>
3 #include <stdio.h>
4 #include <unistd.h>
5 #include <sys/select.h>
6 #include <sys/wait.h>
7
8
9 static volatile int handler_called;
10
11 static void
12 handler (int sig)
13 {
14   handler_called = 1;
15 }
16
17
18 static int
19 do_test (void)
20 {
21   struct sigaction sa;
22   sa.sa_handler = handler;
23   sa.sa_flags = 0;
24   sigemptyset (&sa.sa_mask);
25
26   if (sigaction (SIGUSR1, &sa, NULL) != 0)
27     {
28       puts ("sigaction failed");
29       return 1;
30     }
31
32   sa.sa_handler = SIG_IGN;
33   sa.sa_flags = SA_NOCLDWAIT;
34
35   if (sigaction (SIGCHLD, &sa, NULL) != 0)
36     {
37       puts ("2nd sigaction failed");
38       return 1;
39     }
40
41   if (sigblock (sigmask (SIGUSR1)) != 0)
42     {
43       puts ("sigblock failed");
44       return 1;
45     }
46
47   int fds[2][2];
48
49   if (pipe (fds[0]) != 0 || pipe (fds[1]) != 0)
50     {
51       puts ("pipe failed");
52       return 1;
53     }
54
55   fd_set rfds;
56   FD_ZERO (&rfds);
57
58   sigset_t ss;
59   sigprocmask (SIG_SETMASK, NULL, &ss);
60   sigdelset (&ss, SIGUSR1);
61
62   struct timespec to = { .tv_sec = 0, .tv_nsec = 500000000 };
63
64   pid_t parent = getpid ();
65   pid_t p = fork ();
66   if (p == 0)
67     {
68       close (fds[0][1]);
69       close (fds[1][0]);
70
71       FD_SET (fds[0][0], &rfds);
72
73       int e;
74       do
75         {
76           if (getppid () != parent)
77             exit (2);
78
79           errno = 0;
80           e = pselect (fds[0][0] + 1, &rfds, NULL, NULL, &to, &ss);
81         }
82       while (e == 0);
83
84       if (e != -1)
85         {
86           puts ("child: pselect did not fail");
87           return 0;
88         }
89       if (errno != EINTR)
90         {
91           puts ("child: pselect did not set errno to EINTR");
92           return 0;
93         }
94
95       TEMP_FAILURE_RETRY (write (fds[1][1], "foo", 3));
96
97       exit (0);
98     }
99
100   close (fds[0][0]);
101   close (fds[1][1]);
102
103   FD_SET (fds[1][0], &rfds);
104
105   kill (p, SIGUSR1);
106
107   int e = pselect (fds[1][0] + 1, &rfds, NULL, NULL, NULL, &ss);
108   if (e == -1)
109     {
110       puts ("parent: pselect failed");
111       return 1;
112     }
113   if (e != 1)
114     {
115       puts ("parent: pselect did not report readable fd");
116       return 1;
117     }
118   if (!FD_ISSET (fds[1][0], &rfds))
119     {
120       puts ("parent: pselect reports wrong fd");
121       return 1;
122     }
123
124   return 0;
125 }
126
127 #define TEST_FUNCTION do_test ()
128 #include "../test-skeleton.c"