All of lore.kernel.org
 help / color / mirror / Atom feed
* [LTP] [PATCH v2 0/6] add open/openat + O_TMPFILE tests
@ 2016-01-28 12:28 Alexey Kodanev
  2016-01-28 12:28 ` [LTP] [PATCH v2 1/6] lib/tst_dir_is_empty: add a library function Alexey Kodanev
                   ` (5 more replies)
  0 siblings, 6 replies; 10+ messages in thread
From: Alexey Kodanev @ 2016-01-28 12:28 UTC (permalink / raw)
  To: ltp

v2:
* move dir_not_empty() -> tst_dir_is_empty() to a library,
* add SAFE_LINKAT, SAFE_READLINK macros,
* move O_TMPFILE definition to lapi/fcntl.h
* use relative path for test_dir,
* enable len_strict in SAFE_WRITE,
* set constant buffer size.

Alexey Kodanev (6):
  lib/tst_dir_is_empty: add a library function
  include/lapi/fcntl.h: add O_TMPFILE definition
  lib/safe_macros: add linkat()
  lib/safe_macros: add readlink()
  kernel/syscalls: add new test with 'open() + O_TMPFILE'
  kernel/syscalls/open14: openat03: add new test-cases

 include/lapi/fcntl.h                        |    4 +
 include/safe_macros.h                       |   13 ++
 include/test.h                              |    8 +
 lib/safe_macros.c                           |   35 ++++
 lib/tst_dir_is_empty.c                      |   49 +++++
 runtest/syscalls                            |    2 +
 testcases/kernel/syscalls/.gitignore        |    2 +
 testcases/kernel/syscalls/open/open14.c     |  253 +++++++++++++++++++++++++++
 testcases/kernel/syscalls/openat/openat03.c |  252 ++++++++++++++++++++++++++
 9 files changed, 618 insertions(+), 0 deletions(-)
 create mode 100644 lib/tst_dir_is_empty.c
 create mode 100644 testcases/kernel/syscalls/open/open14.c
 create mode 100644 testcases/kernel/syscalls/openat/openat03.c


^ permalink raw reply	[flat|nested] 10+ messages in thread

* [LTP] [PATCH v2 1/6] lib/tst_dir_is_empty: add a library function
  2016-01-28 12:28 [LTP] [PATCH v2 0/6] add open/openat + O_TMPFILE tests Alexey Kodanev
@ 2016-01-28 12:28 ` Alexey Kodanev
  2016-01-28 12:28 ` [LTP] [PATCH v2 2/6] include/lapi/fcntl.h: add O_TMPFILE definition Alexey Kodanev
                   ` (4 subsequent siblings)
  5 siblings, 0 replies; 10+ messages in thread
From: Alexey Kodanev @ 2016-01-28 12:28 UTC (permalink / raw)
  To: ltp

Checks if a given directory is empty.

Signed-off-by: Alexey Kodanev <alexey.kodanev@oracle.com>
---
 include/test.h         |    8 +++++++
 lib/tst_dir_is_empty.c |   49 ++++++++++++++++++++++++++++++++++++++++++++++++
 2 files changed, 57 insertions(+), 0 deletions(-)
 create mode 100644 lib/tst_dir_is_empty.c

diff --git a/include/test.h b/include/test.h
index fc07dae..c364b75 100644
--- a/include/test.h
+++ b/include/test.h
@@ -441,6 +441,14 @@ int tst_fs_fill_hardlinks(void (*cleanup) (void), const char *dir);
 int tst_fs_fill_subdirs(void (*cleanup) (void), const char *dir);
 
 /*
+ * lib/tst_dir_is_empty.c
+ *
+ * Checks if a given directory contains any entities,
+ * returns 1 if directory is empty, 0 otherwise
+ */
+int tst_dir_is_empty(void (*cleanup) (void), const char *name, int verbose);
+
+/*
  * lib/tst_pid.c
  *
  * Get a pid value not used by the OS
diff --git a/lib/tst_dir_is_empty.c b/lib/tst_dir_is_empty.c
new file mode 100644
index 0000000..75df50d
--- /dev/null
+++ b/lib/tst_dir_is_empty.c
@@ -0,0 +1,49 @@
+/*
+ * Copyright (c) 2016 Oracle and/or its affiliates. All Rights Reserved.
+ *
+ * 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, see <http://www.gnu.org/licenses/>.
+ *
+ * Author: Alexey Kodanev <alexey.kodanev@oracle.com>
+ *
+ */
+
+#include <string.h>
+#include <sys/types.h>
+#include <dirent.h>
+
+#include "test.h"
+#include "safe_macros.h"
+
+int tst_dir_is_empty(void (cleanup_fn)(void), const char *name, int verbose)
+{
+	struct dirent *entry;
+	DIR *dir = SAFE_OPENDIR(cleanup_fn, name);
+	int ret = 1;
+
+	while ((entry = SAFE_READDIR(cleanup_fn, dir)) != NULL) {
+		const char *file = entry->d_name;
+
+		if (!strcmp(file, "..") || !strcmp(file, "."))
+			continue;
+
+		if (verbose)
+			tst_resm(TINFO, "found a file: %s", file);
+		ret = 0;
+		break;
+	}
+
+	SAFE_CLOSEDIR(cleanup_fn, dir);
+
+	return ret;
+}
-- 
1.7.1


^ permalink raw reply related	[flat|nested] 10+ messages in thread

* [LTP] [PATCH v2 2/6] include/lapi/fcntl.h: add O_TMPFILE definition
  2016-01-28 12:28 [LTP] [PATCH v2 0/6] add open/openat + O_TMPFILE tests Alexey Kodanev
  2016-01-28 12:28 ` [LTP] [PATCH v2 1/6] lib/tst_dir_is_empty: add a library function Alexey Kodanev
@ 2016-01-28 12:28 ` Alexey Kodanev
  2016-01-28 12:28 ` [LTP] [PATCH v2 3/6] lib/safe_macros: add linkat() Alexey Kodanev
                   ` (3 subsequent siblings)
  5 siblings, 0 replies; 10+ messages in thread
From: Alexey Kodanev @ 2016-01-28 12:28 UTC (permalink / raw)
  To: ltp

Signed-off-by: Alexey Kodanev <alexey.kodanev@oracle.com>
---
 include/lapi/fcntl.h |    4 ++++
 1 files changed, 4 insertions(+), 0 deletions(-)

diff --git a/include/lapi/fcntl.h b/include/lapi/fcntl.h
index d0bb713..1ea3fb4 100644
--- a/include/lapi/fcntl.h
+++ b/include/lapi/fcntl.h
@@ -23,6 +23,10 @@
 # define O_CLOEXEC 02000000
 #endif
 
+#ifndef O_TMPFILE
+# define O_TMPFILE (020000000 | O_DIRECTORY)
+#endif
+
 #ifndef F_DUPFD_CLOEXEC
 # define F_DUPFD_CLOEXEC 1030
 #endif
-- 
1.7.1


^ permalink raw reply related	[flat|nested] 10+ messages in thread

* [LTP] [PATCH v2 3/6] lib/safe_macros: add linkat()
  2016-01-28 12:28 [LTP] [PATCH v2 0/6] add open/openat + O_TMPFILE tests Alexey Kodanev
  2016-01-28 12:28 ` [LTP] [PATCH v2 1/6] lib/tst_dir_is_empty: add a library function Alexey Kodanev
  2016-01-28 12:28 ` [LTP] [PATCH v2 2/6] include/lapi/fcntl.h: add O_TMPFILE definition Alexey Kodanev
@ 2016-01-28 12:28 ` Alexey Kodanev
  2016-01-28 12:28 ` [LTP] [PATCH v2 4/6] lib/safe_macros: add readlink() Alexey Kodanev
                   ` (2 subsequent siblings)
  5 siblings, 0 replies; 10+ messages in thread
From: Alexey Kodanev @ 2016-01-28 12:28 UTC (permalink / raw)
  To: ltp

Signed-off-by: Alexey Kodanev <alexey.kodanev@oracle.com>
---
 include/safe_macros.h |    7 +++++++
 lib/safe_macros.c     |   18 ++++++++++++++++++
 2 files changed, 25 insertions(+), 0 deletions(-)

diff --git a/include/safe_macros.h b/include/safe_macros.h
index ab09699..e4041d4 100644
--- a/include/safe_macros.h
+++ b/include/safe_macros.h
@@ -157,6 +157,13 @@ int	safe_link(const char *file, const int lineno,
 #define SAFE_LINK(cleanup_fn, oldpath, newpath) \
         safe_link(__FILE__, __LINE__, cleanup_fn, (oldpath), (newpath))
 
+int	safe_linkat(const char *file, const int lineno,
+		    void (cleanup_fn)(void), int olddirfd, const char *oldpath,
+		    int newdirfd, const char *newpath, int flags);
+#define SAFE_LINKAT(cleanup_fn, olddirfd, oldpath, newdirfd, newpath, flags) \
+	safe_linkat(__FILE__, __LINE__, cleanup_fn, (olddirfd), (oldpath), \
+		    (newdirfd), (newpath), (flags))
+
 int	safe_symlink(const char *file, const int lineno,
                      void (cleanup_fn)(void), const char *oldpath,
                      const char *newpath);
diff --git a/lib/safe_macros.c b/lib/safe_macros.c
index 173d72f..9fa6ac4 100644
--- a/lib/safe_macros.c
+++ b/lib/safe_macros.c
@@ -391,6 +391,24 @@ int safe_link(const char *file, const int lineno,
 	return rval;
 }
 
+int safe_linkat(const char *file, const int lineno,
+		void (cleanup_fn)(void), int olddirfd, const char *oldpath,
+		int newdirfd, const char *newpath, int flags)
+{
+	int rval;
+
+	rval = linkat(olddirfd, oldpath, newdirfd, newpath, flags);
+
+	if (rval == -1) {
+		tst_brkm(TBROK | TERRNO, cleanup_fn,
+			 "%s:%d: linkat(%d,%s,%d,%s,%d) failed",
+			 file, lineno, olddirfd, oldpath, newdirfd,
+			 newpath, flags);
+	}
+
+	return rval;
+}
+
 int safe_symlink(const char *file, const int lineno,
                  void (cleanup_fn)(void), const char *oldpath,
                  const char *newpath)
-- 
1.7.1


^ permalink raw reply related	[flat|nested] 10+ messages in thread

* [LTP] [PATCH v2 4/6] lib/safe_macros: add readlink()
  2016-01-28 12:28 [LTP] [PATCH v2 0/6] add open/openat + O_TMPFILE tests Alexey Kodanev
                   ` (2 preceding siblings ...)
  2016-01-28 12:28 ` [LTP] [PATCH v2 3/6] lib/safe_macros: add linkat() Alexey Kodanev
@ 2016-01-28 12:28 ` Alexey Kodanev
  2016-01-28 12:28 ` [LTP] [PATCH v2 5/6] kernel/syscalls: add new test with 'open() + O_TMPFILE' Alexey Kodanev
  2016-01-28 12:28 ` [LTP] [PATCH v2 6/6] kernel/syscalls/open14: openat03: add new test-cases Alexey Kodanev
  5 siblings, 0 replies; 10+ messages in thread
From: Alexey Kodanev @ 2016-01-28 12:28 UTC (permalink / raw)
  To: ltp

Signed-off-by: Alexey Kodanev <alexey.kodanev@oracle.com>
---
 include/safe_macros.h |    6 ++++++
 lib/safe_macros.c     |   17 +++++++++++++++++
 2 files changed, 23 insertions(+), 0 deletions(-)

diff --git a/include/safe_macros.h b/include/safe_macros.h
index e4041d4..8545c97 100644
--- a/include/safe_macros.h
+++ b/include/safe_macros.h
@@ -164,6 +164,12 @@ int	safe_linkat(const char *file, const int lineno,
 	safe_linkat(__FILE__, __LINE__, cleanup_fn, (olddirfd), (oldpath), \
 		    (newdirfd), (newpath), (flags))
 
+ssize_t	safe_readlink(const char *file, const int lineno,
+		      void (cleanup_fn)(void), const char *path,
+		      char *buf, size_t bufsize);
+#define SAFE_READLINK(cleanup_fn, path, buf, bufsize) \
+	safe_readlink(__FILE__, __LINE__, cleanup_fn, (path), (buf), (bufsize))
+
 int	safe_symlink(const char *file, const int lineno,
                      void (cleanup_fn)(void), const char *oldpath,
                      const char *newpath);
diff --git a/lib/safe_macros.c b/lib/safe_macros.c
index 9fa6ac4..5a05c84 100644
--- a/lib/safe_macros.c
+++ b/lib/safe_macros.c
@@ -409,6 +409,23 @@ int safe_linkat(const char *file, const int lineno,
 	return rval;
 }
 
+ssize_t safe_readlink(const char *file, const int lineno,
+		  void (cleanup_fn)(void), const char *path,
+		  char *buf, size_t bufsize)
+{
+	ssize_t rval;
+
+	rval = readlink(path, buf, bufsize);
+
+	if (rval == -1) {
+		tst_brkm(TBROK | TERRNO, cleanup_fn,
+			 "%s:%d: readlink(%s,%p,%zu) failed",
+			 file, lineno, path, buf, bufsize);
+	}
+
+	return rval;
+}
+
 int safe_symlink(const char *file, const int lineno,
                  void (cleanup_fn)(void), const char *oldpath,
                  const char *newpath)
-- 
1.7.1


^ permalink raw reply related	[flat|nested] 10+ messages in thread

* [LTP] [PATCH v2 5/6] kernel/syscalls: add new test with 'open() + O_TMPFILE'
  2016-01-28 12:28 [LTP] [PATCH v2 0/6] add open/openat + O_TMPFILE tests Alexey Kodanev
                   ` (3 preceding siblings ...)
  2016-01-28 12:28 ` [LTP] [PATCH v2 4/6] lib/safe_macros: add readlink() Alexey Kodanev
@ 2016-01-28 12:28 ` Alexey Kodanev
  2016-01-28 13:41   ` Cyril Hrubis
  2016-01-28 12:28 ` [LTP] [PATCH v2 6/6] kernel/syscalls/open14: openat03: add new test-cases Alexey Kodanev
  5 siblings, 1 reply; 10+ messages in thread
From: Alexey Kodanev @ 2016-01-28 12:28 UTC (permalink / raw)
  To: ltp

Test does the following steps:
* create an unnamed temporary file in TMP directory,
* write data into it,
* check that file not visible in the filesystem,
* name the file and check that it becomes visible in FS.

'openat() + O_TMPFILE' test repeats the same steps.

Signed-off-by: Alexey Kodanev <alexey.kodanev@oracle.com>
---
 runtest/syscalls                            |    2 +
 testcases/kernel/syscalls/.gitignore        |    2 +
 testcases/kernel/syscalls/open/open14.c     |  120 +++++++++++++++++++++++++++
 testcases/kernel/syscalls/openat/openat03.c |  120 +++++++++++++++++++++++++++
 4 files changed, 244 insertions(+), 0 deletions(-)
 create mode 100644 testcases/kernel/syscalls/open/open14.c
 create mode 100644 testcases/kernel/syscalls/openat/openat03.c

diff --git a/runtest/syscalls b/runtest/syscalls
index 7173f22..3439948 100644
--- a/runtest/syscalls
+++ b/runtest/syscalls
@@ -721,10 +721,12 @@ open10 open10
 open11 open11
 open12 open12
 open13 open13
+open14 open14
 
 #openat test cases
 openat01 openat01
 openat02 openat02
+openat03 openat03
 
 mincore01 mincore01
 mincore02 mincore02
diff --git a/testcases/kernel/syscalls/.gitignore b/testcases/kernel/syscalls/.gitignore
index d5f21ef..6451dc4 100644
--- a/testcases/kernel/syscalls/.gitignore
+++ b/testcases/kernel/syscalls/.gitignore
@@ -624,9 +624,11 @@
 /open/open12
 /open/open12_child
 /open/open13
+/open/open14
 /openat/openat01
 /openat/openat02
 /openat/openat02_child
+/openat/openat03
 /pathconf/pathconf01
 /pause/pause01
 /pause/pause02
diff --git a/testcases/kernel/syscalls/open/open14.c b/testcases/kernel/syscalls/open/open14.c
new file mode 100644
index 0000000..3784cb3
--- /dev/null
+++ b/testcases/kernel/syscalls/open/open14.c
@@ -0,0 +1,120 @@
+/*
+ * Copyright (c) 2015-2016 Oracle and/or its affiliates. All Rights Reserved.
+ *
+ * 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, see <http://www.gnu.org/licenses/>.
+ *
+ * Author: Alexey Kodanev <alexey.kodanev@oracle.com>
+ *
+ */
+
+#define _GNU_SOURCE
+#include <sys/types.h>
+#include <sys/stat.h>
+#include <fcntl.h>
+#include <errno.h>
+
+#include "test.h"
+#include "safe_macros.h"
+#include "lapi/fcntl.h"
+
+char *TCID = "open14";
+int TST_TOTAL = 1;
+static const char *test_dir = ".";
+static const ssize_t size = 1024;
+static char buf[1024];
+static const ssize_t blocks_num = 4;
+static struct stat st;
+
+static void cleanup(void)
+{
+	tst_rmdir();
+}
+
+static void setup(void)
+{
+	tst_tmpdir();
+
+	memset(buf, 1, size);
+}
+
+void test01(void)
+{
+	int fd, i;
+
+	char path[PATH_MAX], tmp[PATH_MAX];
+
+	tst_resm(TINFO, "creating a file with O_TMPFILE flag");
+
+	fd = open(test_dir, O_TMPFILE | O_WRONLY | O_SYNC);
+	if (fd == -1) {
+		if (errno == EISDIR) {
+			tst_brkm(TCONF, cleanup,
+				"O_TMPFILE not supported");
+		}
+		tst_resm(TFAIL | TERRNO, "open() failed");
+		return;
+	}
+
+	tst_resm(TINFO, "writing data to the file");
+	for (i = 0; i < blocks_num; ++i)
+		SAFE_WRITE(cleanup, 1, fd, buf, size);
+
+	SAFE_FSTAT(cleanup, fd, &st);
+	tst_resm(TINFO, "file size is '%zu'", st.st_size);
+
+	if (st.st_size != blocks_num * size) {
+		tst_resm(TFAIL, "not expected size: '%zu' != '%zu'",
+			 st.st_size, blocks_num * size);
+		SAFE_CLOSE(cleanup, fd);
+		return;
+	}
+
+	tst_resm(TINFO, "looking for the file in '%s'", test_dir);
+	if (!tst_dir_is_empty(cleanup, test_dir, 1))
+		tst_brkm(TBROK, cleanup, "found a file, this is not expected");
+	tst_resm(TINFO, "file not found, OK");
+
+	snprintf(path, PATH_MAX,  "/proc/self/fd/%d", fd);
+	SAFE_READLINK(cleanup, path, tmp, PATH_MAX);
+
+	tst_resm(TINFO, "renaming '%s' -> '%s/tmpfile'",
+		 tmp, test_dir);
+	SAFE_LINKAT(cleanup, AT_FDCWD, path, AT_FDCWD, "tmpfile",
+		    AT_SYMLINK_FOLLOW);
+
+	if (tst_dir_is_empty(cleanup, test_dir, 1))
+		tst_brkm(TBROK, cleanup, "file not found");
+
+	SAFE_UNLINK(cleanup, "tmpfile");
+	SAFE_CLOSE(cleanup, fd);
+
+	tst_resm(TPASS, "test succeeded");
+}
+
+int main(int ac, char *av[])
+{
+	int lc;
+
+	tst_parse_opts(ac, av, NULL, NULL);
+
+	setup();
+
+	for (lc = 0; TEST_LOOPING(lc); ++lc) {
+		tst_count = 0;
+		test01();
+	}
+
+	cleanup();
+	tst_exit();
+}
diff --git a/testcases/kernel/syscalls/openat/openat03.c b/testcases/kernel/syscalls/openat/openat03.c
new file mode 100644
index 0000000..3a0c2f1
--- /dev/null
+++ b/testcases/kernel/syscalls/openat/openat03.c
@@ -0,0 +1,120 @@
+/*
+ * Copyright (c) 2015-2016 Oracle and/or its affiliates. All Rights Reserved.
+ *
+ * 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, see <http://www.gnu.org/licenses/>.
+ *
+ * Author: Alexey Kodanev <alexey.kodanev@oracle.com>
+ *
+ */
+
+#define _GNU_SOURCE
+#include <sys/types.h>
+#include <sys/stat.h>
+#include <fcntl.h>
+#include <errno.h>
+
+#include "test.h"
+#include "safe_macros.h"
+#include "lapi/fcntl.h"
+
+char *TCID = "openat03";
+int TST_TOTAL = 1;
+static const char *test_dir = ".";
+static const ssize_t size = 1024;
+static char buf[1024];
+static const ssize_t blocks_num = 4;
+static struct stat st;
+
+static void cleanup(void)
+{
+	tst_rmdir();
+}
+
+static void setup(void)
+{
+	tst_tmpdir();
+
+	memset(buf, 1, size);
+}
+
+void test01(void)
+{
+	int fd, i;
+
+	char path[PATH_MAX], tmp[PATH_MAX];
+
+	tst_resm(TINFO, "creating a file with O_TMPFILE flag");
+
+	fd = openat(AT_FDCWD, test_dir, O_TMPFILE | O_WRONLY | O_SYNC);
+	if (fd == -1) {
+		if (errno == EISDIR) {
+			tst_brkm(TCONF, cleanup,
+				"O_TMPFILE not supported");
+		}
+		tst_resm(TFAIL | TERRNO, "openat() failed");
+		return;
+	}
+
+	tst_resm(TINFO, "writing data to the file");
+	for (i = 0; i < blocks_num; ++i)
+		SAFE_WRITE(cleanup, 1, fd, buf, size);
+
+	SAFE_FSTAT(cleanup, fd, &st);
+	tst_resm(TINFO, "file size is '%zu'", st.st_size);
+
+	if (st.st_size != blocks_num * size) {
+		tst_resm(TFAIL, "not expected size: '%zu' != '%zu'",
+			 st.st_size, blocks_num * size);
+		SAFE_CLOSE(cleanup, fd);
+		return;
+	}
+
+	tst_resm(TINFO, "looking for the file in '%s'", test_dir);
+	if (!tst_dir_is_empty(cleanup, test_dir, 1))
+		tst_brkm(TBROK, cleanup, "found a file, this is not expected");
+	tst_resm(TINFO, "file not found, OK");
+
+	snprintf(path, PATH_MAX,  "/proc/self/fd/%d", fd);
+	SAFE_READLINK(cleanup, path, tmp, PATH_MAX);
+
+	tst_resm(TINFO, "renaming '%s' -> '%s/tmpfile'",
+		 tmp, test_dir);
+	SAFE_LINKAT(cleanup, AT_FDCWD, path, AT_FDCWD, "tmpfile",
+		    AT_SYMLINK_FOLLOW);
+
+	if (tst_dir_is_empty(cleanup, test_dir, 1))
+		tst_brkm(TBROK, cleanup, "file not found");
+
+	SAFE_UNLINK(cleanup, "tmpfile");
+	SAFE_CLOSE(cleanup, fd);
+
+	tst_resm(TPASS, "test succeeded");
+}
+
+int main(int ac, char *av[])
+{
+	int lc;
+
+	tst_parse_opts(ac, av, NULL, NULL);
+
+	setup();
+
+	for (lc = 0; TEST_LOOPING(lc); ++lc) {
+		tst_count = 0;
+		test01();
+	}
+
+	cleanup();
+	tst_exit();
+}
-- 
1.7.1


^ permalink raw reply related	[flat|nested] 10+ messages in thread

* [LTP] [PATCH v2 6/6] kernel/syscalls/open14: openat03: add new test-cases
  2016-01-28 12:28 [LTP] [PATCH v2 0/6] add open/openat + O_TMPFILE tests Alexey Kodanev
                   ` (4 preceding siblings ...)
  2016-01-28 12:28 ` [LTP] [PATCH v2 5/6] kernel/syscalls: add new test with 'open() + O_TMPFILE' Alexey Kodanev
@ 2016-01-28 12:28 ` Alexey Kodanev
  2016-01-28 14:01   ` Cyril Hrubis
  5 siblings, 1 reply; 10+ messages in thread
From: Alexey Kodanev @ 2016-01-28 12:28 UTC (permalink / raw)
  To: ltp

* create multiple directories and related temporary files;

* create multiple directories and link files into them. Check
  that files permissions correspond to the ones specified with
  open()/openat().

Signed-off-by: Alexey Kodanev <alexey.kodanev@oracle.com>
---
 testcases/kernel/syscalls/open/open14.c     |  163 ++++++++++++++++++++++++---
 testcases/kernel/syscalls/openat/openat03.c |  160 ++++++++++++++++++++++++---
 2 files changed, 294 insertions(+), 29 deletions(-)

diff --git a/testcases/kernel/syscalls/open/open14.c b/testcases/kernel/syscalls/open/open14.c
index 3784cb3..37a900a 100644
--- a/testcases/kernel/syscalls/open/open14.c
+++ b/testcases/kernel/syscalls/open/open14.c
@@ -21,6 +21,7 @@
 #define _GNU_SOURCE
 #include <sys/types.h>
 #include <sys/stat.h>
+#include <unistd.h>
 #include <fcntl.h>
 #include <errno.h>
 
@@ -29,7 +30,8 @@
 #include "lapi/fcntl.h"
 
 char *TCID = "open14";
-int TST_TOTAL = 1;
+int TST_TOTAL = 3;
+
 static const char *test_dir = ".";
 static const ssize_t size = 1024;
 static char buf[1024];
@@ -48,27 +50,36 @@ static void setup(void)
 	memset(buf, 1, size);
 }
 
-void test01(void)
+static void create_file(const char *dir_name, int *fd, int mode)
 {
-	int fd, i;
+	*fd = open(dir_name, O_TMPFILE | O_RDWR, mode);
+	if (*fd != -1)
+		return;
 
-	char path[PATH_MAX], tmp[PATH_MAX];
+	if (errno == EISDIR)
+		tst_brkm(TCONF, cleanup, "O_TMPFILE not supported");
 
-	tst_resm(TINFO, "creating a file with O_TMPFILE flag");
+	tst_brkm(TFAIL | TERRNO, cleanup, "open() failed");
+}
 
-	fd = open(test_dir, O_TMPFILE | O_WRONLY | O_SYNC);
-	if (fd == -1) {
-		if (errno == EISDIR) {
-			tst_brkm(TCONF, cleanup,
-				"O_TMPFILE not supported");
-		}
-		tst_resm(TFAIL | TERRNO, "open() failed");
-		return;
-	}
+static void write_file(int fd)
+{
+	int i;
 
-	tst_resm(TINFO, "writing data to the file");
 	for (i = 0; i < blocks_num; ++i)
 		SAFE_WRITE(cleanup, 1, fd, buf, size);
+}
+
+void test01(void)
+{
+	int fd;
+	char path[PATH_MAX], tmp[PATH_MAX];
+
+	tst_resm(TINFO, "creating a file with O_TMPFILE flag");
+	create_file(test_dir, &fd, 0600);
+
+	tst_resm(TINFO, "writing data to the file");
+	write_file(fd);
 
 	SAFE_FSTAT(cleanup, fd, &st);
 	tst_resm(TINFO, "file size is '%zu'", st.st_size);
@@ -102,6 +113,126 @@ void test01(void)
 	tst_resm(TPASS, "test succeeded");
 }
 
+static void read_file(int fd)
+{
+	int i;
+	char tmp[size];
+
+	SAFE_LSEEK(cleanup, fd, 0, SEEK_SET);
+
+	for (i = 0; i < blocks_num; ++i) {
+		SAFE_READ(cleanup, 0, fd, tmp, size);
+		if (strncmp(buf, tmp, size))
+			tst_brkm(TBROK, cleanup, "got unexepected data");
+	}
+}
+
+static void test02(void)
+{
+	const int files_num = 100;
+	int i, fd[files_num];
+	char path[PATH_MAX];
+
+	tst_resm(TINFO, "create files in multiple directories");
+	for (i = 0; i < files_num; ++i) {
+		snprintf(path, PATH_MAX, "tst02_%d", i);
+		SAFE_MKDIR(cleanup, path, 0700);
+		SAFE_CHDIR(cleanup, path);
+		SAFE_GETCWD(cleanup, path, PATH_MAX);
+		create_file(path, fd + i, 0600);
+		write_file(fd[i]);
+	}
+
+	tst_resm(TINFO, "removing test directories");
+	for (i = files_num - 1; i >= 0; --i) {
+		SAFE_CHDIR(cleanup, "../");
+		snprintf(path, PATH_MAX, "tst02_%d", i);
+		SAFE_RMDIR(cleanup, path);
+	}
+
+	tst_resm(TINFO, "writing/reading temporary files");
+	for (i = 0; i < files_num; ++i) {
+		write_file(fd[i]);
+		read_file(fd[i]);
+	}
+
+	tst_resm(TINFO, "closing temporary files");
+	for (i = 0; i < files_num; ++i)
+		SAFE_CLOSE(cleanup, fd[i]);
+
+	tst_resm(TPASS, "test succeeded");
+}
+
+static void link_tmp_file(int fd)
+{
+	char path1[PATH_MAX], path2[PATH_MAX];
+
+	snprintf(path1, PATH_MAX,  "/proc/self/fd/%d", fd);
+	snprintf(path2, PATH_MAX,  "tmpfile_%d", fd);
+
+	SAFE_LINKAT(cleanup, AT_FDCWD, path1, AT_FDCWD, path2,
+		    AT_SYMLINK_FOLLOW);
+}
+
+static const int tst_perm[] = { 0, 07777, 001, 0755, 0644, 0440 };
+
+static void test03(void)
+{
+	const int files_num = 100;
+	int i, fd[files_num];
+	char path[PATH_MAX];
+	struct stat st;
+	unsigned int j;
+	mode_t mask = umask(0);
+
+	umask(mask);
+
+	tst_resm(TINFO, "create multiple directories, link files into them");
+	tst_resm(TINFO, "and check file permissions");
+	for (i = 0, j = 0; i < files_num; ++i) {
+
+		snprintf(path, PATH_MAX, "tst03_%d", i);
+		SAFE_MKDIR(cleanup, path, 0700);
+		SAFE_CHDIR(cleanup, path);
+		SAFE_GETCWD(cleanup, path, PATH_MAX);
+
+		create_file(path, fd + i, tst_perm[j]);
+		write_file(fd[i]);
+		read_file(fd[i]);
+
+		link_tmp_file(fd[i]);
+
+		snprintf(path, PATH_MAX, "tmpfile_%d", fd[i]);
+
+		SAFE_LSTAT(cleanup, path, &st);
+
+		mode_t exp_mode = tst_perm[j] & ~mask;
+
+		if ((st.st_mode & ~S_IFMT) != exp_mode) {
+			tst_brkm(TFAIL, cleanup,
+				"file mode read %o, but expected %o",
+				st.st_mode & ~S_IFMT, exp_mode);
+		}
+
+		if (++j >= ARRAY_SIZE(tst_perm))
+			j = 0;
+	}
+
+	tst_resm(TINFO, "remove files, directories");
+	for (i = files_num - 1; i >= 0; --i) {
+		snprintf(path, PATH_MAX, "tmpfile_%d", fd[i]);
+		SAFE_UNLINK(cleanup, path);
+		SAFE_CLOSE(cleanup, fd[i]);
+
+		SAFE_CHDIR(cleanup, "..");
+
+		snprintf(path, PATH_MAX, "tst03_%d", i);
+		SAFE_RMDIR(cleanup, path);
+	}
+
+	tst_resm(TPASS, "test passed");
+}
+
 int main(int ac, char *av[])
 {
 	int lc;
@@ -113,6 +244,8 @@ int main(int ac, char *av[])
 	for (lc = 0; TEST_LOOPING(lc); ++lc) {
 		tst_count = 0;
 		test01();
+		test02();
+		test03();
 	}
 
 	cleanup();
diff --git a/testcases/kernel/syscalls/openat/openat03.c b/testcases/kernel/syscalls/openat/openat03.c
index 3a0c2f1..743442c 100644
--- a/testcases/kernel/syscalls/openat/openat03.c
+++ b/testcases/kernel/syscalls/openat/openat03.c
@@ -21,6 +21,7 @@
 #define _GNU_SOURCE
 #include <sys/types.h>
 #include <sys/stat.h>
+#include <unistd.h>
 #include <fcntl.h>
 #include <errno.h>
 
@@ -48,27 +49,36 @@ static void setup(void)
 	memset(buf, 1, size);
 }
 
-void test01(void)
+static void create_file(const char *dir_name, int *fd, int mode)
 {
-	int fd, i;
+	*fd = openat(AT_FDCWD, dir_name, O_TMPFILE | O_RDWR, mode);
+	if (*fd != -1)
+		return;
 
-	char path[PATH_MAX], tmp[PATH_MAX];
+	if (errno == EISDIR)
+		tst_brkm(TCONF, cleanup, "O_TMPFILE not supported");
 
-	tst_resm(TINFO, "creating a file with O_TMPFILE flag");
+	tst_brkm(TFAIL | TERRNO, cleanup, "openat() failed");
+}
 
-	fd = openat(AT_FDCWD, test_dir, O_TMPFILE | O_WRONLY | O_SYNC);
-	if (fd == -1) {
-		if (errno == EISDIR) {
-			tst_brkm(TCONF, cleanup,
-				"O_TMPFILE not supported");
-		}
-		tst_resm(TFAIL | TERRNO, "openat() failed");
-		return;
-	}
+static void write_file(int fd)
+{
+	int i;
 
-	tst_resm(TINFO, "writing data to the file");
 	for (i = 0; i < blocks_num; ++i)
 		SAFE_WRITE(cleanup, 1, fd, buf, size);
+}
+
+void test01(void)
+{
+	int fd;
+	char path[PATH_MAX], tmp[PATH_MAX];
+
+	tst_resm(TINFO, "creating a file with O_TMPFILE flag");
+	create_file(test_dir, &fd, 0600);
+
+	tst_resm(TINFO, "writing data to the file");
+	write_file(fd);
 
 	SAFE_FSTAT(cleanup, fd, &st);
 	tst_resm(TINFO, "file size is '%zu'", st.st_size);
@@ -102,6 +112,126 @@ void test01(void)
 	tst_resm(TPASS, "test succeeded");
 }
 
+static void read_file(int fd)
+{
+	int i;
+	char tmp[size];
+
+	SAFE_LSEEK(cleanup, fd, 0, SEEK_SET);
+
+	for (i = 0; i < blocks_num; ++i) {
+		SAFE_READ(cleanup, 0, fd, tmp, size);
+		if (strncmp(buf, tmp, size))
+			tst_brkm(TBROK, cleanup, "got unexepected data");
+	}
+}
+
+static void test02(void)
+{
+	const int files_num = 100;
+	int i, fd[files_num];
+	char path[PATH_MAX];
+
+	tst_resm(TINFO, "create files in multiple directories");
+	for (i = 0; i < files_num; ++i) {
+		snprintf(path, PATH_MAX, "tst02_%d", i);
+		SAFE_MKDIR(cleanup, path, 0700);
+		SAFE_CHDIR(cleanup, path);
+		SAFE_GETCWD(cleanup, path, PATH_MAX);
+		create_file(path, fd + i, 0600);
+		write_file(fd[i]);
+	}
+
+	tst_resm(TINFO, "removing test directories");
+	for (i = files_num - 1; i >= 0; --i) {
+		SAFE_CHDIR(cleanup, "../");
+		snprintf(path, PATH_MAX, "tst02_%d", i);
+		SAFE_RMDIR(cleanup, path);
+	}
+
+	tst_resm(TINFO, "writing/reading temporary files");
+	for (i = 0; i < files_num; ++i) {
+		write_file(fd[i]);
+		read_file(fd[i]);
+	}
+
+	tst_resm(TINFO, "closing temporary files");
+	for (i = 0; i < files_num; ++i)
+		SAFE_CLOSE(cleanup, fd[i]);
+
+	tst_resm(TPASS, "test succeeded");
+}
+
+static void link_tmp_file(int fd)
+{
+	char path1[PATH_MAX], path2[PATH_MAX];
+
+	snprintf(path1, PATH_MAX,  "/proc/self/fd/%d", fd);
+	snprintf(path2, PATH_MAX,  "tmpfile_%d", fd);
+
+	SAFE_LINKAT(cleanup, AT_FDCWD, path1, AT_FDCWD, path2,
+		    AT_SYMLINK_FOLLOW);
+}
+
+static const int tst_perm[] = { 0, 07777, 001, 0755, 0644, 0440 };
+
+static void test03(void)
+{
+	const int files_num = 100;
+	int i, fd[files_num];
+	char path[PATH_MAX];
+	struct stat st;
+	unsigned int j;
+	mode_t mask = umask(0);
+
+	umask(mask);
+
+	tst_resm(TINFO, "create multiple directories, link files into them");
+	tst_resm(TINFO, "and check file permissions");
+	for (i = 0, j = 0; i < files_num; ++i) {
+
+		snprintf(path, PATH_MAX, "tst03_%d", i);
+		SAFE_MKDIR(cleanup, path, 0700);
+		SAFE_CHDIR(cleanup, path);
+		SAFE_GETCWD(cleanup, path, PATH_MAX);
+
+		create_file(path, fd + i, tst_perm[j]);
+		write_file(fd[i]);
+		read_file(fd[i]);
+
+		link_tmp_file(fd[i]);
+
+		snprintf(path, PATH_MAX, "tmpfile_%d", fd[i]);
+
+		SAFE_LSTAT(cleanup, path, &st);
+
+		mode_t exp_mode = tst_perm[j] & ~mask;
+
+		if ((st.st_mode & ~S_IFMT) != exp_mode) {
+			tst_brkm(TFAIL, cleanup,
+				"file mode read %o, but expected %o",
+				st.st_mode & ~S_IFMT, exp_mode);
+		}
+
+		if (++j >= ARRAY_SIZE(tst_perm))
+			j = 0;
+	}
+
+	tst_resm(TINFO, "remove files, directories");
+	for (i = files_num - 1; i >= 0; --i) {
+		snprintf(path, PATH_MAX, "tmpfile_%d", fd[i]);
+		SAFE_UNLINK(cleanup, path);
+		SAFE_CLOSE(cleanup, fd[i]);
+
+		SAFE_CHDIR(cleanup, "..");
+
+		snprintf(path, PATH_MAX, "tst03_%d", i);
+		SAFE_RMDIR(cleanup, path);
+	}
+
+	tst_resm(TPASS, "test passed");
+}
+
 int main(int ac, char *av[])
 {
 	int lc;
@@ -113,6 +243,8 @@ int main(int ac, char *av[])
 	for (lc = 0; TEST_LOOPING(lc); ++lc) {
 		tst_count = 0;
 		test01();
+		test02();
+		test03();
 	}
 
 	cleanup();
-- 
1.7.1


^ permalink raw reply related	[flat|nested] 10+ messages in thread

* [LTP] [PATCH v2 5/6] kernel/syscalls: add new test with 'open() + O_TMPFILE'
  2016-01-28 12:28 ` [LTP] [PATCH v2 5/6] kernel/syscalls: add new test with 'open() + O_TMPFILE' Alexey Kodanev
@ 2016-01-28 13:41   ` Cyril Hrubis
  0 siblings, 0 replies; 10+ messages in thread
From: Cyril Hrubis @ 2016-01-28 13:41 UTC (permalink / raw)
  To: ltp

Hi!
> +#define _GNU_SOURCE
> +#include <sys/types.h>
> +#include <sys/stat.h>
> +#include <fcntl.h>
> +#include <errno.h>
> +
> +#include "test.h"
> +#include "safe_macros.h"
> +#include "lapi/fcntl.h"
> +
> +char *TCID = "open14";
> +int TST_TOTAL = 1;
> +static const char *test_dir = ".";
> +static const ssize_t size = 1024;
> +static char buf[1024];
> +static const ssize_t blocks_num = 4;
> +static struct stat st;
> +
> +static void cleanup(void)
> +{
> +	tst_rmdir();
> +}
> +
> +static void setup(void)
> +{
> +	tst_tmpdir();
> +
> +	memset(buf, 1, size);
                       ^
		       sizeof(buf)
> +}
> +
> +void test01(void)
> +{
> +	int fd, i;
> +
> +	char path[PATH_MAX], tmp[PATH_MAX];
> +
> +	tst_resm(TINFO, "creating a file with O_TMPFILE flag");
> +
> +	fd = open(test_dir, O_TMPFILE | O_WRONLY | O_SYNC);
> +	if (fd == -1) {
> +		if (errno == EISDIR) {
> +			tst_brkm(TCONF, cleanup,
> +				"O_TMPFILE not supported");
> +		}
> +		tst_resm(TFAIL | TERRNO, "open() failed");
> +		return;
> +	}
> +
> +	tst_resm(TINFO, "writing data to the file");
> +	for (i = 0; i < blocks_num; ++i)
> +		SAFE_WRITE(cleanup, 1, fd, buf, size);
> +
> +	SAFE_FSTAT(cleanup, fd, &st);
> +	tst_resm(TINFO, "file size is '%zu'", st.st_size);
> +
> +	if (st.st_size != blocks_num * size) {
> +		tst_resm(TFAIL, "not expected size: '%zu' != '%zu'",
> +			 st.st_size, blocks_num * size);
> +		SAFE_CLOSE(cleanup, fd);
> +		return;
> +	}
> +
> +	tst_resm(TINFO, "looking for the file in '%s'", test_dir);
> +	if (!tst_dir_is_empty(cleanup, test_dir, 1))
> +		tst_brkm(TBROK, cleanup, "found a file, this is not expected");
                          ^
                         Isn't this TFAIL rather than TBROK?

I see the difference as:

If some of the preparation steps has failed -> TBROK
If some test assertion fails -> TFAIL

> +	tst_resm(TINFO, "file not found, OK");
> +
> +	snprintf(path, PATH_MAX,  "/proc/self/fd/%d", fd);
> +	SAFE_READLINK(cleanup, path, tmp, PATH_MAX);
> +
> +	tst_resm(TINFO, "renaming '%s' -> '%s/tmpfile'",
> +		 tmp, test_dir);
> +	SAFE_LINKAT(cleanup, AT_FDCWD, path, AT_FDCWD, "tmpfile",
> +		    AT_SYMLINK_FOLLOW);
> +
> +	if (tst_dir_is_empty(cleanup, test_dir, 1))
> +		tst_brkm(TBROK, cleanup, "file not found");

Here as well.

> +	SAFE_UNLINK(cleanup, "tmpfile");
> +	SAFE_CLOSE(cleanup, fd);
> +
> +	tst_resm(TPASS, "test succeeded");
> +}
> +
> +int main(int ac, char *av[])
> +{
> +	int lc;
> +
> +	tst_parse_opts(ac, av, NULL, NULL);
> +
> +	setup();
> +
> +	for (lc = 0; TEST_LOOPING(lc); ++lc) {
> +		tst_count = 0;
> +		test01();
> +	}
> +
> +	cleanup();
> +	tst_exit();
> +}
> diff --git a/testcases/kernel/syscalls/openat/openat03.c b/testcases/kernel/syscalls/openat/openat03.c
> new file mode 100644
> index 0000000..3a0c2f1
> --- /dev/null
> +++ b/testcases/kernel/syscalls/openat/openat03.c
> @@ -0,0 +1,120 @@
> +/*
> + * Copyright (c) 2015-2016 Oracle and/or its affiliates. All Rights Reserved.
> + *
> + * 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, see <http://www.gnu.org/licenses/>.
> + *
> + * Author: Alexey Kodanev <alexey.kodanev@oracle.com>
> + *
> + */
> +
> +#define _GNU_SOURCE
> +#include <sys/types.h>
> +#include <sys/stat.h>
> +#include <fcntl.h>
> +#include <errno.h>
> +
> +#include "test.h"
> +#include "safe_macros.h"
> +#include "lapi/fcntl.h"
> +
> +char *TCID = "openat03";
> +int TST_TOTAL = 1;
> +static const char *test_dir = ".";
> +static const ssize_t size = 1024;
> +static char buf[1024];
> +static const ssize_t blocks_num = 4;
> +static struct stat st;
> +
> +static void cleanup(void)
> +{
> +	tst_rmdir();
> +}
> +
> +static void setup(void)
> +{
> +	tst_tmpdir();
> +
> +	memset(buf, 1, size);

Here as well.

> +}
> +
> +void test01(void)
> +{
> +	int fd, i;
> +
> +	char path[PATH_MAX], tmp[PATH_MAX];
> +
> +	tst_resm(TINFO, "creating a file with O_TMPFILE flag");
> +
> +	fd = openat(AT_FDCWD, test_dir, O_TMPFILE | O_WRONLY | O_SYNC);
> +	if (fd == -1) {
> +		if (errno == EISDIR) {
> +			tst_brkm(TCONF, cleanup,
> +				"O_TMPFILE not supported");
> +		}
> +		tst_resm(TFAIL | TERRNO, "openat() failed");
> +		return;
> +	}
> +
> +	tst_resm(TINFO, "writing data to the file");
> +	for (i = 0; i < blocks_num; ++i)
> +		SAFE_WRITE(cleanup, 1, fd, buf, size);
> +
> +	SAFE_FSTAT(cleanup, fd, &st);
> +	tst_resm(TINFO, "file size is '%zu'", st.st_size);
> +
> +	if (st.st_size != blocks_num * size) {
> +		tst_resm(TFAIL, "not expected size: '%zu' != '%zu'",
> +			 st.st_size, blocks_num * size);
> +		SAFE_CLOSE(cleanup, fd);
> +		return;
> +	}
> +
> +	tst_resm(TINFO, "looking for the file in '%s'", test_dir);
> +	if (!tst_dir_is_empty(cleanup, test_dir, 1))
> +		tst_brkm(TBROK, cleanup, "found a file, this is not expected");

And here.

> +	tst_resm(TINFO, "file not found, OK");
> +
> +	snprintf(path, PATH_MAX,  "/proc/self/fd/%d", fd);
> +	SAFE_READLINK(cleanup, path, tmp, PATH_MAX);
> +
> +	tst_resm(TINFO, "renaming '%s' -> '%s/tmpfile'",
> +		 tmp, test_dir);
> +	SAFE_LINKAT(cleanup, AT_FDCWD, path, AT_FDCWD, "tmpfile",
> +		    AT_SYMLINK_FOLLOW);
> +
> +	if (tst_dir_is_empty(cleanup, test_dir, 1))
> +		tst_brkm(TBROK, cleanup, "file not found");

And here.

> +	SAFE_UNLINK(cleanup, "tmpfile");
> +	SAFE_CLOSE(cleanup, fd);
> +
> +	tst_resm(TPASS, "test succeeded");
> +}
> +
> +int main(int ac, char *av[])
> +{
> +	int lc;
> +
> +	tst_parse_opts(ac, av, NULL, NULL);
> +
> +	setup();
> +
> +	for (lc = 0; TEST_LOOPING(lc); ++lc) {
> +		tst_count = 0;
> +		test01();
> +	}
> +
> +	cleanup();
> +	tst_exit();
> +}
> -- 
> 1.7.1
> 
> 
> -- 
> Mailing list info: http://lists.linux.it/listinfo/ltp

-- 
Cyril Hrubis
chrubis@suse.cz

^ permalink raw reply	[flat|nested] 10+ messages in thread

* [LTP] [PATCH v2 6/6] kernel/syscalls/open14: openat03: add new test-cases
  2016-01-28 12:28 ` [LTP] [PATCH v2 6/6] kernel/syscalls/open14: openat03: add new test-cases Alexey Kodanev
@ 2016-01-28 14:01   ` Cyril Hrubis
  2016-01-28 15:28     ` Alexey Kodanev
  0 siblings, 1 reply; 10+ messages in thread
From: Cyril Hrubis @ 2016-01-28 14:01 UTC (permalink / raw)
  To: ltp

Hi!
> * create multiple directories and related temporary files;
> 
> * create multiple directories and link files into them. Check
>   that files permissions correspond to the ones specified with
>   open()/openat().

I would say that for newly added code it makes more sense to add new
files in one patch. It's kind of strange to add more code to files you
have added in previous one.

> Signed-off-by: Alexey Kodanev <alexey.kodanev@oracle.com>
> ---
>  testcases/kernel/syscalls/open/open14.c     |  163 ++++++++++++++++++++++++---
>  testcases/kernel/syscalls/openat/openat03.c |  160 ++++++++++++++++++++++++---
>  2 files changed, 294 insertions(+), 29 deletions(-)
> 
> diff --git a/testcases/kernel/syscalls/open/open14.c b/testcases/kernel/syscalls/open/open14.c
> index 3784cb3..37a900a 100644
> --- a/testcases/kernel/syscalls/open/open14.c
> +++ b/testcases/kernel/syscalls/open/open14.c
> @@ -21,6 +21,7 @@
>  #define _GNU_SOURCE
>  #include <sys/types.h>
>  #include <sys/stat.h>
> +#include <unistd.h>
>  #include <fcntl.h>
>  #include <errno.h>
>  
> @@ -29,7 +30,8 @@
>  #include "lapi/fcntl.h"
>  
>  char *TCID = "open14";
> -int TST_TOTAL = 1;
> +int TST_TOTAL = 3;
> +
>  static const char *test_dir = ".";
>  static const ssize_t size = 1024;
>  static char buf[1024];
> @@ -48,27 +50,36 @@ static void setup(void)
>  	memset(buf, 1, size);
>  }
>  
> -void test01(void)
> +static void create_file(const char *dir_name, int *fd, int mode)
>  {
> -	int fd, i;
> +	*fd = open(dir_name, O_TMPFILE | O_RDWR, mode);
> +	if (*fd != -1)
> +		return;
>  
> -	char path[PATH_MAX], tmp[PATH_MAX];
> +	if (errno == EISDIR)
> +		tst_brkm(TCONF, cleanup, "O_TMPFILE not supported");
>  
> -	tst_resm(TINFO, "creating a file with O_TMPFILE flag");
> +	tst_brkm(TFAIL | TERRNO, cleanup, "open() failed");
> +}

Maybe it would be easier to try to open dummy tmpfile in setup and check
for EISDIR there. Then we can just do SAFE_OPEN() in the rest of the
code.

> -	fd = open(test_dir, O_TMPFILE | O_WRONLY | O_SYNC);
> -	if (fd == -1) {
> -		if (errno == EISDIR) {
> -			tst_brkm(TCONF, cleanup,
> -				"O_TMPFILE not supported");
> -		}
> -		tst_resm(TFAIL | TERRNO, "open() failed");
> -		return;
> -	}
> +static void write_file(int fd)
> +{
> +	int i;
>  
> -	tst_resm(TINFO, "writing data to the file");
>  	for (i = 0; i < blocks_num; ++i)
>  		SAFE_WRITE(cleanup, 1, fd, buf, size);
> +}
> +
> +void test01(void)
> +{
> +	int fd;
> +	char path[PATH_MAX], tmp[PATH_MAX];
> +
> +	tst_resm(TINFO, "creating a file with O_TMPFILE flag");
> +	create_file(test_dir, &fd, 0600);
> +
> +	tst_resm(TINFO, "writing data to the file");
> +	write_file(fd);
>  
>  	SAFE_FSTAT(cleanup, fd, &st);
>  	tst_resm(TINFO, "file size is '%zu'", st.st_size);
> @@ -102,6 +113,126 @@ void test01(void)
>  	tst_resm(TPASS, "test succeeded");
>  }
>  
> +static void read_file(int fd)
> +{
> +	int i;
> +	char tmp[size];
> +
> +	SAFE_LSEEK(cleanup, fd, 0, SEEK_SET);
> +
> +	for (i = 0; i < blocks_num; ++i) {
> +		SAFE_READ(cleanup, 0, fd, tmp, size);
> +		if (strncmp(buf, tmp, size))\

Using memcmp() here would be a bit cleaner solution.

> +			tst_brkm(TBROK, cleanup, "got unexepected data");

Here again, I would say that this should rather be TFAIL.

> +	}
> +}
> +
> +static void test02(void)
> +{
> +	const int files_num = 100;
> +	int i, fd[files_num];
> +	char path[PATH_MAX];
> +
> +	tst_resm(TINFO, "create files in multiple directories");
> +	for (i = 0; i < files_num; ++i) {
> +		snprintf(path, PATH_MAX, "tst02_%d", i);
> +		SAFE_MKDIR(cleanup, path, 0700);
> +		SAFE_CHDIR(cleanup, path);
> +		SAFE_GETCWD(cleanup, path, PATH_MAX);
> +		create_file(path, fd + i, 0600);

We can do just create_file(".", fd + 1, 0600) here as well.

> +		write_file(fd[i]);
> +	}
> +
> +	tst_resm(TINFO, "removing test directories");
> +	for (i = files_num - 1; i >= 0; --i) {
> +		SAFE_CHDIR(cleanup, "../");
> +		snprintf(path, PATH_MAX, "tst02_%d", i);
> +		SAFE_RMDIR(cleanup, path);
> +	}
> +
> +	tst_resm(TINFO, "writing/reading temporary files");
> +	for (i = 0; i < files_num; ++i) {
> +		write_file(fd[i]);
> +		read_file(fd[i]);
> +	}
> +
> +	tst_resm(TINFO, "closing temporary files");
> +	for (i = 0; i < files_num; ++i)
> +		SAFE_CLOSE(cleanup, fd[i]);
> +
> +	tst_resm(TPASS, "test succeeded");
> +}
>
> +static void link_tmp_file(int fd)
> +{
> +	char path1[PATH_MAX], path2[PATH_MAX];
> +
> +	snprintf(path1, PATH_MAX,  "/proc/self/fd/%d", fd);
> +	snprintf(path2, PATH_MAX,  "tmpfile_%d", fd);
> +
> +	SAFE_LINKAT(cleanup, AT_FDCWD, path1, AT_FDCWD, path2,
> +		    AT_SYMLINK_FOLLOW);
> +}
> +
> +static const int tst_perm[] = { 0, 07777, 001, 0755, 0644, 0440 };
> +
> +static void test03(void)
> +{
> +	const int files_num = 100;
> +	int i, fd[files_num];
> +	char path[PATH_MAX];
> +	struct stat st;
> +	unsigned int j;
> +	mode_t mask = umask(0);
> +
> +	umask(mask);
> +
> +	tst_resm(TINFO, "create multiple directories, link files into them");
> +	tst_resm(TINFO, "and check file permissions");
> +	for (i = 0, j = 0; i < files_num; ++i) {
> +
> +		snprintf(path, PATH_MAX, "tst03_%d", i);
> +		SAFE_MKDIR(cleanup, path, 0700);
> +		SAFE_CHDIR(cleanup, path);
> +		SAFE_GETCWD(cleanup, path, PATH_MAX);
> +
> +		create_file(path, fd + i, tst_perm[j]);

And here as well.

> +		write_file(fd[i]);
> +		read_file(fd[i]);
> +
> +		link_tmp_file(fd[i]);
> +
> +		snprintf(path, PATH_MAX, "tmpfile_%d", fd[i]);
> +
> +		SAFE_LSTAT(cleanup, path, &st);
> +
> +		mode_t exp_mode = tst_perm[j] & ~mask;
> +
> +		if ((st.st_mode & ~S_IFMT) != exp_mode) {
> +			tst_brkm(TFAIL, cleanup,
> +				"file mode read %o, but expected %o",
> +				st.st_mode & ~S_IFMT, exp_mode);
> +		}
> +
> +		if (++j >= ARRAY_SIZE(tst_perm))
> +			j = 0;
> +	}
> +
> +	tst_resm(TINFO, "remove files, directories");
> +	for (i = files_num - 1; i >= 0; --i) {
> +		snprintf(path, PATH_MAX, "tmpfile_%d", fd[i]);
> +		SAFE_UNLINK(cleanup, path);
> +		SAFE_CLOSE(cleanup, fd[i]);
> +
> +		SAFE_CHDIR(cleanup, "..");
> +
> +		snprintf(path, PATH_MAX, "tst03_%d", i);
> +		SAFE_RMDIR(cleanup, path);
> +	}
> +
> +	tst_resm(TPASS, "test passed");

We should be a bit more informative here.

What about "permission tests passed"

And for test02 we should say somethign as: "unlink tests passed"

> +}
> +
>  int main(int ac, char *av[])
>  {
>  	int lc;
> @@ -113,6 +244,8 @@ int main(int ac, char *av[])
>  	for (lc = 0; TEST_LOOPING(lc); ++lc) {
>  		tst_count = 0;
>  		test01();
> +		test02();
> +		test03();
>  	}
>  
>  	cleanup();
> diff --git a/testcases/kernel/syscalls/openat/openat03.c b/testcases/kernel/syscalls/openat/openat03.c
> index 3a0c2f1..743442c 100644
> --- a/testcases/kernel/syscalls/openat/openat03.c
> +++ b/testcases/kernel/syscalls/openat/openat03.c

The same applies for openat03.

The rest of the patchset looks good.

-- 
Cyril Hrubis
chrubis@suse.cz

^ permalink raw reply	[flat|nested] 10+ messages in thread

* [LTP] [PATCH v2 6/6] kernel/syscalls/open14: openat03: add new test-cases
  2016-01-28 14:01   ` Cyril Hrubis
@ 2016-01-28 15:28     ` Alexey Kodanev
  0 siblings, 0 replies; 10+ messages in thread
From: Alexey Kodanev @ 2016-01-28 15:28 UTC (permalink / raw)
  To: ltp

Hi,
On 01/28/2016 05:01 PM, Cyril Hrubis wrote:
> Hi!
>> * create multiple directories and related temporary files;
>>
>> * create multiple directories and link files into them. Check
>>    that files permissions correspond to the ones specified with
>>    open()/openat().
> I would say that for newly added code it makes more sense to add new
> files in one patch. It's kind of strange to add more code to files you
> have added in previous one.

The previous patch was sent in the end of Dec, the last one quite recently.
I thought it would be easier to notice that the last one is included here
right now. Agree, it looks strange in the one patch set. Will squash it into
the previous.

Thanks,
Alexey


^ permalink raw reply	[flat|nested] 10+ messages in thread

end of thread, other threads:[~2016-01-28 15:28 UTC | newest]

Thread overview: 10+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2016-01-28 12:28 [LTP] [PATCH v2 0/6] add open/openat + O_TMPFILE tests Alexey Kodanev
2016-01-28 12:28 ` [LTP] [PATCH v2 1/6] lib/tst_dir_is_empty: add a library function Alexey Kodanev
2016-01-28 12:28 ` [LTP] [PATCH v2 2/6] include/lapi/fcntl.h: add O_TMPFILE definition Alexey Kodanev
2016-01-28 12:28 ` [LTP] [PATCH v2 3/6] lib/safe_macros: add linkat() Alexey Kodanev
2016-01-28 12:28 ` [LTP] [PATCH v2 4/6] lib/safe_macros: add readlink() Alexey Kodanev
2016-01-28 12:28 ` [LTP] [PATCH v2 5/6] kernel/syscalls: add new test with 'open() + O_TMPFILE' Alexey Kodanev
2016-01-28 13:41   ` Cyril Hrubis
2016-01-28 12:28 ` [LTP] [PATCH v2 6/6] kernel/syscalls/open14: openat03: add new test-cases Alexey Kodanev
2016-01-28 14:01   ` Cyril Hrubis
2016-01-28 15:28     ` Alexey Kodanev

This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.