From: Masatake YAMATO Date: Sat, 29 Nov 2025 19:53:24 +0000 (+0900) Subject: lsfd: (refactor) make call_with_foreign_fd reusable X-Git-Tag: v2.43-devel~95^2~4 X-Git-Url: http://git.ipfire.org/gitweb.cgi?a=commitdiff_plain;h=9d76cfb729bfe7995f7626f150f9e727636a4bd2;p=thirdparty%2Futil-linux.git lsfd: (refactor) make call_with_foreign_fd reusable Signed-off-by: Masatake YAMATO --- diff --git a/lsfd-cmd/Makemodule.am b/lsfd-cmd/Makemodule.am index 0f96ce147..4674cff9c 100644 --- a/lsfd-cmd/Makemodule.am +++ b/lsfd-cmd/Makemodule.am @@ -20,7 +20,8 @@ lsfd_SOURCES = \ lsfd-cmd/unkn.c \ lsfd-cmd/fifo.c \ lsfd-cmd/pidfd.h \ - lsfd-cmd/pidfd.c + lsfd-cmd/pidfd.c \ + lsfd-cmd/util.c lsfd_LDADD = $(LDADD) $(MQ_LIBS) libsmartcols.la libcommon.la lsfd_CFLAGS = $(AM_CFLAGS) -I$(ul_libsmartcols_incdir) endif diff --git a/lsfd-cmd/cdev.c b/lsfd-cmd/cdev.c index 322e38b4a..989ffa481 100644 --- a/lsfd-cmd/cdev.c +++ b/lsfd-cmd/cdev.c @@ -466,28 +466,6 @@ static int cdev_tun_handle_fdinfo(struct cdev *cdev, const char *key, const char } #ifdef TUNGETDEVNETNS -static int call_with_foreign_fd(pid_t target_pid, int target_fd, - int (*fn)(int, void*), void *data) -{ - int pidfd, tfd, r; - - pidfd = pidfd_open(target_pid, 0); - if (pidfd < 0) - return pidfd; - - tfd = pidfd_getfd(pidfd, target_fd, 0); - if (tfd < 0) { - close(pidfd); - return tfd; - } - - r = fn(tfd, data); - - close(tfd); - close(pidfd); - return r; -} - static int cdev_tun_get_devnetns(int tfd, void *data) { struct tundata *tundata = data; diff --git a/lsfd-cmd/lsfd.h b/lsfd-cmd/lsfd.h index 626027a4a..553546d8b 100644 --- a/lsfd-cmd/lsfd.h +++ b/lsfd-cmd/lsfd.h @@ -338,4 +338,10 @@ bool is_multiplexed_by_eventpoll(int fd, struct list_head *eventpolls); */ bool is_pidfs_dev(dev_t dev); +/* + * Utility + */ +int call_with_foreign_fd(pid_t target_pid, int target_fd, + int (*fn)(int, void*), void *data); + #endif /* UTIL_LINUX_LSFD_H */ diff --git a/lsfd-cmd/meson.build b/lsfd-cmd/meson.build index 856d5cdd0..f10ca1a41 100644 --- a/lsfd-cmd/meson.build +++ b/lsfd-cmd/meson.build @@ -12,6 +12,7 @@ lsfd_sources = files ( 'unkn.c', 'fifo.c', 'pidfd.c', + 'util.c', ) lsfd_manadocs = files('lsfd.1.adoc') diff --git a/lsfd-cmd/sock-xinfo.c b/lsfd-cmd/sock-xinfo.c index 7e6ca0cf8..d31067009 100644 --- a/lsfd-cmd/sock-xinfo.c +++ b/lsfd-cmd/sock-xinfo.c @@ -231,24 +231,16 @@ void load_sock_xinfo(struct path_cxt *pc, const char *name, ino_t netns) } } -void load_fdsk_xinfo(struct proc *proc, int fd) +static int load_fdsk_xinfo_cb(int sk, void *data __attribute__((__unused__))) { - int pidfd, sk, nsfd; + int nsfd; struct netns *nsobj; struct stat sb; - - /* This is additional/extra information, ignoring failures. */ - pidfd = pidfd_open(proc->pid, 0); - if (pidfd < 0) - return; - - sk = pidfd_getfd(pidfd, fd, 0); - if (sk < 0) - goto out_pidfd; + int r = -1; nsfd = ioctl(sk, SIOCGSKNS); if (nsfd < 0) - goto out_sk; + return nsfd; if (fstat(nsfd, &sb) < 0) goto out_nsfd; @@ -256,15 +248,20 @@ void load_fdsk_xinfo(struct proc *proc, int fd) if (is_sock_xinfo_loaded(sb.st_ino)) goto out_nsfd; + r = 0; nsobj = mark_sock_xinfo_loaded(sb.st_ino); load_sock_xinfo_with_fd(nsfd, nsobj); out_nsfd: close(nsfd); -out_sk: - close(sk); -out_pidfd: - close(pidfd); + return r; +} + +void load_fdsk_xinfo(struct proc *proc, int fd) +{ + call_with_foreign_fd(proc->pid, fd, + load_fdsk_xinfo_cb, NULL); + } void initialize_sock_xinfos(void) diff --git a/lsfd-cmd/util.c b/lsfd-cmd/util.c new file mode 100644 index 000000000..f3e3a727c --- /dev/null +++ b/lsfd-cmd/util.c @@ -0,0 +1,52 @@ +/* + * util.c - utilities used in lsfd + * + * Copyright (C) 2021-2026 Red Hat, Inc. All rights reserved. + * Written by Masatake YAMATO + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 2 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it would be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software Foundation, + * Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + */ +#include "lsfd.h" /* prototype decl for call_with_foreign_fd */ +#include "pidfd-utils.h" + +static int call_with_foreign_fd_via_pidfd(int pidfd, int target_fd, + int (*fn)(int, void*), void *data) +{ + int tfd, r; + + tfd = pidfd_getfd(pidfd, target_fd, 0); + if (tfd < 0) + return tfd; + + r = fn(tfd, data); + + close(tfd); + return r; +} + +int call_with_foreign_fd(pid_t target_pid, int target_fd, + int (*fn)(int, void*), void *data) +{ + int pidfd, r; + + pidfd = pidfd_open(target_pid, 0); + if (pidfd < 0) + return pidfd; + + r = call_with_foreign_fd_via_pidfd(pidfd, target_fd, fn, data); + + close(pidfd); + return r; +}