1f08c3bdfSopenharmony_ci/*
2f08c3bdfSopenharmony_ci * Copyright (c) 2014 Fujitsu Ltd.
3f08c3bdfSopenharmony_ci * Author: Xiaoguang Wang <wangxg.fnst@cn.fujitsu.com>
4f08c3bdfSopenharmony_ci *
5f08c3bdfSopenharmony_ci * This program is free software; you can redistribute it and/or modify it
6f08c3bdfSopenharmony_ci * under the terms of version 2 of the GNU General Public License as
7f08c3bdfSopenharmony_ci * published by the Free Software Foundation.
8f08c3bdfSopenharmony_ci *
9f08c3bdfSopenharmony_ci * This program is distributed in the hope that it would be useful, but
10f08c3bdfSopenharmony_ci * WITHOUT ANY WARRANTY; without even the implied warranty of
11f08c3bdfSopenharmony_ci * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
12f08c3bdfSopenharmony_ci *
13f08c3bdfSopenharmony_ci * You should have received a copy of the GNU General Public License along
14f08c3bdfSopenharmony_ci * with this program; if not, write the Free Software Foundation, Inc.,
15f08c3bdfSopenharmony_ci * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
16f08c3bdfSopenharmony_ci */
17f08c3bdfSopenharmony_ci
18f08c3bdfSopenharmony_ci/*
19f08c3bdfSopenharmony_ci * Description:
20f08c3bdfSopenharmony_ci * Verify that:
21f08c3bdfSopenharmony_ci *     Basic test for fcntl(2) using F_GETOWN, F_SETOWN, F_GETOWN_EX,
22f08c3bdfSopenharmony_ci *     F_SETOWN_EX, F_GETSIG, F_SETSIG argument.
23f08c3bdfSopenharmony_ci */
24f08c3bdfSopenharmony_ci
25f08c3bdfSopenharmony_ci#include <stdio.h>
26f08c3bdfSopenharmony_ci#include <errno.h>
27f08c3bdfSopenharmony_ci#include <unistd.h>
28f08c3bdfSopenharmony_ci#include <string.h>
29f08c3bdfSopenharmony_ci#include <signal.h>
30f08c3bdfSopenharmony_ci#include <sys/types.h>
31f08c3bdfSopenharmony_ci#include <sys/wait.h>
32f08c3bdfSopenharmony_ci#include <pwd.h>
33f08c3bdfSopenharmony_ci#include <sched.h>
34f08c3bdfSopenharmony_ci
35f08c3bdfSopenharmony_ci#include "test.h"
36f08c3bdfSopenharmony_ci#include "config.h"
37f08c3bdfSopenharmony_ci#include "lapi/syscalls.h"
38f08c3bdfSopenharmony_ci#include "safe_macros.h"
39f08c3bdfSopenharmony_ci#include "lapi/fcntl.h"
40f08c3bdfSopenharmony_ci
41f08c3bdfSopenharmony_cistatic void setup(void);
42f08c3bdfSopenharmony_cistatic void cleanup(void);
43f08c3bdfSopenharmony_ci
44f08c3bdfSopenharmony_cistatic void setown_pid_test(void);
45f08c3bdfSopenharmony_cistatic void setown_pgrp_test(void);
46f08c3bdfSopenharmony_ci
47f08c3bdfSopenharmony_ci#if defined(HAVE_STRUCT_F_OWNER_EX)
48f08c3bdfSopenharmony_cistatic void setownex_tid_test(void);
49f08c3bdfSopenharmony_cistatic void setownex_pid_test(void);
50f08c3bdfSopenharmony_cistatic void setownex_pgrp_test(void);
51f08c3bdfSopenharmony_ci
52f08c3bdfSopenharmony_cistatic struct f_owner_ex orig_own_ex;
53f08c3bdfSopenharmony_ci#endif
54f08c3bdfSopenharmony_ci
55f08c3bdfSopenharmony_cistatic void signal_parent(void);
56f08c3bdfSopenharmony_cistatic void check_io_signal(char *des);
57f08c3bdfSopenharmony_cistatic void test_set_and_get_sig(int sig, char *des);
58f08c3bdfSopenharmony_ci
59f08c3bdfSopenharmony_cistatic pid_t pid;
60f08c3bdfSopenharmony_cistatic pid_t orig_pid;
61f08c3bdfSopenharmony_cistatic pid_t pgrp_pid;
62f08c3bdfSopenharmony_ci
63f08c3bdfSopenharmony_cistatic struct timespec timeout;
64f08c3bdfSopenharmony_cistatic sigset_t newset, oldset;
65f08c3bdfSopenharmony_ci
66f08c3bdfSopenharmony_cistatic int test_fd;
67f08c3bdfSopenharmony_cistatic int pipe_fds[2];
68f08c3bdfSopenharmony_ci
69f08c3bdfSopenharmony_cistatic void (*testfunc[])(void) = {
70f08c3bdfSopenharmony_ci	setown_pid_test, setown_pgrp_test,
71f08c3bdfSopenharmony_ci#if defined(HAVE_STRUCT_F_OWNER_EX)
72f08c3bdfSopenharmony_ci	setownex_tid_test, setownex_pid_test, setownex_pgrp_test
73f08c3bdfSopenharmony_ci#endif
74f08c3bdfSopenharmony_ci};
75f08c3bdfSopenharmony_ci
76f08c3bdfSopenharmony_cichar *TCID = "fcntl31";
77f08c3bdfSopenharmony_ciint TST_TOTAL = ARRAY_SIZE(testfunc);
78f08c3bdfSopenharmony_ci
79f08c3bdfSopenharmony_ci
80f08c3bdfSopenharmony_ciint main(int ac, char **av)
81f08c3bdfSopenharmony_ci{
82f08c3bdfSopenharmony_ci	int lc, i;
83f08c3bdfSopenharmony_ci
84f08c3bdfSopenharmony_ci	tst_parse_opts(ac, av, NULL, NULL);
85f08c3bdfSopenharmony_ci
86f08c3bdfSopenharmony_ci	setup();
87f08c3bdfSopenharmony_ci
88f08c3bdfSopenharmony_ci	for (lc = 0; TEST_LOOPING(lc); lc++) {
89f08c3bdfSopenharmony_ci		tst_count = 0;
90f08c3bdfSopenharmony_ci
91f08c3bdfSopenharmony_ci		for (i = 0; i < TST_TOTAL; i++)
92f08c3bdfSopenharmony_ci			(*testfunc[i])();
93f08c3bdfSopenharmony_ci	}
94f08c3bdfSopenharmony_ci
95f08c3bdfSopenharmony_ci	cleanup();
96f08c3bdfSopenharmony_ci	tst_exit();
97f08c3bdfSopenharmony_ci}
98f08c3bdfSopenharmony_ci
99f08c3bdfSopenharmony_cistatic void setup(void)
100f08c3bdfSopenharmony_ci{
101f08c3bdfSopenharmony_ci	int ret;
102f08c3bdfSopenharmony_ci
103f08c3bdfSopenharmony_ci	tst_sig(FORK, DEF_HANDLER, cleanup);
104f08c3bdfSopenharmony_ci
105f08c3bdfSopenharmony_ci	TEST_PAUSE;
106f08c3bdfSopenharmony_ci
107f08c3bdfSopenharmony_ci	/* we have these tests on pipe */
108f08c3bdfSopenharmony_ci	SAFE_PIPE(cleanup, pipe_fds);
109f08c3bdfSopenharmony_ci	test_fd = pipe_fds[0];
110f08c3bdfSopenharmony_ci	if (fcntl(test_fd, F_SETFL, O_ASYNC) < 0)
111f08c3bdfSopenharmony_ci		tst_brkm(TBROK | TERRNO, cleanup, "fcntl set O_ASYNC failed");
112f08c3bdfSopenharmony_ci
113f08c3bdfSopenharmony_ci	pid = getpid();
114f08c3bdfSopenharmony_ci
115f08c3bdfSopenharmony_ci	/* Changing process group ID is forbidden when PID == SID i.e. we are session leader */
116f08c3bdfSopenharmony_ci	if (pid != getsid(0)) {
117f08c3bdfSopenharmony_ci		ret = setpgrp();
118f08c3bdfSopenharmony_ci		if (ret < 0)
119f08c3bdfSopenharmony_ci			tst_brkm(TBROK | TERRNO, cleanup, "setpgrp() failed");
120f08c3bdfSopenharmony_ci	}
121f08c3bdfSopenharmony_ci	pgrp_pid = getpgid(0);
122f08c3bdfSopenharmony_ci	if (pgrp_pid < 0)
123f08c3bdfSopenharmony_ci		tst_brkm(TBROK | TERRNO, cleanup, "getpgid() failed");
124f08c3bdfSopenharmony_ci
125f08c3bdfSopenharmony_ci#if defined(HAVE_STRUCT_F_OWNER_EX)
126f08c3bdfSopenharmony_ci	/* get original f_owner_ex info */
127f08c3bdfSopenharmony_ci	TEST(fcntl(test_fd, F_GETOWN_EX, &orig_own_ex));
128f08c3bdfSopenharmony_ci	if (TEST_RETURN < 0) {
129f08c3bdfSopenharmony_ci		tst_brkm(TFAIL | TTERRNO, cleanup,
130f08c3bdfSopenharmony_ci			 "fcntl get original f_owner_ex info failed");
131f08c3bdfSopenharmony_ci	}
132f08c3bdfSopenharmony_ci#endif
133f08c3bdfSopenharmony_ci
134f08c3bdfSopenharmony_ci	/* get original pid info */
135f08c3bdfSopenharmony_ci	TEST(fcntl(test_fd, F_GETOWN));
136f08c3bdfSopenharmony_ci	if (TEST_RETURN < 0) {
137f08c3bdfSopenharmony_ci		tst_brkm(TFAIL | TTERRNO, cleanup,
138f08c3bdfSopenharmony_ci			 "fcntl get original pid info failed");
139f08c3bdfSopenharmony_ci	}
140f08c3bdfSopenharmony_ci	orig_pid = TEST_RETURN;
141f08c3bdfSopenharmony_ci
142f08c3bdfSopenharmony_ci	sigemptyset(&newset);
143f08c3bdfSopenharmony_ci	sigaddset(&newset, SIGUSR1);
144f08c3bdfSopenharmony_ci	sigaddset(&newset, SIGIO);
145f08c3bdfSopenharmony_ci
146f08c3bdfSopenharmony_ci	if (sigprocmask(SIG_SETMASK, &newset, &oldset) < 0)
147f08c3bdfSopenharmony_ci		tst_brkm(TBROK | TERRNO, cleanup, "sigprocmask failed");
148f08c3bdfSopenharmony_ci
149f08c3bdfSopenharmony_ci	timeout.tv_sec = 5;
150f08c3bdfSopenharmony_ci	timeout.tv_nsec = 0;
151f08c3bdfSopenharmony_ci}
152f08c3bdfSopenharmony_ci
153f08c3bdfSopenharmony_cistatic void setown_pid_test(void)
154f08c3bdfSopenharmony_ci{
155f08c3bdfSopenharmony_ci	TEST(fcntl(test_fd, F_SETOWN, pid));
156f08c3bdfSopenharmony_ci	if (TEST_RETURN < 0) {
157f08c3bdfSopenharmony_ci		tst_brkm(TFAIL | TTERRNO, cleanup,
158f08c3bdfSopenharmony_ci			 "fcntl(F_SETOWN) set process id failed");
159f08c3bdfSopenharmony_ci	}
160f08c3bdfSopenharmony_ci	test_set_and_get_sig(SIGUSR1, "F_GETOWN, F_SETOWN for process ID");
161f08c3bdfSopenharmony_ci
162f08c3bdfSopenharmony_ci	TEST(fcntl(test_fd, F_SETOWN, orig_pid));
163f08c3bdfSopenharmony_ci	if (TEST_RETURN < 0) {
164f08c3bdfSopenharmony_ci		tst_brkm(TFAIL | TTERRNO, cleanup,
165f08c3bdfSopenharmony_ci			 "fcntl(F_SETOWN) restore orig_pid failed");
166f08c3bdfSopenharmony_ci	}
167f08c3bdfSopenharmony_ci}
168f08c3bdfSopenharmony_ci
169f08c3bdfSopenharmony_cistatic void setown_pgrp_test(void)
170f08c3bdfSopenharmony_ci{
171f08c3bdfSopenharmony_ci	TEST(fcntl(test_fd, F_SETOWN, -pgrp_pid));
172f08c3bdfSopenharmony_ci	if (TEST_RETURN < 0) {
173f08c3bdfSopenharmony_ci		tst_brkm(TFAIL | TTERRNO, cleanup,
174f08c3bdfSopenharmony_ci			 "fcntl(F_SETOWN) set process group id failed");
175f08c3bdfSopenharmony_ci	}
176f08c3bdfSopenharmony_ci	test_set_and_get_sig(SIGUSR1,
177f08c3bdfSopenharmony_ci			     "F_GETOWN, F_SETOWN for process group ID");
178f08c3bdfSopenharmony_ci
179f08c3bdfSopenharmony_ci	TEST(fcntl(test_fd, F_SETOWN, orig_pid));
180f08c3bdfSopenharmony_ci	if (TEST_RETURN < 0) {
181f08c3bdfSopenharmony_ci		tst_brkm(TFAIL | TTERRNO, cleanup,
182f08c3bdfSopenharmony_ci			 "fcntl(F_SETOWN) restore orig_pid failed");
183f08c3bdfSopenharmony_ci	}
184f08c3bdfSopenharmony_ci}
185f08c3bdfSopenharmony_ci
186f08c3bdfSopenharmony_ci#if defined(HAVE_STRUCT_F_OWNER_EX)
187f08c3bdfSopenharmony_cistatic void setownex_cleanup(void)
188f08c3bdfSopenharmony_ci{
189f08c3bdfSopenharmony_ci	TEST(fcntl(test_fd, F_SETOWN_EX, &orig_own_ex));
190f08c3bdfSopenharmony_ci	if (TEST_RETURN < 0) {
191f08c3bdfSopenharmony_ci		tst_brkm(TFAIL | TTERRNO, cleanup,
192f08c3bdfSopenharmony_ci			 "fcntl F_SETOWN_EX restore orig_own_ex failed");
193f08c3bdfSopenharmony_ci	}
194f08c3bdfSopenharmony_ci}
195f08c3bdfSopenharmony_ci
196f08c3bdfSopenharmony_cistatic void setownex_tid_test(void)
197f08c3bdfSopenharmony_ci{
198f08c3bdfSopenharmony_ci	static struct f_owner_ex tst_own_ex;
199f08c3bdfSopenharmony_ci
200f08c3bdfSopenharmony_ci	tst_own_ex.type = F_OWNER_TID;
201f08c3bdfSopenharmony_ci	tst_own_ex.pid = tst_syscall(__NR_gettid);
202f08c3bdfSopenharmony_ci
203f08c3bdfSopenharmony_ci	TEST(fcntl(test_fd, F_SETOWN_EX, &tst_own_ex));
204f08c3bdfSopenharmony_ci	if (TEST_RETURN < 0) {
205f08c3bdfSopenharmony_ci		tst_brkm(TFAIL | TTERRNO, cleanup,
206f08c3bdfSopenharmony_ci			 "fcntl F_SETOWN_EX failed");
207f08c3bdfSopenharmony_ci	}
208f08c3bdfSopenharmony_ci	test_set_and_get_sig(SIGUSR1, "F_GETOWN_EX, F_SETOWN_EX for thread ID");
209f08c3bdfSopenharmony_ci
210f08c3bdfSopenharmony_ci	setownex_cleanup();
211f08c3bdfSopenharmony_ci}
212f08c3bdfSopenharmony_ci
213f08c3bdfSopenharmony_cistatic void setownex_pid_test(void)
214f08c3bdfSopenharmony_ci{
215f08c3bdfSopenharmony_ci	static struct f_owner_ex tst_own_ex;
216f08c3bdfSopenharmony_ci
217f08c3bdfSopenharmony_ci	tst_own_ex.type = F_OWNER_PID;
218f08c3bdfSopenharmony_ci	tst_own_ex.pid = pid;
219f08c3bdfSopenharmony_ci
220f08c3bdfSopenharmony_ci	TEST(fcntl(test_fd, F_SETOWN_EX, &tst_own_ex));
221f08c3bdfSopenharmony_ci	if (TEST_RETURN < 0) {
222f08c3bdfSopenharmony_ci		tst_brkm(TFAIL | TTERRNO, cleanup,
223f08c3bdfSopenharmony_ci			 "fcntl F_SETOWN_EX failed");
224f08c3bdfSopenharmony_ci	}
225f08c3bdfSopenharmony_ci	test_set_and_get_sig(SIGUSR1,
226f08c3bdfSopenharmony_ci			     "F_GETOWN_EX, F_SETOWN_EX for process ID");
227f08c3bdfSopenharmony_ci
228f08c3bdfSopenharmony_ci	setownex_cleanup();
229f08c3bdfSopenharmony_ci}
230f08c3bdfSopenharmony_ci
231f08c3bdfSopenharmony_cistatic void setownex_pgrp_test(void)
232f08c3bdfSopenharmony_ci{
233f08c3bdfSopenharmony_ci	static struct f_owner_ex tst_own_ex;
234f08c3bdfSopenharmony_ci
235f08c3bdfSopenharmony_ci	tst_own_ex.type = F_OWNER_PGRP;
236f08c3bdfSopenharmony_ci	tst_own_ex.pid = pgrp_pid;
237f08c3bdfSopenharmony_ci
238f08c3bdfSopenharmony_ci	TEST(fcntl(test_fd, F_SETOWN_EX, &tst_own_ex));
239f08c3bdfSopenharmony_ci	if (TEST_RETURN < 0) {
240f08c3bdfSopenharmony_ci		tst_brkm(TFAIL | TTERRNO, cleanup,
241f08c3bdfSopenharmony_ci			 "fcntl F_SETOWN_EX failed");
242f08c3bdfSopenharmony_ci	}
243f08c3bdfSopenharmony_ci	test_set_and_get_sig(SIGUSR1,
244f08c3bdfSopenharmony_ci			     "F_GETOWN_EX, F_SETOWN_EX for process group ID");
245f08c3bdfSopenharmony_ci
246f08c3bdfSopenharmony_ci	setownex_cleanup();
247f08c3bdfSopenharmony_ci}
248f08c3bdfSopenharmony_ci#endif
249f08c3bdfSopenharmony_ci
250f08c3bdfSopenharmony_cistatic void test_set_and_get_sig(int sig, char *des)
251f08c3bdfSopenharmony_ci{
252f08c3bdfSopenharmony_ci	int orig_sig;
253f08c3bdfSopenharmony_ci
254f08c3bdfSopenharmony_ci	TEST(fcntl(test_fd, F_GETSIG));
255f08c3bdfSopenharmony_ci	if (TEST_RETURN < 0) {
256f08c3bdfSopenharmony_ci		tst_brkm(TFAIL | TTERRNO, cleanup,
257f08c3bdfSopenharmony_ci			 "fcntl(fd, F_GETSIG) get orig_sig failed");
258f08c3bdfSopenharmony_ci	}
259f08c3bdfSopenharmony_ci	orig_sig = TEST_RETURN;
260f08c3bdfSopenharmony_ci
261f08c3bdfSopenharmony_ci	if (orig_sig == 0 || orig_sig == SIGIO)
262f08c3bdfSopenharmony_ci		tst_resm(TINFO, "default io events signal is SIGIO");
263f08c3bdfSopenharmony_ci
264f08c3bdfSopenharmony_ci	TEST(fcntl(test_fd, F_SETSIG, sig));
265f08c3bdfSopenharmony_ci	if (TEST_RETURN < 0) {
266f08c3bdfSopenharmony_ci		tst_brkm(TFAIL | TTERRNO, cleanup,
267f08c3bdfSopenharmony_ci			 "fcntl(fd, F_SETSIG, SIG: %d) failed", sig);
268f08c3bdfSopenharmony_ci	}
269f08c3bdfSopenharmony_ci
270f08c3bdfSopenharmony_ci	TEST(fcntl(test_fd, F_GETSIG));
271f08c3bdfSopenharmony_ci	if (TEST_RETURN < 0) {
272f08c3bdfSopenharmony_ci		tst_brkm(TFAIL | TTERRNO, cleanup,
273f08c3bdfSopenharmony_ci			 "fcntl(fd, F_GETSIG) get the set signal failed");
274f08c3bdfSopenharmony_ci	}
275f08c3bdfSopenharmony_ci	if (TEST_RETURN != sig) {
276f08c3bdfSopenharmony_ci		tst_brkm(TFAIL | TTERRNO, cleanup,
277f08c3bdfSopenharmony_ci			 "fcntl F_SETSIG set SIG: %d failed", sig);
278f08c3bdfSopenharmony_ci	}
279f08c3bdfSopenharmony_ci
280f08c3bdfSopenharmony_ci	check_io_signal(des);
281f08c3bdfSopenharmony_ci
282f08c3bdfSopenharmony_ci	/* restore the default signal*/
283f08c3bdfSopenharmony_ci	TEST(fcntl(test_fd, F_SETSIG, orig_sig));
284f08c3bdfSopenharmony_ci	if (TEST_RETURN < 0) {
285f08c3bdfSopenharmony_ci		tst_brkm(TFAIL | TTERRNO, cleanup,
286f08c3bdfSopenharmony_ci			 "fcntl restore default signal failed");
287f08c3bdfSopenharmony_ci	}
288f08c3bdfSopenharmony_ci}
289f08c3bdfSopenharmony_ci
290f08c3bdfSopenharmony_cistatic void signal_parent(void)
291f08c3bdfSopenharmony_ci{
292f08c3bdfSopenharmony_ci	int ret, fd;
293f08c3bdfSopenharmony_ci
294f08c3bdfSopenharmony_ci	fd = pipe_fds[1];
295f08c3bdfSopenharmony_ci	close(pipe_fds[0]);
296f08c3bdfSopenharmony_ci
297f08c3bdfSopenharmony_ci	ret = setpgrp();
298f08c3bdfSopenharmony_ci	if (ret < 0) {
299f08c3bdfSopenharmony_ci		fprintf(stderr, "child process(%d) setpgrp() failed: %s \n",
300f08c3bdfSopenharmony_ci			getpid(), strerror(errno));
301f08c3bdfSopenharmony_ci	}
302f08c3bdfSopenharmony_ci
303f08c3bdfSopenharmony_ci	/* Wait for parent process to enter sigtimedwait(). */
304f08c3bdfSopenharmony_ci	tst_process_state_wait2(getppid(), 'S');
305f08c3bdfSopenharmony_ci
306f08c3bdfSopenharmony_ci	ret = write(fd, "c", 1);
307f08c3bdfSopenharmony_ci
308f08c3bdfSopenharmony_ci	switch (ret) {
309f08c3bdfSopenharmony_ci	case 0:
310f08c3bdfSopenharmony_ci		fprintf(stderr, "No data written, something is wrong\n");
311f08c3bdfSopenharmony_ci	break;
312f08c3bdfSopenharmony_ci	case -1:
313f08c3bdfSopenharmony_ci		fprintf(stderr, "Failed to write to pipe: %s\n",
314f08c3bdfSopenharmony_ci			strerror(errno));
315f08c3bdfSopenharmony_ci	break;
316f08c3bdfSopenharmony_ci	}
317f08c3bdfSopenharmony_ci
318f08c3bdfSopenharmony_ci	close(fd);
319f08c3bdfSopenharmony_ci	return;
320f08c3bdfSopenharmony_ci}
321f08c3bdfSopenharmony_ci
322f08c3bdfSopenharmony_cistatic void check_io_signal(char *des)
323f08c3bdfSopenharmony_ci{
324f08c3bdfSopenharmony_ci	int ret;
325f08c3bdfSopenharmony_ci	char c;
326f08c3bdfSopenharmony_ci	pid_t child;
327f08c3bdfSopenharmony_ci
328f08c3bdfSopenharmony_ci	child = tst_fork();
329f08c3bdfSopenharmony_ci	if (child < 0)
330f08c3bdfSopenharmony_ci		tst_brkm(TBROK | TERRNO, cleanup, "fork failed");
331f08c3bdfSopenharmony_ci
332f08c3bdfSopenharmony_ci	if (child == 0) {
333f08c3bdfSopenharmony_ci		signal_parent();
334f08c3bdfSopenharmony_ci		exit(0);
335f08c3bdfSopenharmony_ci	} else {
336f08c3bdfSopenharmony_ci		ret = sigtimedwait(&newset, NULL, &timeout);
337f08c3bdfSopenharmony_ci		if (ret == -1) {
338f08c3bdfSopenharmony_ci			tst_brkm(TBROK | TERRNO, NULL,
339f08c3bdfSopenharmony_ci				 "sigtimedwait() failed.");
340f08c3bdfSopenharmony_ci		}
341f08c3bdfSopenharmony_ci
342f08c3bdfSopenharmony_ci		switch (ret) {
343f08c3bdfSopenharmony_ci		case SIGUSR1:
344f08c3bdfSopenharmony_ci			tst_resm(TPASS, "fcntl test %s success", des);
345f08c3bdfSopenharmony_ci		break;
346f08c3bdfSopenharmony_ci		case SIGIO:
347f08c3bdfSopenharmony_ci			tst_resm(TFAIL, "received default SIGIO, fcntl test "
348f08c3bdfSopenharmony_ci				 "%s failed", des);
349f08c3bdfSopenharmony_ci		break;
350f08c3bdfSopenharmony_ci		default:
351f08c3bdfSopenharmony_ci			tst_brkm(TBROK, cleanup, "fcntl io events "
352f08c3bdfSopenharmony_ci				 "signal mechanism work abnormally");
353f08c3bdfSopenharmony_ci		}
354f08c3bdfSopenharmony_ci
355f08c3bdfSopenharmony_ci		SAFE_READ(cleanup, 1, test_fd, &c, 1);
356f08c3bdfSopenharmony_ci		wait(NULL);
357f08c3bdfSopenharmony_ci	}
358f08c3bdfSopenharmony_ci}
359f08c3bdfSopenharmony_ci
360f08c3bdfSopenharmony_cistatic void cleanup(void)
361f08c3bdfSopenharmony_ci{
362f08c3bdfSopenharmony_ci	if (sigprocmask(SIG_SETMASK, &oldset, NULL) < 0)
363f08c3bdfSopenharmony_ci		tst_resm(TWARN | TERRNO, "sigprocmask restore oldset failed");
364f08c3bdfSopenharmony_ci
365f08c3bdfSopenharmony_ci	if (pipe_fds[0] > 0 && close(pipe_fds[0]) == -1)
366f08c3bdfSopenharmony_ci		tst_resm(TWARN | TERRNO, "close(%d) failed", pipe_fds[0]);
367f08c3bdfSopenharmony_ci	if (pipe_fds[1] > 0 && close(pipe_fds[1]) == -1)
368f08c3bdfSopenharmony_ci		tst_resm(TWARN | TERRNO, "close(%d) failed", pipe_fds[1]);
369f08c3bdfSopenharmony_ci}
370