1// SPDX-License-Identifier: GPL-2.0-or-later
2/*
3 * Copyright (c) 2016 Xiao Yang <yangx.jy@cn.fujitsu.com>
4 */
5
6 /*
7 * Testname: kcmp03.c
8 *
9 * Description:
10 * 1) kcmp() returns 0 if the processes share the same file system information.
11 * 2) kcmp() returns 0 if the processes share I/O context.
12 * 3) kcmp() returns 0 if the processes share the same list of System V
13 *    semaphore undo operations.
14 * 4) kcmp() returns 0 if the processes share the same address space.
15 */
16
17#define _GNU_SOURCE
18
19#include <errno.h>
20#include <stdlib.h>
21#include <sys/wait.h>
22#include "tst_test.h"
23#include "lapi/kcmp.h"
24#include "lapi/sched.h"
25
26#define STACK_SIZE	(1024*1024)
27
28static int pid1;
29static int pid2;
30static void *stack;
31
32static struct tcase {
33	int clone_type;
34	int kcmp_type;
35} tcases[] = {
36	{CLONE_VM, KCMP_VM},
37	{CLONE_FS, KCMP_FS},
38	{CLONE_IO, KCMP_IO},
39	{CLONE_SYSVSEM, KCMP_SYSVSEM}
40};
41
42static void setup(void)
43{
44	stack = SAFE_MALLOC(STACK_SIZE);
45}
46
47static void cleanup(void)
48{
49	free(stack);
50}
51
52static int do_child(void *arg)
53{
54	pid2 = getpid();
55
56	TEST(kcmp(pid1, pid2, *(int *)arg, 0, 0));
57	if (TST_RET == -1) {
58		tst_res(TFAIL | TTERRNO, "kcmp() failed unexpectedly");
59		return 0;
60	}
61
62	if (TST_RET == 0)
63		tst_res(TPASS, "kcmp() returned the expected value");
64	else
65		tst_res(TFAIL, "kcmp() returned the unexpected value");
66
67	return 0;
68}
69
70static void verify_kcmp(unsigned int n)
71{
72	int res;
73
74	struct tcase *tc = &tcases[n];
75
76	pid1 = getpid();
77
78	res = ltp_clone(tc->clone_type | SIGCHLD, do_child, &tc->kcmp_type,
79			STACK_SIZE, stack);
80	if (res == -1)
81		tst_res(TFAIL | TERRNO, "clone() Failed");
82}
83
84static struct tst_test test = {
85	.tcnt = ARRAY_SIZE(tcases),
86	.setup = setup,
87	.cleanup = cleanup,
88	.forks_child = 1,
89	.test = verify_kcmp,
90};
91