From f5ba01cf65309164adb06067b39cf28c071e1ccb Mon Sep 17 00:00:00 2001 From: Colin Walters <walters@verbum.org> Date: Wed, 31 May 2017 14:48:53 -0400 Subject: [PATCH] dirfd: Have dfd iter _take_fd() take a pointer and do a steal This avoids callers having to use `glnx_steal_fd()` on their own; in general, I think we should implement move semantics like this at the callee level. Another reason to do this is there's a subtle problem with doing: ``` somefunction (steal_value (&v), ..., error); ``` in that if `somefunction` throws, it may not have taken ownership of the value. At least `glnx_dirfd_iterator_init_take_fd()` didn't. --- glnx-dirfd.c | 10 +++++----- glnx-dirfd.h | 2 +- glnx-shutil.c | 3 +-- 3 files changed, 7 insertions(+), 8 deletions(-) diff --git a/glnx-dirfd.c b/glnx-dirfd.c index 388f2a324..bb73b015c 100644 --- a/glnx-dirfd.c +++ b/glnx-dirfd.c @@ -103,7 +103,7 @@ glnx_dirfd_iterator_init_at (int dfd, if (!glnx_opendirat (dfd, path, follow, &fd, error)) return FALSE; - if (!glnx_dirfd_iterator_init_take_fd (glnx_steal_fd (&fd), out_dfd_iter, error)) + if (!glnx_dirfd_iterator_init_take_fd (&fd, out_dfd_iter, error)) return FALSE; return TRUE; @@ -111,7 +111,7 @@ glnx_dirfd_iterator_init_at (int dfd, /** * glnx_dirfd_iterator_init_take_fd: - * @dfd: File descriptor - ownership is taken + * @dfd: File descriptor - ownership is taken, and the value is set to -1 * @dfd_iter: A directory iterator * @error: Error * @@ -119,16 +119,16 @@ glnx_dirfd_iterator_init_at (int dfd, * iteration. */ gboolean -glnx_dirfd_iterator_init_take_fd (int dfd, +glnx_dirfd_iterator_init_take_fd (int *dfd, GLnxDirFdIterator *dfd_iter, GError **error) { GLnxRealDirfdIterator *real_dfd_iter = (GLnxRealDirfdIterator*) dfd_iter; - DIR *d = fdopendir (dfd); + DIR *d = fdopendir (*dfd); if (!d) return glnx_throw_errno_prefix (error, "fdopendir"); - real_dfd_iter->fd = dfd; + real_dfd_iter->fd = glnx_steal_fd (dfd); real_dfd_iter->d = d; real_dfd_iter->initialized = TRUE; diff --git a/glnx-dirfd.h b/glnx-dirfd.h index 0cb79e693..581b3032e 100644 --- a/glnx-dirfd.h +++ b/glnx-dirfd.h @@ -55,7 +55,7 @@ typedef struct GLnxDirFdIterator GLnxDirFdIterator; gboolean glnx_dirfd_iterator_init_at (int dfd, const char *path, gboolean follow, GLnxDirFdIterator *dfd_iter, GError **error); -gboolean glnx_dirfd_iterator_init_take_fd (int dfd, GLnxDirFdIterator *dfd_iter, GError **error); +gboolean glnx_dirfd_iterator_init_take_fd (int *dfd, GLnxDirFdIterator *dfd_iter, GError **error); gboolean glnx_dirfd_iterator_next_dent (GLnxDirFdIterator *dfd_iter, struct dirent **out_dent, GCancellable *cancellable, diff --git a/glnx-shutil.c b/glnx-shutil.c index 6a1cdd4a7..2e02eea45 100644 --- a/glnx-shutil.c +++ b/glnx-shutil.c @@ -110,9 +110,8 @@ glnx_shutil_rm_rf_at (int dfd, } else { - if (!glnx_dirfd_iterator_init_take_fd (target_dfd, &dfd_iter, error)) + if (!glnx_dirfd_iterator_init_take_fd (&target_dfd, &dfd_iter, error)) return FALSE; - target_dfd = -1; if (!glnx_shutil_rm_rf_children (&dfd_iter, cancellable, error)) return FALSE; -- GitLab