diff --git a/include/spawn.h b/include/spawn.h index 4ba3998a3e90..53373a6c8db8 100644 --- a/include/spawn.h +++ b/include/spawn.h @@ -92,6 +92,8 @@ int posix_spawn_file_actions_addchdir_np(posix_spawn_file_actions_t * __restrict, const char * __restrict); int posix_spawn_file_actions_addfchdir_np(posix_spawn_file_actions_t *, int); +int posix_spawn_file_actions_addclosefrom_np(posix_spawn_file_actions_t *, + int); #endif /* diff --git a/lib/libc/gen/Symbol.map b/lib/libc/gen/Symbol.map index bae2463d99d4..5554c32ab4f2 100644 --- a/lib/libc/gen/Symbol.map +++ b/lib/libc/gen/Symbol.map @@ -437,6 +437,7 @@ FBSD_1.6 { FBSD_1.7 { posix_spawn_file_actions_addchdir_np; + posix_spawn_file_actions_addclosefrom_np; posix_spawn_file_actions_addfchdir_np; sched_getaffinity; sched_setaffinity; diff --git a/lib/libc/gen/posix_spawn.c b/lib/libc/gen/posix_spawn.c index 00d1724a6515..909db9a60a02 100644 --- a/lib/libc/gen/posix_spawn.c +++ b/lib/libc/gen/posix_spawn.c @@ -68,6 +68,7 @@ typedef struct __posix_spawn_file_actions_entry { FAE_CLOSE, FAE_CHDIR, FAE_FCHDIR, + FAE_CLOSEFROM, } fae_action; int fae_fildes; @@ -190,6 +191,9 @@ process_file_actions_entry(posix_spawn_file_actions_entry_t *fae) if (fchdir(fae->fae_fildes) != 0) return (errno); break; + case FAE_CLOSEFROM: + closefrom(fae->fae_fildes); + break; } return (0); } @@ -533,6 +537,27 @@ posix_spawn_file_actions_addfchdir_np(posix_spawn_file_actions_t *__restrict fa, return (0); } +int +posix_spawn_file_actions_addclosefrom_np (posix_spawn_file_actions_t * + __restrict fa, int from) +{ + posix_spawn_file_actions_entry_t *fae; + + if (from < 0) + return (EBADF); + + /* Allocate object */ + fae = malloc(sizeof(posix_spawn_file_actions_entry_t)); + if (fae == NULL) + return (errno); + + fae->fae_action = FAE_CLOSEFROM; + fae->fae_fildes = from; + + STAILQ_INSERT_TAIL(&(*fa)->fa_list, fae, fae_list); + return (0); +} + /* * Spawn attributes */