Test for Memory Protection Key
v3 cover Test for Memory Protection Key
Change log:
v2 --> v3
* Merge pkey02 into pkey01
* Add huge page in the pkey test
* tst_* functions reprot fail with TERRNO
* tst_res(TFAIL, ...) could print exit code
Li Wang (2):
pkey: add syscall numbers for pkey
pkey: add test for memory protection keys
Signature · 1 line
2.20.1
PATCH v3 1/2 pkey: add syscall numbers for pkey
--- include/lapi/syscalls/aarch64.in | 3 +++ include/lapi/syscalls/arm.in | 3 +++ include/lapi/syscalls/i386.in | 3 +++ include/lapi/syscalls/ia64.in | 3 +++ include/lapi/syscalls/powerpc.in | 3 +++ include/lapi/syscalls/powerpc64.in | 3 +++ include/lapi/syscalls/s390.in | 3 +++ include/lapi/syscalls/s390x.in | 3 +++ include/lapi/syscalls/sparc.in | 3 +++ include/lapi/syscalls/sparc64.in | 3 +++ include/lapi/syscalls/x86_64.in | 3 +++ 11 files changed, 33 insertions(+)
include/lapi/syscalls/aarch64.in +3 -0
@@ -265,5 +265,8 @@ mlock2 284 copy_file_range 285 preadv2 286 pwritev2 287 +pkey_mprotect 288 +pkey_alloc 289 +pkey_free 290 pidfd_send_signal 424 _sysctl 1078
include/lapi/syscalls/arm.in +3 -0
@@ -349,5 +349,8 @@ mlock2 (__NR_SYSCALL_BASE+390) copy_file_range (__NR_SYSCALL_BASE+391) preadv2 (__NR_SYSCALL_BASE+392) pwritev2 (__NR_SYSCALL_BASE+393) +pkey_mprotect (__NR_SYSCALL_BASE+394) +pkey_alloc (__NR_SYSCALL_BASE+395) +pkey_free (__NR_SYSCALL_BASE+396) statx (__NR_SYSCALL_BASE+397) pidfd_send_signal (__NR_SYSCALL_BASE+424)
include/lapi/syscalls/i386.in +3 -0
@@ -347,5 +347,8 @@ mlock2 376 copy_file_range 377 preadv2 378 pwritev2 379 +pkey_mprotect 380 +pkey_alloc 381 +pkey_free 382 statx 383 pidfd_send_signal 424
include/lapi/syscalls/ia64.in +3 -0
@@ -305,4 +305,7 @@ mlock2 1346 copy_file_range 1347 preadv2 1348 pwritev2 1349 +pkey_mprotect 1354 +pkey_alloc 1355 +pkey_free 1356 pidfd_send_signal 1448
include/lapi/syscalls/powerpc.in +3 -0
@@ -356,3 +356,6 @@ preadv2 380 pwritev2 381 statx 383 pidfd_send_signal 424 +pkey_mprotect 386 +pkey_alloc 384 +pkey_free 385
include/lapi/syscalls/powerpc64.in +3 -0
@@ -356,3 +356,6 @@ preadv2 380 pwritev2 381 statx 383 pidfd_send_signal 424 +pkey_mprotect 386 +pkey_alloc 384 +pkey_free 385
include/lapi/syscalls/s390.in +3 -0
@@ -338,4 +338,7 @@ mlock2 374 copy_file_range 375 preadv2 376 pwritev2 377 +pkey_mprotect 384 +pkey_alloc 385 +pkey_free 386 pidfd_send_signal 424
include/lapi/syscalls/s390x.in +3 -0
@@ -337,4 +337,7 @@ mlock2 374 copy_file_range 375 preadv2 376 pwritev2 377 +pkey_mprotect 384 +pkey_alloc 385 +pkey_free 386 pidfd_send_signal 424
include/lapi/syscalls/sparc.in +3 -0
@@ -343,4 +343,7 @@ mlock2 356 copy_file_range 357 preadv2 358 pwritev2 359 +pkey_mprotect 362 +pkey_alloc 363 +pkey_free 364 pidfd_send_signal 424
include/lapi/syscalls/sparc64.in +3 -0
@@ -319,4 +319,7 @@ mlock2 356 copy_file_range 357 preadv2 358 pwritev2 359 +pkey_mprotect 362 +pkey_alloc 363 +pkey_free 364 pidfd_send_signal 424
include/lapi/syscalls/x86_64.in +3 -0
@@ -314,5 +314,8 @@ mlock2 325 copy_file_range 326 preadv2 327 pwritev2 328 +pkey_mprotect 329 +pkey_alloc 330 +pkey_free 331 statx 332 pidfd_send_signal 424
Signature · 1 line
2.20.1
PATCH v3 2/2 pkey: add test for memory protection keys
Memory Protection Keys for Userspace (PKU aka PKEYs) is a Skylake-SP server feature that provides a mechanism for enforcing page-based protections, but without requiring modification of the page tables when an application changes protection domains. It works by dedicating 4 previously ignored bits in each page table entry to a "protection key", giving 16 possible keys.
Basic method for PKEYs test:
1. test allocates a pkey(e.g. PKEY_DISABLE_ACCESS) via pkey_alloc()
2. pkey_mprotect() apply this pkey to a piece of memory buffer
3. check if the access right of buffer has been changed and take effect
4. remove the access right(pkey) from this buffer via pkey_mprotect()
5. check if buffer area can be read or write after removing pkey
6. pkey_free() releases the pkey after using it
Looping around this basic test on diffenrent types of memory.
--- configure.ac | 1 + runtest/syscalls | 2 + testcases/kernel/syscalls/pkeys/.gitignore | 1 + testcases/kernel/syscalls/pkeys/Makefile | 8 + testcases/kernel/syscalls/pkeys/pkey.h | 50 +++++ testcases/kernel/syscalls/pkeys/pkey01.c | 235 +++++++++++++++++++++ 6 files changed, 297 insertions(+) create mode 100644 testcases/kernel/syscalls/pkeys/.gitignore create mode 100644 testcases/kernel/syscalls/pkeys/Makefile create mode 100644 testcases/kernel/syscalls/pkeys/pkey.h create mode 100644 testcases/kernel/syscalls/pkeys/pkey01.c
configure.ac +1 -0
@@ -74,6 +74,7 @@ AC_CHECK_FUNCS([ \ pidfd_send_signal \ preadv \ preadv2 \ + pkey_mprotect \ profil \ pwritev \ pwritev2 \
runtest/syscalls +2 -0
@@ -721,6 +721,8 @@ mprotect02 mprotect02 mprotect03 mprotect03 mprotect04 mprotect04 +pkey01 pkey01 + mq_notify01 mq_notify01 mq_notify02 mq_notify02 mq_open01 mq_open01
testcases/kernel/syscalls/pkeys/.gitignore new file +1 -0
@@ -0,0 +1 @@ +/pkey01
testcases/kernel/syscalls/pkeys/Makefile new file +8 -0
@@ -0,0 +1,8 @@ +# SPDX-License-Identifier: GPL-2.0-or-later +# Copyright (c) 2019 Red Hat, Inc. + +top_srcdir ?= ../../../.. + +include $(top_srcdir)/include/mk/testcases.mk + +include $(top_srcdir)/include/mk/generic_leaf_target.mk
testcases/kernel/syscalls/pkeys/pkey.h new file +50 -0
50 lines not on this page · raw message
testcases/kernel/syscalls/pkeys/pkey01.c new file +235 -0
235 lines not on this page · raw message
Signature · 1 line
2.20.1
PATCH v3 2/2 pkey: add test for memory protection keys
----- Original Message -----
Quoted 6 lines
testcases/kernel/syscalls/pkeys/pkey.h new file +6
-0+ +#ifndef PKEYS_H +#define PKEYS_H + +#include "tst_test.h" +#include "lapi/syscalls.h"
testcases/kernel/syscalls/pkeys/pkey.h line 20
Quoted 10 lines
testcases/kernel/syscalls/pkeys/pkey.h new file +10
-0+ +#ifndef PKEY_DISABLE_ACCESS +# define PKEY_DISABLE_ACCESS 0x1 +# define PKEY_DISABLE_WRITE 0x2 +#endif + +#ifndef HAVE_PKEY_MPROTECT +static inline int pkey_mprotect (void *addr,size_t len,int prot,int pkey) +{ +return tst_syscall (SYS_pkey_mprotect, addr, len, prot, pkey);
Hi,
This should be __NR_*:
In file included from pkey01.c:32:pkey.h: In function ?pkey_mprotect?:
pkey.h:20: error: ?SYS_pkey_mprotect? undeclared (first use in this function) pkey.h:20: error: (Each undeclared identifier is reported only once pkey.h:20: error: for each function it appears in.)pkey.h: In function ?pkey_alloc?:
pkey.h:25: error: ?SYS_pkey_alloc? undeclared (first use in this function) pkey.h: In function ?pkey_free?:
pkey.h:30: error: ?SYS_pkey_free? undeclared (first use in this function)
testcases/kernel/syscalls/pkeys/pkey01.c line 64
Quoted 10 lines
testcases/kernel/syscalls/pkeys/pkey01.c new file +10
-0+static void setup (void ) +{ +int i, fd; + +if (access ("/proc/sys/vm/nr_hugepages" ,F_OK )) { +tst_res (TINFO ,"Huge page is not supported" ); + size =getpagesize (); + no_hugepage =1 ; + }else { +SAFE_FILE_PRINTF ("/proc/sys/vm/nr_hugepages" ,"%d" ,1 );
There are 2 problems here, both related to fact that this file exists, but may return EOPNOTSUPP on read/write.
1. save_restore should ignore also read/open errors if path is prefixed with '?' I'll send this separately.
2. SAFE_FILE_PRINTF in pkey01.c shouldn't be safe, because we need to somehow detect that write worked
# ls -la /proc/sys/vm/nr_hugepages -rw-r--r--. 1 root root 0 Jun 25 04:12 /proc/sys/vm/nr_hugepages
# cat /proc/sys/vm/nr_hugepages cat: /proc/sys/vm/nr_hugepages: Operation not supported
testcases/kernel/syscalls/pkeys/pkey01.c line 234
Quoted 7 lines
testcases/kernel/syscalls/pkeys/pkey01.c new file +7
-0+static struct tst_test test = { + .tcnt =ARRAY_SIZE (tcases), + .forks_child =1 , + .test = verify_pkey, + .setup = setup, + .cleanup = cleanup, + .save_restore = save_restore,
.needs_root = 1 as well, since we write to /proc and mount tmpfs
Rest looks good to me, but I haven't found yet system that could run the test.
Regards,
Jan
PATCH v3 2/2 pkey: add test for memory protection keys
Quoted 17 lines · Jan Stancek
----- Original Message -----
Quoted 4 lines
testcases/kernel/syscalls/pkeys/pkey.h new file +4
-0+ +#ifndef PKEYS_H +#define PKEYS_H +testcases/kernel/syscalls/pkeys/pkey.h
Quoted 10 lines
testcases/kernel/syscalls/pkeys/pkey.h new file +10
-0+#include "tst_test.h" +#include "lapi/syscalls.h" + +#ifndef PKEY_DISABLE_ACCESS +# define PKEY_DISABLE_ACCESS 0x1 +# define PKEY_DISABLE_WRITE 0x2 +#endif + +#ifndef HAVE_PKEY_MPROTECT +static inline int pkey_mprotect(void *addr, size_t len, int prot, intpkey)
Quoted 7 lines
testcases/kernel/syscalls/pkeys/pkey.h line 20
Quoted 2 lines
testcases/kernel/syscalls/pkeys/pkey.h new file +2
-0+{ +return tst_syscall (SYS_pkey_mprotect, addr, len, prot, pkey);Hi,
This should be __NR_*:
Exactly. Sorry about that mistake.
Quoted 26 lines
In file included from pkey01.c:32:
pkey.h: In function ?pkey_mprotect?:
pkey.h:20: error: ?SYS_pkey_mprotect? undeclared (first use in this function)
pkey.h:20: error: (Each undeclared identifier is reported only once pkey.h:20: error: for each function it appears in.)pkey.h: In function ?pkey_alloc?:
pkey.h:25: error: ?SYS_pkey_alloc? undeclared (first use in this function)pkey.h: In function ?pkey_free?:
pkey.h:30: error: ?SYS_pkey_free? undeclared (first use in this function)testcases/kernel/syscalls/pkeys/pkey01.c line 64
Quoted 10 lines
testcases/kernel/syscalls/pkeys/pkey01.c new file +10
-0+static void setup (void ) +{ +int i, fd; + +if (access ("/proc/sys/vm/nr_hugepages" ,F_OK )) { +tst_res (TINFO ,"Huge page is not supported" ); + size =getpagesize (); + no_hugepage =1 ; + }else { +SAFE_FILE_PRINTF ("/proc/sys/vm/nr_hugepages" ,"%d" ,1 );There are 2 problems here, both related to fact that this file exists, but may return EOPNOTSUPP on read/write.
Quoted 4 lines
1.
save_restoreshould ignore also read/open errors if path is prefixed with '?'
I'll send this separately.
Thank you for that patch.
Quoted 5 lines
2.
SAFE_FILE_PRINTFinpkey01.cshouldn't be safe, because we need to somehow
detect that write worked
Yes, we should verify if that value has been wrote.
Quoted 15 lines
# ls -la /proc/sys/vm/nr_hugepages -rw-r--r--. 1 root root 0 Jun 25 04:12 /proc/sys/vm/nr_hugepages# cat /proc/sys/vm/nr_hugepages cat: /proc/sys/vm/nr_hugepages: Operation not supportedtestcases/kernel/syscalls/pkeys/pkey01.c line 234
Quoted 7 lines
testcases/kernel/syscalls/pkeys/pkey01.c new file +7
-0+static struct tst_test test = { + .tcnt =ARRAY_SIZE (tcases), + .forks_child =1 , + .test = verify_pkey, + .setup = setup, + .cleanup = cleanup, + .save_restore = save_restore,
Quoted 2 lines
.needs_root = 1 as well, since we write to /proc and mount tmpfs
Agree.
Quoted 7 lines
Rest looks good to me, but I haven't found yet system that could run the test.
Regards,
Jan
Signature · 5 lines
Regards, Li Wang -------------- next part -------------- An HTML attachment was scrubbed... URL: <http://lists.linux.it/pipermail/ltp/attachments/20190625/cc81287a/attachment.html>