[LTP] [PATCH] lib: tst_detach_device_by_fd() set dev_fd to -1

Cyril Hrubis chrubis@suse.cz
Tue Oct 7 13:27:19 CEST 2025


Apparently I tend to forget that tst_detach_device_by_fd() closes the
file descriptor. This change makes it more obvious by chaning the fd to
a pointer and also sets the dev_fd to -1, which matches the SAFE_CLOSE()
behavior.

Signed-off-by: Cyril Hrubis <chrubis@suse.cz>
---
 include/tst_device.h                          |  4 ++--
 lib/tst_device.c                              | 21 ++++++++++---------
 testcases/kernel/syscalls/ioctl/ioctl09.c     |  2 +-
 .../kernel/syscalls/ioctl/ioctl_loop01.c      |  6 +++---
 .../kernel/syscalls/ioctl/ioctl_loop02.c      |  2 +-
 .../kernel/syscalls/ioctl/ioctl_loop04.c      |  2 +-
 .../kernel/syscalls/ioctl/ioctl_loop06.c      |  4 ++--
 .../kernel/syscalls/ioctl/ioctl_loop07.c      |  4 ++--
 8 files changed, 23 insertions(+), 22 deletions(-)

diff --git a/include/tst_device.h b/include/tst_device.h
index 898335b16..252942f8b 100644
--- a/include/tst_device.h
+++ b/include/tst_device.h
@@ -77,10 +77,10 @@ uint64_t tst_get_device_size(const char *dev_path);
  * it is up to caller to open it again for further usage.
  *
  * @dev_path Path to the loop device e.g. /dev/loop0
- * @dev_fd a open fd for the loop device
+ * @dev_fd An open fd for the loop device, set to -1 after the completion.
  * @return Zero on succes, non-zero otherwise.
  */
-int tst_detach_device_by_fd(const char *dev_path, int dev_fd);
+int tst_detach_device_by_fd(const char *dev_path, int *dev_fd);
 
 /*
  * Detaches a file from a loop device.
diff --git a/lib/tst_device.c b/lib/tst_device.c
index 2364df052..6ae914720 100644
--- a/lib/tst_device.c
+++ b/lib/tst_device.c
@@ -239,9 +239,9 @@ uint64_t tst_get_device_size(const char *dev_path)
 	return size/1024/1024;
 }
 
-int tst_detach_device_by_fd(const char *dev, int dev_fd)
+int tst_detach_device_by_fd(const char *dev, int *dev_fd)
 {
-	int ret, i;
+	int ret, i, retval = 1;
 
 	/* keep trying to clear LOOPDEV until we get ENXIO, a quick succession
 	 * of attach/detach might not give udev enough time to complete
@@ -250,19 +250,18 @@ int tst_detach_device_by_fd(const char *dev, int dev_fd)
 	 * device is detached only after last close.
 	 */
 	for (i = 0; i < 40; i++) {
-		ret = ioctl(dev_fd, LOOP_CLR_FD, 0);
+		ret = ioctl(*dev_fd, LOOP_CLR_FD, 0);
 
 		if (ret && (errno == ENXIO)) {
-			SAFE_CLOSE(NULL, dev_fd);
-			return 0;
+			retval = 0;
+			goto exit;
 		}
 
 		if (ret && (errno != EBUSY)) {
 			tst_resm(TWARN,
 				 "ioctl(%s, LOOP_CLR_FD, 0) unexpectedly failed with: %s",
 				 dev, tst_strerrno(errno));
-			SAFE_CLOSE(NULL, dev_fd);
-			return 1;
+			goto exit;
 		}
 
 		usleep(50000);
@@ -270,8 +269,10 @@ int tst_detach_device_by_fd(const char *dev, int dev_fd)
 
 	tst_resm(TWARN,
 		"ioctl(%s, LOOP_CLR_FD, 0) no ENXIO for too long", dev);
-	SAFE_CLOSE(NULL, dev_fd);
-	return 1;
+exit:
+	SAFE_CLOSE(NULL, *dev_fd);
+	*dev_fd = -1;
+	return retval;
 }
 
 int tst_detach_device(const char *dev)
@@ -284,7 +285,7 @@ int tst_detach_device(const char *dev)
 		return 1;
 	}
 
-	ret = tst_detach_device_by_fd(dev, dev_fd);
+	ret = tst_detach_device_by_fd(dev, &dev_fd);
 	return ret;
 }
 
diff --git a/testcases/kernel/syscalls/ioctl/ioctl09.c b/testcases/kernel/syscalls/ioctl/ioctl09.c
index f86355f2c..262d6fcab 100644
--- a/testcases/kernel/syscalls/ioctl/ioctl09.c
+++ b/testcases/kernel/syscalls/ioctl/ioctl09.c
@@ -76,7 +76,7 @@ static void verify_ioctl(void)
 	check_partition(1, true);
 	check_partition(2, true);
 
-	tst_detach_device_by_fd(dev_path, dev_fd);
+	tst_detach_device_by_fd(dev_path, &dev_fd);
 	dev_fd = SAFE_OPEN(dev_path, O_RDWR);
 	attach_flag = 0;
 }
diff --git a/testcases/kernel/syscalls/ioctl/ioctl_loop01.c b/testcases/kernel/syscalls/ioctl/ioctl_loop01.c
index cb1b506d2..4ecc93b1e 100644
--- a/testcases/kernel/syscalls/ioctl/ioctl_loop01.c
+++ b/testcases/kernel/syscalls/ioctl/ioctl_loop01.c
@@ -99,13 +99,14 @@ static void verify_ioctl_loop(void)
 	TST_ASSERT_INT(autoclear_path, 0);
 	TST_ASSERT_STR(backing_path, backing_file_path);
 
+	dev_fd = SAFE_OPEN(dev_path, O_RDWR);
+
 	check_loop_value(SET_FLAGS, GET_FLAGS, 1);
 
 	tst_res(TINFO, "Test flag can be clear");
 	check_loop_value(0, LO_FLAGS_PARTSCAN, 0);
 
-	tst_detach_device_by_fd(dev_path, dev_fd);
-	dev_fd = SAFE_OPEN(dev_path, O_RDWR);
+	tst_detach_device_by_fd(dev_path, &dev_fd);
 
 	attach_flag = 0;
 }
@@ -122,7 +123,6 @@ static void setup(void)
 	sprintf(sys_loop_partpath, "/sys/block/loop%d/loop%dp1", dev_num, dev_num);
 	backing_file_path = tst_tmpdir_genpath("test.img");
 	sprintf(loop_partpath, "%sp1", dev_path);
-	dev_fd = SAFE_OPEN(dev_path, O_RDWR);
 }
 
 static void cleanup(void)
diff --git a/testcases/kernel/syscalls/ioctl/ioctl_loop02.c b/testcases/kernel/syscalls/ioctl/ioctl_loop02.c
index 6026af1e2..10776d0b6 100644
--- a/testcases/kernel/syscalls/ioctl/ioctl_loop02.c
+++ b/testcases/kernel/syscalls/ioctl/ioctl_loop02.c
@@ -100,7 +100,7 @@ static void verify_ioctl_loop(unsigned int n)
 	}
 
 	SAFE_CLOSE(file_fd);
-	tst_detach_device_by_fd(dev_path, dev_fd);
+	tst_detach_device_by_fd(dev_path, &dev_fd);
 	dev_fd = SAFE_OPEN(dev_path, O_RDWR);
 	attach_flag = 0;
 }
diff --git a/testcases/kernel/syscalls/ioctl/ioctl_loop04.c b/testcases/kernel/syscalls/ioctl/ioctl_loop04.c
index 839648f26..59f9de643 100644
--- a/testcases/kernel/syscalls/ioctl/ioctl_loop04.c
+++ b/testcases/kernel/syscalls/ioctl/ioctl_loop04.c
@@ -60,7 +60,7 @@ static void verify_ioctl_loop(void)
 	TST_ASSERT_INT(sys_loop_sizepath, NEW_SIZE/512);
 
 	SAFE_CLOSE(file_fd);
-	tst_detach_device_by_fd(dev_path, dev_fd);
+	tst_detach_device_by_fd(dev_path, &dev_fd);
 	dev_fd = SAFE_OPEN(dev_path, O_RDWR);
 	unlink("test.img");
 	attach_flag = 0;
diff --git a/testcases/kernel/syscalls/ioctl/ioctl_loop06.c b/testcases/kernel/syscalls/ioctl/ioctl_loop06.c
index 35e9e79e9..0a9618d00 100644
--- a/testcases/kernel/syscalls/ioctl/ioctl_loop06.c
+++ b/testcases/kernel/syscalls/ioctl/ioctl_loop06.c
@@ -58,7 +58,7 @@ static void verify_ioctl_loop(unsigned int n)
 	if (TST_RET == 0) {
 		tst_res(TFAIL, "Set block size succeed unexpectedly");
 		if (tcases[n].ioctl_flag == LOOP_CONFIGURE) {
-			tst_detach_device_by_fd(dev_path, dev_fd);
+			tst_detach_device_by_fd(dev_path, &dev_fd);
 			dev_fd = SAFE_OPEN(dev_path, O_RDWR);
 		}
 		return;
@@ -88,7 +88,7 @@ static void run(unsigned int n)
 		return;
 	}
 	if (attach_flag) {
-		tst_detach_device_by_fd(dev_path, dev_fd);
+		tst_detach_device_by_fd(dev_path, &dev_fd);
 		dev_fd = SAFE_OPEN(dev_path, O_RDWR);
 		attach_flag = 0;
 	}
diff --git a/testcases/kernel/syscalls/ioctl/ioctl_loop07.c b/testcases/kernel/syscalls/ioctl/ioctl_loop07.c
index be136fe0d..0e05b2021 100644
--- a/testcases/kernel/syscalls/ioctl/ioctl_loop07.c
+++ b/testcases/kernel/syscalls/ioctl/ioctl_loop07.c
@@ -70,7 +70,7 @@ static void verify_ioctl_loop(unsigned int n)
 				loopinfoget.lo_sizelimit, tc->set_sizelimit);
 	/*Reset*/
 	if (tc->ioctl_flag == LOOP_CONFIGURE) {
-		tst_detach_device_by_fd(dev_path, dev_fd);
+		tst_detach_device_by_fd(dev_path, &dev_fd);
 		dev_fd = SAFE_OPEN(dev_path, O_RDWR);
 	} else {
 		loopinfo.lo_sizelimit = 0;
@@ -99,7 +99,7 @@ static void run(unsigned int n)
 		return;
 	}
 	if (attach_flag) {
-		tst_detach_device_by_fd(dev_path, dev_fd);
+		tst_detach_device_by_fd(dev_path, &dev_fd);
 		dev_fd = SAFE_OPEN(dev_path, O_RDWR);
 		attach_flag = 0;
 	}
-- 
2.49.1



More information about the ltp mailing list