It is handy to close all FDs from given FD to infinity. On FreeBSD the libc even has a function for that: closefrom(). It was ported to glibc too, but not musl. At least glibc implementation falls back to calling: close_range(from, ~0U, 0); Now that we have a wrapper for close_range() we implement closefrom() trivially. Signed-off-by: Michal Privoznik <mprivozn@xxxxxxxxxx> --- src/libvirt_private.syms | 1 + src/util/virfile.c | 21 +++++++++++++++++++++ src/util/virfile.h | 1 + 3 files changed, 23 insertions(+) diff --git a/src/libvirt_private.syms b/src/libvirt_private.syms index 3782f7f3c7..9477a07834 100644 --- a/src/libvirt_private.syms +++ b/src/libvirt_private.syms @@ -2269,6 +2269,7 @@ saferead; safewrite; safezero; virBuildPathInternal; +virCloseFrom; virCloseRange; virCloseRangeInit; virCloseRangeIsSupported; diff --git a/src/util/virfile.c b/src/util/virfile.c index 7696910e00..c74bdd1264 100644 --- a/src/util/virfile.c +++ b/src/util/virfile.c @@ -265,6 +265,27 @@ virCloseRangeIsSupported(void) } +/** + * virCloseFrom: + * + * Closes all open file descriptors greater than or equal to @fromfd. + * + * Returns: 0 on success, + * -1 on error (with errno set). + */ +int +virCloseFrom(int fromfd) +{ +#ifdef __FreeBSD__ + /* FreeBSD has closefrom() since FreeBSD-8.0, i.e. since 2009. */ + closefrom(fromfd); + return 0; +#else /* !__FreeBSD__ */ + return virCloseRange(fromfd, ~0U); +#endif /* !__FreeBSD__ */ +} + + /** * virFileDirectFdFlag: * diff --git a/src/util/virfile.h b/src/util/virfile.h index be0b02fdf0..adc032ba33 100644 --- a/src/util/virfile.h +++ b/src/util/virfile.h @@ -64,6 +64,7 @@ static inline void virForceCloseHelper(int *fd) int virCloseRange(unsigned int from, unsigned int to); int virCloseRangeInit(void); bool virCloseRangeIsSupported(void); +int virCloseFrom(int fromfd); /* For use on normal paths; caller must check return value, and failure sets errno per close. */ -- 2.41.0