mirror of
https://github.com/freebsd/freebsd-src
synced 2024-09-06 17:18:32 +00:00
libc: Fix t_spawn_fileactions test after ATF update
Since 4581cefc1e
ATF opens the results file on startup. This fixes problems like
capsicumized tests not being able to open the file on exit.
However, this test closes all file descriptors above 3 to get a
deterministic fd table allocation for the child. Instead of using closefrom
(which will close the ATF output file FD) I've changed this test use
the lowest available fd and pass that to the helper program as a string.
We could also try to re-open the results file in ATF if we get a EBADF
error, but that will fail when running under Capsicum.
Reviewed By: cem
Differential Revision: https://reviews.freebsd.org/D28684
This commit is contained in:
parent
1c808fcd85
commit
2aa3ef285a
|
@ -49,48 +49,61 @@ int
|
|||
main(int argc, char **argv)
|
||||
{
|
||||
int res = EXIT_SUCCESS;
|
||||
long lowfd;
|
||||
char buf[BUFSIZE];
|
||||
struct stat sb0, sb1;
|
||||
|
||||
if (argc < 2) {
|
||||
fprintf(stderr, "%s: Not enough arguments: %d\n", getprogname(),
|
||||
argc);
|
||||
return EXIT_FAILURE;
|
||||
}
|
||||
lowfd = strtol(argv[1], NULL, 10);
|
||||
if (lowfd < 3) {
|
||||
fprintf(stderr, "%s: Invalid lowfd %d (as str: %s) \n",
|
||||
getprogname(), argc, argv[1]);
|
||||
return EXIT_FAILURE;
|
||||
}
|
||||
|
||||
strcpy(buf, "test...");
|
||||
/* file desc 3 should be closed via addclose */
|
||||
if (read(3, buf, BUFSIZE) != -1 || errno != EBADF) {
|
||||
fprintf(stderr, "%s: filedesc 3 is not closed\n",
|
||||
/* First fd should be closed via addclose */
|
||||
if (read(lowfd, buf, BUFSIZE) != -1 || errno != EBADF) {
|
||||
fprintf(stderr, "%s: first filedesc is not closed\n",
|
||||
getprogname());
|
||||
res = EXIT_FAILURE;
|
||||
}
|
||||
/* file desc 4 should be closed via closeonexec */
|
||||
if (read(4, buf, BUFSIZE) != -1 || errno != EBADF) {
|
||||
fprintf(stderr, "%s: filedesc 4 is not closed\n",
|
||||
/* Next file desc should be closed via closeonexec */
|
||||
if (read(lowfd + 1, buf, BUFSIZE) != -1 || errno != EBADF) {
|
||||
fprintf(stderr, "%s: filedesc +1 is not closed\n",
|
||||
getprogname());
|
||||
res = EXIT_FAILURE;
|
||||
}
|
||||
/* file desc 5 remains open */
|
||||
if (write(5, buf, BUFSIZE) <= 0) {
|
||||
fprintf(stderr, "%s: could not write to filedesc 5\n",
|
||||
/* file desc + 2 remains open */
|
||||
if (write(lowfd + 2, buf, BUFSIZE) <= 0) {
|
||||
fprintf(stderr, "%s: could not write to filedesc +2\n",
|
||||
getprogname());
|
||||
res = EXIT_FAILURE;
|
||||
}
|
||||
/* file desc 6 should be open (via addopen) */
|
||||
if (write(6, buf, BUFSIZE) <= 0) {
|
||||
fprintf(stderr, "%s: could not write to filedesc 6\n",
|
||||
/* file desc + 3 should be open (via addopen) */
|
||||
if (write(lowfd + 3, buf, BUFSIZE) <= 0) {
|
||||
fprintf(stderr, "%s: could not write to filedesc +3\n",
|
||||
getprogname());
|
||||
res = EXIT_FAILURE;
|
||||
}
|
||||
/* file desc 7 should refer to stdout */
|
||||
/* file desc + 4 should refer to stdout */
|
||||
fflush(stdout);
|
||||
if (fstat(fileno(stdout), &sb0) != 0) {
|
||||
fprintf(stderr, "%s: could not fstat stdout\n",
|
||||
getprogname());
|
||||
res = EXIT_FAILURE;
|
||||
}
|
||||
if (fstat(7, &sb1) != 0) {
|
||||
fprintf(stderr, "%s: could not fstat filedesc 7\n",
|
||||
if (fstat(lowfd + 4, &sb1) != 0) {
|
||||
fprintf(stderr, "%s: could not fstat filedesc +4\n",
|
||||
getprogname());
|
||||
res = EXIT_FAILURE;
|
||||
}
|
||||
if (write(7, buf, strlen(buf)) <= 0) {
|
||||
fprintf(stderr, "%s: could not write to filedesc 7\n",
|
||||
if (write(lowfd + 4, buf, strlen(buf)) <= 0) {
|
||||
fprintf(stderr, "%s: could not write to filedesc +4\n",
|
||||
getprogname());
|
||||
res = EXIT_FAILURE;
|
||||
}
|
||||
|
|
|
@ -301,26 +301,34 @@ ATF_TC_BODY(t_spawn_fileactions, tc)
|
|||
{
|
||||
int fd1, fd2, fd3, status, err;
|
||||
pid_t pid;
|
||||
char * const args[2] = { __UNCONST("h_fileactions"), NULL };
|
||||
char *args[3] = { __UNCONST("h_fileactions"), NULL, NULL };
|
||||
int lowfd;
|
||||
char lowfdstr[32];
|
||||
char helper[FILENAME_MAX];
|
||||
posix_spawn_file_actions_t fa;
|
||||
|
||||
posix_spawn_file_actions_init(&fa);
|
||||
|
||||
closefrom(fileno(stderr)+1);
|
||||
/* Note: this assumes no gaps in the fd table */
|
||||
lowfd = open("/", O_RDONLY);
|
||||
ATF_REQUIRE(lowfd > 0);
|
||||
ATF_REQUIRE_EQ(0, close(lowfd));
|
||||
snprintf(lowfdstr, sizeof(lowfdstr), "%d", lowfd);
|
||||
args[1] = lowfdstr;
|
||||
|
||||
fd1 = open("/dev/null", O_RDONLY);
|
||||
ATF_REQUIRE(fd1 == 3);
|
||||
ATF_REQUIRE_EQ(fd1, lowfd);
|
||||
|
||||
fd2 = open("/dev/null", O_WRONLY, O_CLOEXEC);
|
||||
ATF_REQUIRE(fd2 == 4);
|
||||
ATF_REQUIRE_EQ(fd2, lowfd + 1);
|
||||
|
||||
fd3 = open("/dev/null", O_WRONLY);
|
||||
ATF_REQUIRE(fd3 == 5);
|
||||
ATF_REQUIRE_EQ(fd3, lowfd + 2);
|
||||
|
||||
posix_spawn_file_actions_addclose(&fa, fd1);
|
||||
posix_spawn_file_actions_addopen(&fa, 6, "/dev/null", O_RDWR, 0);
|
||||
posix_spawn_file_actions_adddup2(&fa, 1, 7);
|
||||
posix_spawn_file_actions_addopen(&fa, lowfd + 3, "/dev/null", O_RDWR,
|
||||
0);
|
||||
posix_spawn_file_actions_adddup2(&fa, 1, lowfd + 4);
|
||||
|
||||
snprintf(helper, sizeof helper, "%s/h_fileactions",
|
||||
atf_tc_get_config_var(tc, "srcdir"));
|
||||
|
|
Loading…
Reference in a new issue