[LTP] [PATCH] mprotect: Add mprotect05 testcase

Liam R. Howlett Liam.Howlett@oracle.com
Wed Mar 1 15:16:34 CET 2023


Add a test that uses mprotect to split and combine VMAs.  Created to
ensure the correctness of the VMA iterator after a bug report.

Link: https://bugzilla.kernel.org/show_bug.cgi?id=217061
Signed-off-by: Liam R. Howlett <Liam.Howlett@oracle.com>
---
 .../kernel/syscalls/mprotect/mprotect05.c     | 118 ++++++++++++++++++
 1 file changed, 118 insertions(+)
 create mode 100644 testcases/kernel/syscalls/mprotect/mprotect05.c

diff --git a/testcases/kernel/syscalls/mprotect/mprotect05.c b/testcases/kernel/syscalls/mprotect/mprotect05.c
new file mode 100644
index 000000000..36f137544
--- /dev/null
+++ b/testcases/kernel/syscalls/mprotect/mprotect05.c
@@ -0,0 +1,118 @@
+/*
+ * Copyright (c) International Business Machines  Corp., 2001
+ *
+ * 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 will 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., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
+ */
+
+/*
+ * DESCRIPTION
+ *	Testcase to check the mprotect(2) system call split/merge
+ *
+ * ALGORITHM
+ *	Create a mapped region using mmap with READ permission.
+ *	Create different VMAs in stripes with mprotect (exec & write)
+ *	mprotect over middle & write area, causing vma_merge of prev & next
+ *	before hitting the limnits.
+ *
+ */
+
+#include <sys/mman.h>
+#include <sys/wait.h>
+#include <errno.h>
+#include <fcntl.h>
+#include <limits.h>
+#include <stdlib.h>
+#include "test.h"
+
+#include "safe_macros.h"
+
+static void sighandler(int sig);
+static void cleanup(void);
+static void setup(void);
+
+char *TCID = "mprotect05";
+int TST_TOTAL = 1;
+static int fd;
+static char file1[BUFSIZ];
+
+static char *addr = MAP_FAILED;
+static unsigned long fullsize;
+
+int main(int ac, char **av)
+{
+	int lc;
+	int fd;
+	unsigned long pagesize;
+
+	tst_parse_opts(ac, av, NULL, NULL);
+
+	setup();
+
+	pagesize = getpagesize();
+	fullsize = 5 * pagesize;
+
+	for (lc = 0; TEST_LOOPING(lc); lc++) {
+		fd = SAFE_OPEN(cleanup, file1, O_RDWR | O_CREAT, 0777);
+
+		addr = SAFE_MMAP(cleanup, 0, fullsize, PROT_READ,
+				MAP_SHARED, fd, 0);
+
+		TEST(mprotect(addr + pagesize, pagesize*1, PROT_EXEC));
+		if (TEST_RETURN)
+			tst_resm(TFAIL | TERRNO, "mprotect failed to write");
+
+		TEST(mprotect(addr + 3*pagesize, pagesize, PROT_WRITE));
+		if (TEST_RETURN)
+			tst_resm(TFAIL | TERRNO, "mprotect failed to write");
+
+		TEST(mprotect(addr + pagesize, pagesize*4, PROT_READ));
+		if (TEST_RETURN)
+			tst_resm(TFAIL | TERRNO, "mprotect failed to write");
+
+		SAFE_MUNMAP(cleanup, addr, fullsize);
+		addr = MAP_FAILED;
+		SAFE_CLOSE(cleanup, fd);
+		SAFE_UNLINK(cleanup, file1);
+	}
+
+	cleanup();
+	tst_exit();
+}
+
+static void sighandler(int sig)
+{
+	_exit((sig == SIGSEGV) ? 0 : sig);
+}
+
+static void setup(void)
+{
+	tst_sig(FORK, sighandler, cleanup);
+
+	TEST_PAUSE;
+
+	tst_tmpdir();
+
+	sprintf(file1, "mprotect05.tmp.%d", getpid());
+}
+
+static void cleanup(void)
+{
+	if (addr != MAP_FAILED) {
+		SAFE_MUNMAP(NULL, addr, fullsize);
+		SAFE_CLOSE(NULL, fd);
+	}
+
+	tst_rmdir();
+}
-- 
2.39.0



More information about the ltp mailing list