[LTP] [PATCH] save_restore: Check whether path is writable

Martin Doucha mdoucha@suse.cz
Fri Oct 21 17:57:40 CEST 2022


Tests using the .save_restore functionality currently cannot run
without root privileges at all because the test will write
into the path at least at the end and trigger error, even when
the config paths are flagged as optional. Check whether .save_restore
paths are writable and handle negative result the same way as if
the path does not exist.

Signed-off-by: Martin Doucha <mdoucha@suse.cz>
---

This is the first part of sysfile handling fixes to allow running some
tests without root privileges again. I think this is a good enough solution
for the save_restore part but we should discuss a few open questions first:

1) Is it OK to fail early during sysfile save when the test would otherwise
   run fine but throw TWARN at the end because the sysfile is read-only?
2) Should the '?' flag skip read-only files as if they don't exist?
   Alternatively, we could still let the '?' flag fail trying to write
   into read-only sysfiles and instead introduce a new flag for cases where
   read-only file should be skipped.

 doc/c-test-api.txt | 11 +++++------
 lib/tst_sys_conf.c | 32 ++++++++++++++++++++++----------
 2 files changed, 27 insertions(+), 16 deletions(-)

diff --git a/doc/c-test-api.txt b/doc/c-test-api.txt
index 64ee3397f..0f36b5a67 100644
--- a/doc/c-test-api.txt
+++ b/doc/c-test-api.txt
@@ -1601,13 +1601,12 @@ If non-NULL value is passed it is written to the respective file at
 the beginning of the test. Only the first line of a specified file
 is saved and restored.
 
-Pathnames can be optionally prefixed to specify how strictly (during
-'store') are handled errors:
+Pathnames can be optionally prefixed to specify how to handle missing or
+read-only files:
 
-* (no prefix) - test ends with 'TCONF', if file doesn't exist
-* '?'         - test prints info message and continues,
-                if file doesn't exist or open/read fails
-* '!'         - test ends with 'TBROK', if file doesn't exist
+* (no prefix) - test ends with 'TCONF'
+* '?'         - test prints info message and continues, even on read error
+* '!'         - test ends with 'TBROK'
 
 'restore' is always strict and will TWARN if it encounters any error.
 
diff --git a/lib/tst_sys_conf.c b/lib/tst_sys_conf.c
index 003698825..1e381a249 100644
--- a/lib/tst_sys_conf.c
+++ b/lib/tst_sys_conf.c
@@ -20,6 +20,22 @@ struct tst_sys_conf {
 
 static struct tst_sys_conf *save_restore_data;
 
+static void print_access_error(char flag, const char *err, const char *path)
+{
+	switch (flag) {
+	case '?':
+		tst_res(TINFO, "%s: '%s'", err, path);
+		break;
+
+	case '!':
+		tst_brk(TBROK|TERRNO, "%s: '%s'", err, path);
+		break;
+
+	default:
+		tst_brk(TCONF|TERRNO, "%s: '%s'", err, path);
+	}
+}
+
 void tst_sys_conf_dump(void)
 {
 	struct tst_sys_conf *i;
@@ -59,16 +75,12 @@ int tst_sys_conf_save(const char *path)
 		path++;
 
 	if (access(path, F_OK) != 0) {
-		switch (flag) {
-		case '?':
-			tst_res(TINFO, "Path not found: '%s'", path);
-			break;
-		case '!':
-			tst_brk(TBROK|TERRNO, "Path not found: '%s'", path);
-			break;
-		default:
-			tst_brk(TCONF|TERRNO, "Path not found: '%s'", path);
-		}
+		print_access_error(flag, "Path not found", path);
+		return 1;
+	}
+
+	if (access(path, W_OK) != 0) {
+		print_access_error(flag, "Path is not writable", path);
 		return 1;
 	}
 
-- 
2.37.3



More information about the ltp mailing list