asterinas/test/src/apps/process/group_session.c

211 lines
4.9 KiB
C
Raw Normal View History

2025-04-21 06:17:02 +00:00
// SPDX-License-Identifier: MPL-2.0
2025-06-21 15:56:55 +00:00
#include "../test.h"
2025-04-21 06:17:02 +00:00
#include <unistd.h>
#include <sys/wait.h>
static pid_t current;
static pid_t child1, child2;
FN_SETUP(setpgrp)
{
CHECK(setpgid(0, 0));
}
END_SETUP()
FN_SETUP(spawn_child)
{
current = CHECK(getpid());
if ((child1 = CHECK(fork())) == 0) {
sleep(60);
exit(EXIT_FAILURE);
}
if ((child2 = CHECK(fork())) == 0) {
sleep(60);
exit(EXIT_FAILURE);
}
}
END_SETUP()
FN_TEST(setpgid_invalid)
{
// Negative PIDs or PGIDs
TEST_ERRNO(setpgid(-1, current), EINVAL);
TEST_ERRNO(setpgid(current, -1), EINVAL);
2025-04-21 06:17:02 +00:00
// Non-present process groups
TEST_ERRNO(setpgid(child1, child2), EPERM);
TEST_ERRNO(setpgid(child2, child1), EPERM);
TEST_ERRNO(setpgid(child1, 0x3c3c3c3c), EPERM);
TEST_ERRNO(setpgid(child2, 0x3c3c3c3c), EPERM);
// Non-present processes
TEST_ERRNO(setpgid(0x3c3c3c3c, current), ESRCH);
TEST_ERRNO(setpgid(0x3c3c3c3c, current), ESRCH);
// Non-current and non-child processes
TEST_ERRNO(setpgid(getppid(), 0), ESRCH);
TEST_ERRNO(setpgid(getppid(), 0x3c3c3c3c), ESRCH);
}
END_TEST()
2025-05-02 14:43:16 +00:00
FN_TEST(setpgid_getpgid)
2025-04-21 06:17:02 +00:00
{
// PGID members
// | |
// v v
// Process groups: [current] = { current, child1, child2 }
TEST_SUCC(setpgid(0, 0));
TEST_SUCC(setpgid(0, current));
TEST_SUCC(setpgid(current, 0));
TEST_SUCC(setpgid(current, getpid()));
TEST_ERRNO(setpgid(child1, child2), EPERM);
TEST_ERRNO(setpgid(child2, child1), EPERM);
2025-05-02 14:43:16 +00:00
TEST_RES(getpgid(current), _ret == current);
TEST_RES(getpgid(child1), _ret == current);
TEST_RES(getpgid(child2), _ret == current);
2025-04-21 06:17:02 +00:00
// Process groups: [current] = { current, child2 }, [child1] = { child1 }
TEST_SUCC(setpgid(child1, 0));
2025-05-02 14:43:16 +00:00
TEST_RES(getpgid(current), _ret == current);
TEST_RES(getpgid(child1), _ret == child1);
TEST_RES(getpgid(child2), _ret == current);
2025-04-21 06:17:02 +00:00
// Process groups: [current] = { current }, [child1] = { child1, child2 }
TEST_SUCC(setpgid(child2, child1));
2025-05-02 14:43:16 +00:00
TEST_RES(getpgid(current), _ret == current);
TEST_RES(getpgid(child1), _ret == child1);
TEST_RES(getpgid(child2), _ret == child1);
2025-04-21 06:17:02 +00:00
// Process groups: [current] = { current, child1 }, [child1] = { child2 }
TEST_SUCC(setpgid(child1, current));
2025-05-02 14:43:16 +00:00
TEST_RES(getpgid(current), _ret == current);
TEST_RES(getpgid(child1), _ret == current);
TEST_RES(getpgid(child2), _ret == child1);
2025-04-21 06:17:02 +00:00
// Process groups: [current] = { current }, [child1] = { child1, child2 }
TEST_SUCC(setpgid(child1, child1));
2025-05-02 14:43:16 +00:00
TEST_RES(getpgid(current), _ret == current);
TEST_RES(getpgid(child1), _ret == child1);
TEST_RES(getpgid(child2), _ret == child1);
2025-04-21 06:17:02 +00:00
}
END_TEST()
FN_TEST(setsid_group_leader)
{
// Process groups: [current] = { current }, [child1] = { child1, child2 }
TEST_ERRNO(setsid(), EPERM);
// Process groups: [current] = { child1 }, [child1] = { current, child2 }
TEST_SUCC(setpgid(child1, current));
TEST_SUCC(setpgid(current, child1));
2025-05-02 14:43:16 +00:00
TEST_RES(getpgid(current), _ret == child1);
TEST_RES(getpgid(child1), _ret == current);
TEST_RES(getpgid(child2), _ret == child1);
2025-04-21 06:17:02 +00:00
TEST_ERRNO(setsid(), EPERM);
}
END_TEST()
FN_TEST(setsid)
{
// Process groups: [child1] = { current, child1, child2 }
TEST_SUCC(setpgid(child1, child1));
2025-05-02 14:43:16 +00:00
TEST_RES(getpgid(current), _ret == child1);
TEST_RES(getpgid(child1), _ret == child1);
TEST_RES(getpgid(child2), _ret == child1);
2025-04-21 06:17:02 +00:00
// Process groups (old session): [child1] = { child1, child2 }
// Process groups (new session): [current] = { current }
TEST_SUCC(setsid());
}
END_TEST()
// From now on, the current process and the child processes are in two sessions!
FN_TEST(setsid_session_leader)
{
// FIXME: We fail this test to work around a gVisor bug.
// See comments in `Process::to_new_session` for details.
2025-12-14 14:07:07 +00:00
#ifndef __asterinas__
TEST_ERRNO(setsid(), EPERM);
#endif
2025-04-21 06:17:02 +00:00
}
END_TEST()
FN_TEST(setpgid_two_sessions)
{
// Setting process groups in another session should never succeed
TEST_ERRNO(setpgid(child1, child1), EPERM);
TEST_ERRNO(setpgid(child2, child2), EPERM);
TEST_ERRNO(setpgid(child1, current), EPERM);
TEST_ERRNO(setpgid(child2, current), EPERM);
TEST_ERRNO(setpgid(child2, child1), EPERM);
}
END_TEST()
2025-05-02 14:43:16 +00:00
FN_TEST(getpgid_two_sessions)
{
TEST_RES(getpgid(current), _ret == current);
TEST_RES(getpgid(child1), _ret == child1);
TEST_RES(getpgid(child2), _ret == child1);
}
END_TEST()
FN_TEST(getsid_two_sessions)
{
int old_sid;
TEST_RES(getsid(current), _ret == current);
old_sid = TEST_SUCC(getsid(child1));
TEST_RES(getsid(child2), _ret == old_sid);
}
END_TEST()
FN_TEST(getpgid_invalid)
{
// Negative PIDs
TEST_ERRNO(getpgid(-1), ESRCH);
2025-05-02 14:43:16 +00:00
// Non-present processes
TEST_ERRNO(getpgid(0x3c3c3c3c), ESRCH);
}
END_TEST()
FN_TEST(getsid_invalid)
{
// Negative PIDs
TEST_ERRNO(getsid(-1), ESRCH);
2025-05-02 14:43:16 +00:00
// Non-present processes
TEST_ERRNO(getsid(0x3c3c3c3c), ESRCH);
}
END_TEST()
2025-04-21 06:17:02 +00:00
FN_SETUP(kill_child)
{
CHECK(kill(child1, SIGKILL));
CHECK_WITH(wait(NULL), _ret == child1);
CHECK(kill(child2, SIGKILL));
CHECK_WITH(wait(NULL), _ret == child2);
}
END_SETUP()