Update syscall lists for Linux 6.5
[glibc.git] / sysdeps / pthread / tst-cancel4.c
blob4c9e8670ca8d18430ca57647979c09338a4bce1b
1 /* Copyright (C) 2002-2023 Free Software Foundation, Inc.
2 This file is part of the GNU C Library.
4 The GNU C Library is free software; you can redistribute it and/or
5 modify it under the terms of the GNU Lesser General Public
6 License as published by the Free Software Foundation; either
7 version 2.1 of the License, or (at your option) any later version.
9 The GNU C Library is distributed in the hope that it will be useful,
10 but WITHOUT ANY WARRANTY; without even the implied warranty of
11 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
12 Lesser General Public License for more details.
14 You should have received a copy of the GNU Lesser General Public
15 License along with the GNU C Library; if not, see
16 <https://www.gnu.org/licenses/>. */
18 /* NOTE: this tests functionality beyond POSIX. POSIX does not allow
19 exit to be called more than once. */
21 #include <stddef.h>
22 #include <stdio.h>
23 #include <stdlib.h>
24 #include <string.h>
25 #include <sys/types.h>
26 #include <sys/socket.h>
27 #include <sys/un.h>
28 #include <sys/ipc.h>
29 #include <sys/msg.h>
30 #include <unistd.h>
31 #include <errno.h>
32 #include <limits.h>
33 #include <pthread.h>
34 #include <fcntl.h>
35 #include <termios.h>
36 #include <sys/mman.h>
37 #include <sys/poll.h>
38 #include <sys/wait.h>
39 #include <sys/stat.h>
40 #include <sys/uio.h>
41 #include <libc-diag.h>
44 /* Since STREAMS are not supported in the standard Linux kernel and
45 there we don't advertise STREAMS as supported is no need to test
46 the STREAMS related functions. This affects
47 getmsg() getpmsg() putmsg()
48 putpmsg()
50 lockf() and fcntl() are tested in tst-cancel16.
52 pthread_join() is tested in tst-join5.
54 pthread_testcancel()'s only purpose is to allow cancellation. This
55 is tested in several places.
57 sem_wait() and sem_timedwait() are checked in tst-cancel1[2345] tests.
59 mq_send(), mq_timedsend(), mq_receive() and mq_timedreceive() are checked
60 in tst-mqueue8{,x} tests.
62 aio_suspend() is tested in tst-cancel17.
64 clock_nanosleep() is tested in tst-cancel18.
66 Linux sendmmsg and recvmmsg are checked in tst-cancel4_1.c and
67 tst-cancel4_2.c respectively.
70 #include "tst-cancel4-common.h"
73 #ifndef IPC_ADDVAL
74 # define IPC_ADDVAL 0
75 #endif
78 static void *
79 tf_read (void *arg)
81 int fd;
83 if (arg == NULL)
84 fd = fds[0];
85 else
87 char fname[] = "/tmp/tst-cancel4-fd-XXXXXX";
88 tempfd = fd = mkstemp (fname);
89 if (fd == -1)
90 FAIL_EXIT1 ("mkstemp failed: %m");
91 unlink (fname);
93 xpthread_barrier_wait (&b2);
96 xpthread_barrier_wait (&b2);
98 ssize_t s;
99 pthread_cleanup_push (cl, NULL);
101 char buf[100];
102 s = read (fd, buf, sizeof (buf));
104 pthread_cleanup_pop (0);
106 FAIL_EXIT1 ("read returns with %zd", s);
110 static void *
111 tf_readv (void *arg)
113 int fd;
115 if (arg == NULL)
116 fd = fds[0];
117 else
119 char fname[] = "/tmp/tst-cancel4-fd-XXXXXX";
120 tempfd = fd = mkstemp (fname);
121 if (fd == -1)
122 FAIL_EXIT1 ("mkstemp failed: %m");
123 unlink (fname);
125 xpthread_barrier_wait (&b2);
128 xpthread_barrier_wait (&b2);
130 ssize_t s;
131 pthread_cleanup_push (cl, NULL);
133 char buf[100];
134 struct iovec iov[1] = { [0] = { .iov_base = buf, .iov_len = sizeof (buf) } };
135 s = readv (fd, iov, 1);
137 pthread_cleanup_pop (0);
139 FAIL_EXIT1 ("readv returns with %zd", s);
143 static void *
144 tf_write (void *arg)
146 int fd;
148 if (arg == NULL)
149 fd = fds[1];
150 else
152 char fname[] = "/tmp/tst-cancel4-fd-XXXXXX";
153 tempfd = fd = mkstemp (fname);
154 if (fd == -1)
155 FAIL_EXIT1 ("mkstemp failed: %m");
156 unlink (fname);
158 xpthread_barrier_wait (&b2);
161 xpthread_barrier_wait (&b2);
163 ssize_t s;
164 pthread_cleanup_push (cl, NULL);
166 char buf[WRITE_BUFFER_SIZE];
167 memset (buf, '\0', sizeof (buf));
168 s = write (fd, buf, sizeof (buf));
169 /* The write can return a value higher than 0 (meaning partial write)
170 due to the SIGCANCEL, but the thread may still be pending
171 cancellation. */
172 pthread_testcancel ();
174 pthread_cleanup_pop (0);
176 FAIL_EXIT1 ("write returns with %zd", s);
180 static void *
181 tf_writev (void *arg)
183 int fd;
185 if (arg == NULL)
186 fd = fds[1];
187 else
189 char fname[] = "/tmp/tst-cancel4-fd-XXXXXX";
190 tempfd = fd = mkstemp (fname);
191 if (fd == -1)
192 FAIL_EXIT1 ("mkstemp failed: %m");
193 unlink (fname);
195 xpthread_barrier_wait (&b2);
198 xpthread_barrier_wait (&b2);
200 ssize_t s;
201 pthread_cleanup_push (cl, NULL);
203 char buf[WRITE_BUFFER_SIZE];
204 memset (buf, '\0', sizeof (buf));
205 struct iovec iov[1] = { [0] = { .iov_base = buf, .iov_len = sizeof (buf) } };
206 s = writev (fd, iov, 1);
208 pthread_cleanup_pop (0);
210 FAIL_EXIT1 ("writev returns with %zd", s);
214 static void *
215 tf_sleep (void *arg)
217 xpthread_barrier_wait (&b2);
219 if (arg != NULL)
220 xpthread_barrier_wait (&b2);
222 pthread_cleanup_push (cl, NULL);
224 sleep (arg == NULL ? 1000000 : 0);
226 pthread_cleanup_pop (0);
228 FAIL_EXIT1 ("sleep returns");
232 static void *
233 tf_usleep (void *arg)
235 xpthread_barrier_wait (&b2);
237 if (arg != NULL)
238 xpthread_barrier_wait (&b2);
240 pthread_cleanup_push (cl, NULL);
242 usleep (arg == NULL ? (useconds_t) ULONG_MAX : 0);
244 pthread_cleanup_pop (0);
246 FAIL_EXIT1 ("usleep returns");
250 static void *
251 tf_nanosleep (void *arg)
253 xpthread_barrier_wait (&b2);
255 if (arg != NULL)
256 xpthread_barrier_wait (&b2);
258 pthread_cleanup_push (cl, NULL);
260 struct timespec ts = { .tv_sec = arg == NULL ? 10000000 : 0, .tv_nsec = 0 };
261 TEMP_FAILURE_RETRY (nanosleep (&ts, &ts));
263 pthread_cleanup_pop (0);
265 FAIL_EXIT1 ("nanosleep returns");
269 static void *
270 tf_select (void *arg)
272 int fd;
274 if (arg == NULL)
275 fd = fds[0];
276 else
278 char fname[] = "/tmp/tst-cancel4-fd-XXXXXX";
279 tempfd = fd = mkstemp (fname);
280 if (fd == -1)
281 FAIL_EXIT1 ("mkstemp failed: %m");
282 unlink (fname);
284 xpthread_barrier_wait (&b2);
287 xpthread_barrier_wait (&b2);
289 fd_set rfs;
290 FD_ZERO (&rfs);
291 FD_SET (fd, &rfs);
293 int s;
294 pthread_cleanup_push (cl, NULL);
296 s = select (fd + 1, &rfs, NULL, NULL, NULL);
298 pthread_cleanup_pop (0);
300 FAIL_EXIT1 ("select returns with %d: %m", s);
304 static void *
305 tf_pselect (void *arg)
307 int fd;
309 if (arg == NULL)
310 fd = fds[0];
311 else
313 char fname[] = "/tmp/tst-cancel4-fd-XXXXXX";
314 tempfd = fd = mkstemp (fname);
315 if (fd == -1)
316 FAIL_EXIT1 ("mkstemp failed: %m");
317 unlink (fname);
319 xpthread_barrier_wait (&b2);
322 xpthread_barrier_wait (&b2);
324 fd_set rfs;
325 FD_ZERO (&rfs);
326 FD_SET (fd, &rfs);
328 int s;
329 pthread_cleanup_push (cl, NULL);
331 s = pselect (fd + 1, &rfs, NULL, NULL, NULL, NULL);
333 pthread_cleanup_pop (0);
335 FAIL_EXIT1 ("pselect returns with %d: %m", s);
339 static void *
340 tf_poll (void *arg)
342 int fd;
344 if (arg == NULL)
345 fd = fds[0];
346 else
348 char fname[] = "/tmp/tst-cancel4-fd-XXXXXX";
349 tempfd = fd = mkstemp (fname);
350 if (fd == -1)
351 FAIL_EXIT1 ("mkstemp failed: %m");
352 unlink (fname);
354 xpthread_barrier_wait (&b2);
357 xpthread_barrier_wait (&b2);
359 struct pollfd rfs[1] = { [0] = { .fd = fd, .events = POLLIN } };
361 int s;
362 pthread_cleanup_push (cl, NULL);
364 s = poll (rfs, 1, -1);
366 pthread_cleanup_pop (0);
368 FAIL_EXIT1 ("poll returns with %d: %m", s);
372 static void *
373 tf_ppoll (void *arg)
375 int fd;
377 if (arg == NULL)
378 fd = fds[0];
379 else
381 char fname[] = "/tmp/tst-cancel4-fd-XXXXXX";
382 tempfd = fd = mkstemp (fname);
383 if (fd == -1)
384 FAIL_EXIT1 ("mkstemp failed: %m");
385 unlink (fname);
387 xpthread_barrier_wait (&b2);
390 xpthread_barrier_wait (&b2);
392 struct pollfd rfs[1] = { [0] = { .fd = fd, .events = POLLIN } };
394 int s;
395 pthread_cleanup_push (cl, NULL);
397 s = ppoll (rfs, 1, NULL, NULL);
399 pthread_cleanup_pop (0);
401 FAIL_EXIT1 ("ppoll returns with %d: %m", s);
405 static void *
406 tf_wait (void *arg)
408 pid_t pid = fork ();
409 if (pid == -1)
410 FAIL_EXIT1 ("fork: %m");
412 if (pid == 0)
414 /* Make the program disappear after a while. */
415 if (arg == NULL)
416 sleep (10);
417 exit (0);
420 if (arg != NULL)
422 struct timespec ts = { .tv_sec = 0, .tv_nsec = 100000000 };
423 while (nanosleep (&ts, &ts) != 0)
424 continue;
426 xpthread_barrier_wait (&b2);
429 xpthread_barrier_wait (&b2);
431 int s;
432 pthread_cleanup_push (cl, NULL);
434 s = wait (NULL);
436 pthread_cleanup_pop (0);
438 FAIL_EXIT1 ("wait returns with %d: %m", s);
442 static void *
443 tf_waitpid (void *arg)
445 pid_t pid = fork ();
446 if (pid == -1)
447 FAIL_EXIT1 ("fork: %m");
449 if (pid == 0)
451 /* Make the program disappear after a while. */
452 if (arg == NULL)
453 sleep (10);
454 exit (0);
457 if (arg != NULL)
459 struct timespec ts = { .tv_sec = 0, .tv_nsec = 100000000 };
460 while (nanosleep (&ts, &ts) != 0)
461 continue;
463 xpthread_barrier_wait (&b2);
466 xpthread_barrier_wait (&b2);
468 int s;
469 pthread_cleanup_push (cl, NULL);
471 s = waitpid (-1, NULL, 0);
473 pthread_cleanup_pop (0);
475 FAIL_EXIT1 ("waitpid returns with %d: %m", s);
479 static void *
480 tf_waitid (void *arg)
482 pid_t pid = fork ();
483 if (pid == -1)
484 FAIL_EXIT1 ("fork: %m");
486 if (pid == 0)
488 /* Make the program disappear after a while. */
489 if (arg == NULL)
490 sleep (10);
491 exit (0);
494 if (arg != NULL)
496 struct timespec ts = { .tv_sec = 0, .tv_nsec = 100000000 };
497 while (nanosleep (&ts, &ts) != 0)
498 continue;
500 xpthread_barrier_wait (&b2);
503 xpthread_barrier_wait (&b2);
505 int s;
506 pthread_cleanup_push (cl, NULL);
508 #ifndef WEXITED
509 # define WEXITED 0
510 #endif
511 siginfo_t si;
512 s = waitid (P_PID, pid, &si, WEXITED);
514 pthread_cleanup_pop (0);
516 FAIL_EXIT1 ("waitid returns with %d: %m", s);
520 static void *
521 tf_sigpause (void *arg)
523 xpthread_barrier_wait (&b2);
525 if (arg != NULL)
526 xpthread_barrier_wait (&b2);
528 pthread_cleanup_push (cl, NULL);
530 /* This tests the deprecated sigpause and sigmask functions. The
531 file is compiled with -Wno-errno so that the sigmask deprecation
532 warning is not fatal. */
533 DIAG_PUSH_NEEDS_COMMENT;
534 DIAG_IGNORE_NEEDS_COMMENT (4.9, "-Wdeprecated-declarations");
535 sigpause (sigmask (SIGINT));
536 DIAG_POP_NEEDS_COMMENT;
538 pthread_cleanup_pop (0);
540 FAIL_EXIT1 ("sigpause returned");
544 static void *
545 tf_sigsuspend (void *arg)
547 xpthread_barrier_wait (&b2);
549 if (arg != NULL)
550 xpthread_barrier_wait (&b2);
552 pthread_cleanup_push (cl, NULL);
554 /* Just for fun block all signals. */
555 sigset_t mask;
556 sigfillset (&mask);
557 sigsuspend (&mask);
559 pthread_cleanup_pop (0);
561 FAIL_EXIT1 ("sigsuspend returned");
565 static void *
566 tf_sigwait (void *arg)
568 xpthread_barrier_wait (&b2);
570 if (arg != NULL)
571 xpthread_barrier_wait (&b2);
573 /* Block SIGUSR1. */
574 sigset_t mask;
575 sigemptyset (&mask);
576 sigaddset (&mask, SIGUSR1);
577 TEST_VERIFY_EXIT (pthread_sigmask (SIG_BLOCK, &mask, NULL) == 0);
579 int sig;
580 pthread_cleanup_push (cl, NULL);
582 /* Wait for SIGUSR1. */
583 sigwait (&mask, &sig);
585 pthread_cleanup_pop (0);
587 FAIL_EXIT1 ("sigwait returned with signal %d", sig);
591 static void *
592 tf_sigwaitinfo (void *arg)
594 xpthread_barrier_wait (&b2);
596 if (arg != NULL)
597 xpthread_barrier_wait (&b2);
599 /* Block SIGUSR1. */
600 sigset_t mask;
601 sigemptyset (&mask);
602 sigaddset (&mask, SIGUSR1);
603 TEST_VERIFY_EXIT (pthread_sigmask (SIG_BLOCK, &mask, NULL) == 0);
605 siginfo_t info;
606 pthread_cleanup_push (cl, NULL);
608 /* Wait for SIGUSR1. */
609 int ret;
610 ret = sigwaitinfo (&mask, &info);
611 if (ret == -1 && errno == ENOSYS)
613 int sig;
615 printf ("sigwaitinfo not supported\n");
616 sigwait (&mask, &sig);
619 pthread_cleanup_pop (0);
621 FAIL_EXIT1 ("sigwaitinfo returned with signal %d", info.si_signo);
625 static void *
626 tf_sigtimedwait (void *arg)
628 xpthread_barrier_wait (&b2);
630 if (arg != NULL)
631 xpthread_barrier_wait (&b2);
633 /* Block SIGUSR1. */
634 sigset_t mask;
635 sigemptyset (&mask);
636 sigaddset (&mask, SIGUSR1);
637 TEST_VERIFY_EXIT (pthread_sigmask (SIG_BLOCK, &mask, NULL) == 0);
639 /* Wait for SIGUSR1. */
640 siginfo_t info;
641 struct timespec ts = { .tv_sec = 60, .tv_nsec = 0 };
642 pthread_cleanup_push (cl, NULL);
644 int ret;
645 ret = sigtimedwait (&mask, &info, &ts);
646 if (ret == -1 && errno == ENOSYS)
648 int sig;
649 printf ("sigtimedwait not supported\n");
651 sigwait (&mask, &sig);
654 pthread_cleanup_pop (0);
656 FAIL_EXIT1 ("sigtimedwait returned with signal %d", info.si_signo);
660 static void *
661 tf_pause (void *arg)
663 xpthread_barrier_wait (&b2);
665 if (arg != NULL)
666 xpthread_barrier_wait (&b2);
668 pthread_cleanup_push (cl, NULL);
670 pause ();
672 pthread_cleanup_pop (0);
674 FAIL_EXIT1 ("pause returned");
678 static void *
679 tf_accept (void *arg)
681 struct sockaddr_un sun;
682 /* To test a non-blocking accept call we make the call file by using
683 a datagrame socket. */
684 int pf = arg == NULL ? SOCK_STREAM : SOCK_DGRAM;
686 tempfd = socket (AF_UNIX, pf, 0);
687 if (tempfd == -1)
688 FAIL_EXIT1 ("socket (AF_UNIX, %s, 0): %m", arg == NULL ? "SOCK_STREAM"
689 : "SOCK_DGRAM");
691 int tries = 0;
694 TEST_VERIFY_EXIT (tries++ < 10);
696 strcpy (sun.sun_path, "/tmp/tst-cancel4-socket-1-XXXXXX");
697 TEST_VERIFY_EXIT (mktemp (sun.sun_path) != NULL);
699 sun.sun_family = AF_UNIX;
701 while (bind (tempfd, (struct sockaddr *) &sun,
702 offsetof (struct sockaddr_un, sun_path)
703 + strlen (sun.sun_path) + 1) != 0);
705 unlink (sun.sun_path);
707 listen (tempfd, 5);
709 socklen_t len = sizeof (sun);
711 xpthread_barrier_wait (&b2);
713 if (arg != NULL)
714 xpthread_barrier_wait (&b2);
716 pthread_cleanup_push (cl, NULL);
718 accept (tempfd, (struct sockaddr *) &sun, &len);
720 pthread_cleanup_pop (0);
722 FAIL_EXIT1 ("accept returned");
726 static void *
727 tf_send (void *arg)
729 struct sockaddr_un sun;
731 tempfd = socket (AF_UNIX, SOCK_STREAM, 0);
732 if (tempfd == -1)
733 FAIL_EXIT1 ("socket (AF_UNIX, SOCK_STREAM, 0): %m");
735 int tries = 0;
738 TEST_VERIFY_EXIT (tries++ < 10);
740 strcpy (sun.sun_path, "/tmp/tst-cancel4-socket-2-XXXXXX");
741 TEST_VERIFY_EXIT (mktemp (sun.sun_path) != NULL);
743 sun.sun_family = AF_UNIX;
745 while (bind (tempfd, (struct sockaddr *) &sun,
746 offsetof (struct sockaddr_un, sun_path)
747 + strlen (sun.sun_path) + 1) != 0);
749 listen (tempfd, 5);
751 tempfd2 = socket (AF_UNIX, SOCK_STREAM, 0);
752 if (tempfd2 == -1)
753 FAIL_EXIT1 ("socket (AF_UNIX, SOCK_STREAM, 0): %m");
755 if (connect (tempfd2, (struct sockaddr *) &sun, sizeof (sun)) != 0)
756 FAIL_EXIT1 ("connect: %m");
758 unlink (sun.sun_path);
760 set_socket_buffer (tempfd2);
762 xpthread_barrier_wait (&b2);
764 if (arg != NULL)
765 xpthread_barrier_wait (&b2);
767 pthread_cleanup_push (cl, NULL);
769 char mem[WRITE_BUFFER_SIZE];
771 size_t s = send (tempfd2, mem, arg == NULL ? sizeof (mem) : 1, 0);
772 /* The send can return a value higher than 0 (meaning partial send)
773 due to the SIGCANCEL, but the thread may still be pending
774 cancellation. */
775 pthread_testcancel ();
776 printf("send returned %zd\n", s);
778 pthread_cleanup_pop (0);
780 FAIL_EXIT1 ("send returned");
784 static void *
785 tf_recv (void *arg)
787 struct sockaddr_un sun;
789 tempfd = socket (AF_UNIX, SOCK_STREAM, 0);
790 if (tempfd == -1)
791 FAIL_EXIT1 ("socket (AF_UNIX, SOCK_STREAM, 0): %m");
793 int tries = 0;
796 TEST_VERIFY_EXIT (tries++ < 10);
798 strcpy (sun.sun_path, "/tmp/tst-cancel4-socket-3-XXXXXX");
799 TEST_VERIFY_EXIT (mktemp (sun.sun_path) != NULL);
801 sun.sun_family = AF_UNIX;
803 while (bind (tempfd, (struct sockaddr *) &sun,
804 offsetof (struct sockaddr_un, sun_path)
805 + strlen (sun.sun_path) + 1) != 0);
807 listen (tempfd, 5);
809 tempfd2 = socket (AF_UNIX, SOCK_STREAM, 0);
810 if (tempfd2 == -1)
811 FAIL_EXIT1 ("socket (AF_UNIX, SOCK_STREAM, 0): %m");
813 if (connect (tempfd2, (struct sockaddr *) &sun, sizeof (sun)) != 0)
814 FAIL_EXIT1 ("connect: %m");
816 unlink (sun.sun_path);
818 xpthread_barrier_wait (&b2);
820 if (arg != NULL)
821 xpthread_barrier_wait (&b2);
823 pthread_cleanup_push (cl, NULL);
825 char mem[70];
827 recv (tempfd2, mem, arg == NULL ? sizeof (mem) : 0, 0);
829 pthread_cleanup_pop (0);
831 FAIL_EXIT1 ("recv returned");
835 static void *
836 tf_recvfrom (void *arg)
838 struct sockaddr_un sun;
840 tempfd = socket (AF_UNIX, SOCK_DGRAM, 0);
841 if (tempfd == -1)
842 FAIL_EXIT1 ("socket (AF_UNIX, SOCK_DGRAM, 0): %m");
844 int tries = 0;
847 TEST_VERIFY_EXIT (tries++ < 10);
849 strcpy (sun.sun_path, "/tmp/tst-cancel4-socket-4-XXXXXX");
850 TEST_VERIFY_EXIT (mktemp (sun.sun_path) != NULL);
852 sun.sun_family = AF_UNIX;
854 while (bind (tempfd, (struct sockaddr *) &sun,
855 offsetof (struct sockaddr_un, sun_path)
856 + strlen (sun.sun_path) + 1) != 0);
858 tempfname = strdup (sun.sun_path);
860 tempfd2 = socket (AF_UNIX, SOCK_DGRAM, 0);
861 if (tempfd2 == -1)
862 FAIL_EXIT1 ("socket (AF_UNIX, SOCK_DGRAM, 0): %m");
864 xpthread_barrier_wait (&b2);
866 if (arg != NULL)
867 xpthread_barrier_wait (&b2);
869 pthread_cleanup_push (cl, NULL);
871 char mem[70];
872 socklen_t len = sizeof (sun);
874 recvfrom (tempfd2, mem, arg == NULL ? sizeof (mem) : 0, 0,
875 (struct sockaddr *) &sun, &len);
877 pthread_cleanup_pop (0);
879 FAIL_EXIT1 ("recvfrom returned");
883 static void *
884 tf_recvmsg (void *arg)
886 struct sockaddr_un sun;
888 tempfd = socket (AF_UNIX, SOCK_DGRAM, 0);
889 if (tempfd == -1)
890 FAIL_EXIT1 ("socket (AF_UNIX, SOCK_DGRAM, 0): %m");
892 int tries = 0;
895 TEST_VERIFY_EXIT (tries++ < 10);
897 strcpy (sun.sun_path, "/tmp/tst-cancel4-socket-5-XXXXXX");
898 TEST_VERIFY_EXIT (mktemp (sun.sun_path) != NULL);
900 sun.sun_family = AF_UNIX;
902 while (bind (tempfd, (struct sockaddr *) &sun,
903 offsetof (struct sockaddr_un, sun_path)
904 + strlen (sun.sun_path) + 1) != 0);
906 tempfname = strdup (sun.sun_path);
908 tempfd2 = socket (AF_UNIX, SOCK_DGRAM, 0);
909 if (tempfd2 == -1)
910 FAIL_EXIT1 ("socket (AF_UNIX, SOCK_DGRAM, 0): %m");
912 xpthread_barrier_wait (&b2);
914 if (arg != NULL)
915 xpthread_barrier_wait (&b2);
917 pthread_cleanup_push (cl, NULL);
919 char mem[70];
920 struct iovec iov[1];
921 iov[0].iov_base = mem;
922 iov[0].iov_len = arg == NULL ? sizeof (mem) : 0;
924 struct msghdr m;
925 m.msg_name = &sun;
926 m.msg_namelen = sizeof (sun);
927 m.msg_iov = iov;
928 m.msg_iovlen = 1;
929 m.msg_control = NULL;
930 m.msg_controllen = 0;
932 recvmsg (tempfd2, &m, 0);
934 pthread_cleanup_pop (0);
936 FAIL_EXIT1 ("recvmsg returned");
939 static void *
940 tf_open (void *arg)
942 if (arg == NULL)
944 fifofd = mkfifo (fifoname, S_IWUSR | S_IRUSR);
945 if (fifofd == -1)
946 FAIL_EXIT1 ("mkfifo: %m");
948 else
950 xpthread_barrier_wait (&b2);
953 xpthread_barrier_wait (&b2);
955 pthread_cleanup_push (cl_fifo, NULL);
957 open (arg ? "Makefile" : fifoname, O_RDONLY);
959 pthread_cleanup_pop (0);
961 FAIL_EXIT1 ("open returned");
965 static void *
966 tf_close (void *arg)
968 if (arg == NULL)
969 // XXX If somebody can provide a portable test case in which close()
970 // blocks we can enable this test to run in both rounds.
971 abort ();
973 char fname[] = "/tmp/tst-cancel-fd-XXXXXX";
974 tempfd = mkstemp (fname);
975 if (tempfd == -1)
976 FAIL_EXIT1 ("mkstemp failed: %m");
977 unlink (fname);
979 xpthread_barrier_wait (&b2);
981 xpthread_barrier_wait (&b2);
983 pthread_cleanup_push (cl, NULL);
985 close (tempfd);
987 pthread_cleanup_pop (0);
989 FAIL_EXIT1 ("close returned");
993 static void *
994 tf_pread (void *arg)
996 if (arg == NULL)
997 // XXX If somebody can provide a portable test case in which pread()
998 // blocks we can enable this test to run in both rounds.
999 abort ();
1001 tempfd = open ("Makefile", O_RDONLY);
1002 if (tempfd == -1)
1003 FAIL_EXIT1 ("open (\"Makefile\", O_RDONLY): %m");
1005 xpthread_barrier_wait (&b2);
1007 xpthread_barrier_wait (&b2);
1009 pthread_cleanup_push (cl, NULL);
1011 char mem[10];
1012 if (pread (tempfd, mem, sizeof (mem), 0) < 0)
1013 FAIL_EXIT1 ("pread failed: %m");
1015 pthread_cleanup_pop (0);
1017 FAIL_EXIT1 ("pread returned");
1021 static void *
1022 tf_pwrite (void *arg)
1024 if (arg == NULL)
1025 // XXX If somebody can provide a portable test case in which pwrite()
1026 // blocks we can enable this test to run in both rounds.
1027 abort ();
1029 char fname[] = "/tmp/tst-cancel4-fd-XXXXXX";
1030 tempfd = mkstemp (fname);
1031 if (tempfd == -1)
1032 FAIL_EXIT1 ("mkstemp failed: %m");
1033 unlink (fname);
1035 xpthread_barrier_wait (&b2);
1037 xpthread_barrier_wait (&b2);
1039 pthread_cleanup_push (cl, NULL);
1041 char mem[10];
1042 if (pwrite (tempfd, mem, sizeof (mem), 0) <0)
1043 FAIL_EXIT1 ("pwrite failed: %m");
1045 pthread_cleanup_pop (0);
1047 FAIL_EXIT1 ("pwrite returned");
1050 static void *
1051 tf_preadv (void *arg)
1053 int fd;
1055 if (arg == NULL)
1056 /* XXX If somebody can provide a portable test case in which preadv
1057 blocks we can enable this test to run in both rounds. */
1058 abort ();
1060 char fname[] = "/tmp/tst-cancel4-fd-XXXXXX";
1061 tempfd = fd = mkstemp (fname);
1062 if (fd == -1)
1063 FAIL_EXIT1 ("mkstemp failed: %m");
1064 unlink (fname);
1066 xpthread_barrier_wait (&b2);
1068 xpthread_barrier_wait (&b2);
1070 ssize_t s;
1071 pthread_cleanup_push (cl, NULL);
1073 char buf[100];
1074 struct iovec iov[1] = { [0] = { .iov_base = buf, .iov_len = sizeof (buf) } };
1075 s = preadv (fd, iov, 1, 0);
1077 pthread_cleanup_pop (0);
1079 FAIL_EXIT1 ("preadv returns with %zd", s);
1082 static void *
1083 tf_pwritev (void *arg)
1085 int fd;
1087 if (arg == NULL)
1088 /* XXX If somebody can provide a portable test case in which pwritev
1089 blocks we can enable this test to run in both rounds. */
1090 abort ();
1092 char fname[] = "/tmp/tst-cancel4-fd-XXXXXX";
1093 tempfd = fd = mkstemp (fname);
1094 if (fd == -1)
1095 FAIL_EXIT1 ("mkstemp failed: %m");
1096 unlink (fname);
1098 xpthread_barrier_wait (&b2);
1100 xpthread_barrier_wait (&b2);
1102 ssize_t s;
1103 pthread_cleanup_push (cl, NULL);
1105 char buf[WRITE_BUFFER_SIZE];
1106 memset (buf, '\0', sizeof (buf));
1107 struct iovec iov[1] = { [0] = { .iov_base = buf, .iov_len = sizeof (buf) } };
1108 s = pwritev (fd, iov, 1, 0);
1110 pthread_cleanup_pop (0);
1112 FAIL_EXIT1 ("pwritev returns with %zd", s);
1115 static void *
1116 tf_pwritev2 (void *arg)
1118 int fd;
1120 if (arg == NULL)
1121 /* XXX If somebody can provide a portable test case in which pwritev2
1122 blocks we can enable this test to run in both rounds. */
1123 abort ();
1125 errno = 0;
1127 char fname[] = "/tmp/tst-cancel4-fd-XXXXXX";
1128 tempfd = fd = mkstemp (fname);
1129 if (fd == -1)
1130 FAIL_EXIT1 ("mkstemp: %m");
1131 unlink (fname);
1133 xpthread_barrier_wait (&b2);
1135 xpthread_barrier_wait (&b2);
1137 ssize_t s;
1138 pthread_cleanup_push (cl, NULL);
1140 char buf[WRITE_BUFFER_SIZE];
1141 memset (buf, '\0', sizeof (buf));
1142 struct iovec iov[1] = { [0] = { .iov_base = buf, .iov_len = sizeof (buf) } };
1143 s = pwritev2 (fd, iov, 1, 0, 0);
1145 pthread_cleanup_pop (0);
1147 FAIL_EXIT1 ("pwritev2 returns with %zd", s);
1150 static void *
1151 tf_preadv2 (void *arg)
1153 int fd;
1155 if (arg == NULL)
1156 /* XXX If somebody can provide a portable test case in which preadv2
1157 blocks we can enable this test to run in both rounds. */
1158 abort ();
1160 errno = 0;
1162 char fname[] = "/tmp/tst-cancel4-fd-XXXXXX";
1163 tempfd = fd = mkstemp (fname);
1164 if (fd == -1)
1165 FAIL_EXIT1 ("mkstemp failed: %m");
1166 unlink (fname);
1168 xpthread_barrier_wait (&b2);
1170 xpthread_barrier_wait (&b2);
1172 ssize_t s;
1173 pthread_cleanup_push (cl, NULL);
1175 char buf[100];
1176 struct iovec iov[1] = { [0] = { .iov_base = buf, .iov_len = sizeof (buf) } };
1177 s = preadv2 (fd, iov, 1, 0, 0);
1179 pthread_cleanup_pop (0);
1181 FAIL_EXIT1 ("preadv2 returns with %zd", s);
1184 static void *
1185 tf_fsync (void *arg)
1187 if (arg == NULL)
1188 // XXX If somebody can provide a portable test case in which fsync()
1189 // blocks we can enable this test to run in both rounds.
1190 abort ();
1192 tempfd = open ("Makefile", O_RDONLY);
1193 if (tempfd == -1)
1194 FAIL_EXIT1 ("open (\"Makefile\", O_RDONLY): %m");
1196 xpthread_barrier_wait (&b2);
1198 xpthread_barrier_wait (&b2);
1200 pthread_cleanup_push (cl, NULL);
1202 fsync (tempfd);
1204 pthread_cleanup_pop (0);
1206 FAIL_EXIT1 ("fsync returned");
1210 static void *
1211 tf_fdatasync (void *arg)
1213 if (arg == NULL)
1214 // XXX If somebody can provide a portable test case in which fdatasync()
1215 // blocks we can enable this test to run in both rounds.
1216 abort ();
1218 tempfd = open ("Makefile", O_RDONLY);
1219 if (tempfd == -1)
1220 FAIL_EXIT1 ("open (\"Makefile\", O_RDONLY): %m");
1222 xpthread_barrier_wait (&b2);
1224 xpthread_barrier_wait (&b2);
1226 pthread_cleanup_push (cl, NULL);
1228 fdatasync (tempfd);
1230 pthread_cleanup_pop (0);
1232 FAIL_EXIT1 ("fdatasync returned");
1236 static void *
1237 tf_msync (void *arg)
1239 if (arg == NULL)
1240 // XXX If somebody can provide a portable test case in which msync()
1241 // blocks we can enable this test to run in both rounds.
1242 abort ();
1244 tempfd = open ("Makefile", O_RDONLY);
1245 if (tempfd == -1)
1246 FAIL_EXIT1 ("open (\"Makefile\", O_RDONLY): %m");
1248 void *p = xmmap (NULL, 10, PROT_READ, MAP_SHARED, tempfd);
1250 xpthread_barrier_wait (&b2);
1252 xpthread_barrier_wait (&b2);
1254 pthread_cleanup_push (cl, NULL);
1256 msync (p, 10, 0);
1258 pthread_cleanup_pop (0);
1260 FAIL_EXIT1 ("msync returned");
1264 static void *
1265 tf_sendto (void *arg)
1267 struct sockaddr_un sun;
1269 tempfd = socket (AF_UNIX, SOCK_STREAM, 0);
1270 if (tempfd == -1)
1271 FAIL_EXIT1 ("socket (AF_UNIX, SOCK_STREAM, 0): %m");
1273 int tries = 0;
1276 TEST_VERIFY_EXIT (tries++ < 10);
1278 strcpy (sun.sun_path, "/tmp/tst-cancel4-socket-6-XXXXXX");
1279 TEST_VERIFY_EXIT (mktemp (sun.sun_path) != NULL);
1281 sun.sun_family = AF_UNIX;
1283 while (bind (tempfd, (struct sockaddr *) &sun,
1284 offsetof (struct sockaddr_un, sun_path)
1285 + strlen (sun.sun_path) + 1) != 0);
1287 listen (tempfd, 5);
1289 tempfd2 = socket (AF_UNIX, SOCK_STREAM, 0);
1290 if (tempfd2 == -1)
1291 FAIL_EXIT1 ("socket (AF_UNIX, SOCK_STREAM, 0): %m");
1293 if (connect (tempfd2, (struct sockaddr *) &sun, sizeof (sun)) != 0)
1294 FAIL_EXIT1 ("connect: %m");
1296 unlink (sun.sun_path);
1298 set_socket_buffer (tempfd2);
1300 xpthread_barrier_wait (&b2);
1302 if (arg != NULL)
1303 xpthread_barrier_wait (&b2);
1305 pthread_cleanup_push (cl, NULL);
1307 char mem[WRITE_BUFFER_SIZE];
1309 sendto (tempfd2, mem, arg == NULL ? sizeof (mem) : 1, 0, NULL, 0);
1311 pthread_cleanup_pop (0);
1313 FAIL_EXIT1 ("sendto returned");
1317 static void *
1318 tf_sendmsg (void *arg)
1320 if (arg == NULL)
1321 // XXX If somebody can provide a portable test case in which sendmsg()
1322 // blocks we can enable this test to run in both rounds.
1323 abort ();
1325 struct sockaddr_un sun;
1327 tempfd = socket (AF_UNIX, SOCK_DGRAM, 0);
1328 if (tempfd == -1)
1329 FAIL_EXIT1 ("socket (AF_UNIX, SOCK_DGRAM, 0): %m");
1331 int tries = 0;
1334 TEST_VERIFY_EXIT (tries++ < 10);
1336 strcpy (sun.sun_path, "/tmp/tst-cancel4-socket-7-XXXXXX");
1337 TEST_VERIFY_EXIT (mktemp (sun.sun_path) != NULL);
1339 sun.sun_family = AF_UNIX;
1341 while (bind (tempfd, (struct sockaddr *) &sun,
1342 offsetof (struct sockaddr_un, sun_path)
1343 + strlen (sun.sun_path) + 1) != 0);
1344 tempfname = strdup (sun.sun_path);
1346 tempfd2 = socket (AF_UNIX, SOCK_DGRAM, 0);
1347 if (tempfd2 == -1)
1348 FAIL_EXIT1 ("socket (AF_UNIX, SOCK_DGRAM, 0): %m");
1350 xpthread_barrier_wait (&b2);
1352 xpthread_barrier_wait (&b2);
1354 pthread_cleanup_push (cl, NULL);
1356 char mem[1];
1357 struct iovec iov[1];
1358 iov[0].iov_base = mem;
1359 iov[0].iov_len = 1;
1361 struct msghdr m;
1362 m.msg_name = &sun;
1363 m.msg_namelen = (offsetof (struct sockaddr_un, sun_path)
1364 + strlen (sun.sun_path) + 1);
1365 m.msg_iov = iov;
1366 m.msg_iovlen = 1;
1367 m.msg_control = NULL;
1368 m.msg_controllen = 0;
1370 sendmsg (tempfd2, &m, 0);
1372 pthread_cleanup_pop (0);
1374 FAIL_EXIT1 ("sendmsg returned");
1378 static void *
1379 tf_creat (void *arg)
1381 if (arg == NULL)
1382 // XXX If somebody can provide a portable test case in which sendmsg()
1383 // blocks we can enable this test to run in both rounds.
1384 abort ();
1386 xpthread_barrier_wait (&b2);
1388 xpthread_barrier_wait (&b2);
1390 pthread_cleanup_push (cl, NULL);
1392 creat ("tmp/tst-cancel-4-should-not-exist", 0666);
1394 pthread_cleanup_pop (0);
1396 FAIL_EXIT1 ("creat returned");
1400 static void *
1401 tf_connect (void *arg)
1403 if (arg == NULL)
1404 // XXX If somebody can provide a portable test case in which connect()
1405 // blocks we can enable this test to run in both rounds.
1406 abort ();
1408 struct sockaddr_un sun;
1410 tempfd = socket (AF_UNIX, SOCK_STREAM, 0);
1411 if (tempfd == -1)
1412 FAIL_EXIT1 ("socket (AF_UNIX, SOCK_STREAM, 0): %m");
1414 int tries = 0;
1417 TEST_VERIFY_EXIT (tries++ < 10);
1419 strcpy (sun.sun_path, "/tmp/tst-cancel4-socket-2-XXXXXX");
1420 TEST_VERIFY_EXIT (mktemp (sun.sun_path) != NULL);
1422 sun.sun_family = AF_UNIX;
1424 while (bind (tempfd, (struct sockaddr *) &sun,
1425 offsetof (struct sockaddr_un, sun_path)
1426 + strlen (sun.sun_path) + 1) != 0);
1427 tempfname = strdup (sun.sun_path);
1429 listen (tempfd, 5);
1431 tempfd2 = socket (AF_UNIX, SOCK_STREAM, 0);
1432 if (tempfd2 == -1)
1433 FAIL_EXIT1 ("socket (AF_UNIX, SOCK_STREAM, 0): %m");
1435 xpthread_barrier_wait (&b2);
1437 if (arg != NULL)
1438 xpthread_barrier_wait (&b2);
1440 pthread_cleanup_push (cl, NULL);
1442 connect (tempfd2, (struct sockaddr *) &sun, sizeof (sun));
1444 pthread_cleanup_pop (0);
1446 FAIL_EXIT1 ("connect returned");
1450 static void *
1451 tf_tcdrain (void *arg)
1453 if (arg == NULL)
1454 // XXX If somebody can provide a portable test case in which tcdrain()
1455 // blocks we can enable this test to run in both rounds.
1456 abort ();
1458 xpthread_barrier_wait (&b2);
1460 if (arg != NULL)
1461 xpthread_barrier_wait (&b2);
1463 pthread_cleanup_push (cl, NULL);
1465 /* Regardless of stderr being a terminal, the tcdrain call should be
1466 canceled. */
1467 tcdrain (STDERR_FILENO);
1469 pthread_cleanup_pop (0);
1471 FAIL_EXIT1 ("tcdrain returned");
1475 static void *
1476 tf_msgrcv (void *arg)
1478 tempmsg = msgget (IPC_PRIVATE, 0666 | IPC_CREAT);
1479 if (tempmsg == -1)
1481 if (errno == ENOSYS)
1483 printf ("msgget not supported\n");
1484 tf_usleep (arg);
1485 pthread_exit (NULL);
1487 else
1488 FAIL_EXIT1 ("msgget (IPC_PRIVATE, 0666 | IPC_CREAT): %m");
1491 xpthread_barrier_wait (&b2);
1493 if (arg != NULL)
1494 xpthread_barrier_wait (&b2);
1496 ssize_t s;
1498 pthread_cleanup_push (cl, NULL);
1500 struct
1502 long int type;
1503 char mem[10];
1504 } m;
1505 int randnr;
1506 /* We need a positive random number. */
1508 randnr = random () % 64000;
1509 while (randnr <= 0);
1512 errno = 0;
1513 s = msgrcv (tempmsg, (struct msgbuf *) &m, 10, randnr, 0);
1515 while (errno == EIDRM || errno == EINTR);
1517 pthread_cleanup_pop (0);
1519 msgctl (tempmsg, IPC_RMID, NULL);
1521 FAIL_EXIT1 ("msgrcv returned %zd", s);
1525 static void *
1526 tf_msgsnd (void *arg)
1528 if (arg == NULL)
1529 // XXX If somebody can provide a portable test case in which msgsnd()
1530 // blocks we can enable this test to run in both rounds.
1531 abort ();
1533 tempmsg = msgget (IPC_PRIVATE, 0666 | IPC_CREAT);
1534 if (tempmsg == -1)
1536 if (errno == ENOSYS)
1538 printf ("msgget not supported\n");
1539 tf_usleep (arg);
1540 pthread_exit (NULL);
1542 else
1543 FAIL_EXIT1 ("msgget (IPC_PRIVATE, 0666 | IPC_CREAT): %m");
1546 xpthread_barrier_wait (&b2);
1548 xpthread_barrier_wait (&b2);
1550 pthread_cleanup_push (cl, NULL);
1552 struct
1554 long int type;
1555 char mem[1];
1556 } m;
1557 /* We need a positive random number. */
1559 m.type = random () % 64000;
1560 while (m.type <= 0);
1561 msgsnd (tempmsg, (struct msgbuf *) &m, sizeof (m.mem), 0);
1563 pthread_cleanup_pop (0);
1565 msgctl (tempmsg, IPC_RMID, NULL);
1567 FAIL_EXIT1 ("msgsnd returned");
1571 struct cancel_tests tests[] =
1573 ADD_TEST (read, 2, 0),
1574 ADD_TEST (readv, 2, 0),
1575 ADD_TEST (select, 2, 0),
1576 ADD_TEST (pselect, 2, 0),
1577 ADD_TEST (poll, 2, 0),
1578 ADD_TEST (ppoll, 2, 0),
1579 ADD_TEST (write, 2, 0),
1580 ADD_TEST (writev, 2, 0),
1581 ADD_TEST (sleep, 2, 0),
1582 ADD_TEST (usleep, 2, 0),
1583 ADD_TEST (nanosleep, 2, 0),
1584 ADD_TEST (wait, 2, 0),
1585 ADD_TEST (waitid, 2, 0),
1586 ADD_TEST (waitpid, 2, 0),
1587 ADD_TEST (sigpause, 2, 0),
1588 ADD_TEST (sigsuspend, 2, 0),
1589 ADD_TEST (sigwait, 2, 0),
1590 ADD_TEST (sigwaitinfo, 2, 0),
1591 ADD_TEST (sigtimedwait, 2, 0),
1592 ADD_TEST (pause, 2, 0),
1593 ADD_TEST (accept, 2, 0),
1594 ADD_TEST (send, 2, 0),
1595 ADD_TEST (recv, 2, 0),
1596 ADD_TEST (recvfrom, 2, 0),
1597 ADD_TEST (recvmsg, 2, 0),
1598 ADD_TEST (preadv, 2, 1),
1599 ADD_TEST (preadv2, 2, 1),
1600 ADD_TEST (pwritev, 2, 1),
1601 ADD_TEST (pwritev2, 2, 1),
1602 ADD_TEST (open, 2, 1),
1603 ADD_TEST (close, 2, 1),
1604 ADD_TEST (pread, 2, 1),
1605 ADD_TEST (pwrite, 2, 1),
1606 ADD_TEST (fsync, 2, 1),
1607 ADD_TEST (fdatasync, 2, 1),
1608 ADD_TEST (msync, 2, 1),
1609 ADD_TEST (sendto, 2, 1),
1610 ADD_TEST (sendmsg, 2, 1),
1611 ADD_TEST (creat, 2, 1),
1612 ADD_TEST (connect, 2, 1),
1613 ADD_TEST (tcdrain, 2, 1),
1614 ADD_TEST (msgrcv, 2, 0),
1615 ADD_TEST (msgsnd, 2, 1),
1617 #define ntest_tf (sizeof (tests) / sizeof (tests[0]))
1619 #include "tst-cancel4-common.c"