* tests/Makefile.am (DECODER_TESTS): Add add_key.test, keyctl.test, request_key.test. (check_PROGRAMS): Add add_key, keyctl, request_key. * tests/.gitignore: Likewise. * tests/add_key.c: New file. * tests/add_key.test: Likewise. * tests/keyctl.c: Likewise. * tests/keyctl.test: Likewise. * tests/request_key.c: Likewise. * tests/request_key.test: Likewise. --- tests/.gitignore | 3 + tests/Makefile.am | 6 + tests/add_key.c | 128 +++++++++ tests/add_key.test | 6 + tests/keyctl.c | 713 ++++++++++++++++++++++++++++++++++++++++++++++++ tests/keyctl.test | 6 + tests/request_key.c | 124 +++++++++ tests/request_key.test | 6 + 8 files changed, 992 insertions(+) create mode 100644 tests/add_key.c create mode 100755 tests/add_key.test create mode 100644 tests/keyctl.c create mode 100755 tests/keyctl.test create mode 100644 tests/request_key.c create mode 100755 tests/request_key.test
diff --git a/tests/.gitignore b/tests/.gitignore index 9ee036b..5b33416 100644 --- a/tests/.gitignore +++ b/tests/.gitignore @@ -10,6 +10,7 @@ accept accept4 access acct +addkey adjtimex aio alarm @@ -117,6 +118,7 @@ ipc_msg ipc_msgbuf ipc_sem ipc_shm +keyctl kill ksysent ksysent.h @@ -208,6 +210,7 @@ remap_file_pages rename renameat renameat2 +request_key restart_syscall rmdir rt_sigpending diff --git a/tests/Makefile.am b/tests/Makefile.am index 86672fc..0c24969 100644 --- a/tests/Makefile.am +++ b/tests/Makefile.am @@ -69,6 +69,7 @@ check_PROGRAMS = \ accept4 \ access \ acct \ + add_key \ adjtimex \ aio \ alarm \ @@ -176,6 +177,7 @@ check_PROGRAMS = \ ipc_msgbuf \ ipc_sem \ ipc_shm \ + keyctl \ kill \ ksysent \ lchown \ @@ -265,6 +267,7 @@ check_PROGRAMS = \ rename \ renameat \ renameat2 \ + request_key \ restart_syscall \ rmdir \ rt_sigpending \ @@ -414,6 +417,7 @@ DECODER_TESTS = \ accept4.test \ access.test \ acct.test \ + add_key.test \ adjtimex.test \ aio.test \ alarm.test \ @@ -518,6 +522,7 @@ DECODER_TESTS = \ ipc_msgbuf.test \ ipc_sem.test \ ipc_shm.test \ + keyctl.test \ kill.test \ lchown.test \ lchown32.test \ @@ -601,6 +606,7 @@ DECODER_TESTS = \ rename.test \ renameat.test \ renameat2.test \ + request_key.test \ rmdir.test \ rt_sigpending.test \ rt_sigprocmask.test \ diff --git a/tests/add_key.c b/tests/add_key.c new file mode 100644 index 0000000..0773823 --- /dev/null +++ b/tests/add_key.c @@ -0,0 +1,128 @@ +#include "tests.h" + +#include <asm/unistd.h> + +#ifdef __NR_add_key + +# include <inttypes.h> +# include <stdio.h> +# include <unistd.h> + +void +print_val_str(const void *ptr, const char *str) +{ + if (str) + printf("%s, ", str); + else + printf("%p, ", ptr); +} + +void +do_add_key(const char *type, const char *type_str, const char *desc, + const char *desc_str, const char *payload, const char *payload_str, + size_t plen, int32_t keyring, const char *keyring_str) +{ + long rc; + + rc = syscall(__NR_add_key, type, desc, payload, plen, keyring); + printf("add_key("); + print_val_str(type, type_str); + print_val_str(desc, desc_str); + print_val_str(payload, payload_str); + printf("%zu, ", plen); + if (keyring_str) + printf("%s", keyring_str); + else + printf("%d", keyring); + printf(") = %s\n", sprintrc(rc)); +} + +# define _STR(_arg) #_arg +# define ARG_STR(_arg) (_arg), #_arg + +int +main(void) +{ + static const char unterminated1[] = { '\1', '\2', '\3', '\4', '\5' }; + static const char unterminated2[] = { '\6', '\7', '\10', '\11', '\12' }; + static const char unterminated3[] = + { '\16', '\17', '\20', '\21', '\22' }; + + char *bogus_type = tail_memdup(unterminated1, sizeof(unterminated1)); + char *bogus_desc = tail_memdup(unterminated2, sizeof(unterminated2)); + char *bogus_payload = tail_memdup(unterminated3, sizeof(unterminated3)); + + unsigned i; + unsigned j; + unsigned k; + unsigned l; + + struct { + const char *type; + const char *str; + } types[] = { + { ARG_STR(NULL) }, + { (const char *) 0xfffffee1fffffbadULL, NULL }, + { bogus_type, NULL }, + { ARG_STR("\20\21\22\23\24") }, + { ARG_STR("user") }, + }; + + struct { + const char *desc; + const char *str; + } descs[] = { + { ARG_STR(NULL) }, + { (const char *) 0xfffff00dfffffca7ULL, NULL }, + { bogus_desc, NULL }, + { ARG_STR("\25\26\27\30\31") }, + { ARG_STR("desc") }, + { "overly long description", _STR("overly long ") "..." }, + }; + + struct { + const char *pload; + const char *str; + size_t plen; + } payloads[] = { + { ARG_STR(NULL), 0 }, + { (const char *) 0xfffffacefffff157ULL, NULL, + (size_t) 0xdeadbeefbadc0dedULL }, + { bogus_payload, _STR(""), 0 }, + { bogus_payload, _STR("\16\17\20\21\22"), 5 }, + { bogus_payload, NULL, 10 }, + { "overly long payload", _STR("overly long ") "...", 15 }, + }; + + struct { + uint32_t keyring; + const char *str; + } keyrings[] = { + { ARG_STR(0) }, + { ARG_STR(1234567890) }, + { ARG_STR(-1234567890) }, + { -1, "KEY_SPEC_THREAD_KEYRING" }, + }; + + for (i = 0; i < ARRAY_SIZE(types); i++) + for (j = 0; j < ARRAY_SIZE(descs); j++) + for (k = 0; k < ARRAY_SIZE(payloads); k++) + for (l = 0; l < ARRAY_SIZE(keyrings); l++) + do_add_key(types[i].type, types[i].str, + descs[j].desc, descs[j].str, + payloads[k].pload, + payloads[k].str, + payloads[k].plen, + keyrings[l].keyring, + keyrings[l].str); + + puts("+++ exited with 0 +++"); + + return 0; +} + +#else + +SKIP_MAIN_UNDEFINED("__NR_add_key"); + +#endif diff --git a/tests/add_key.test b/tests/add_key.test new file mode 100755 index 0000000..574c91d --- /dev/null +++ b/tests/add_key.test @@ -0,0 +1,6 @@ +#!/bin/sh + +# Check add_key syscall decoding. + +. "${srcdir=.}/init.sh" +run_strace_match_diff -a1 -s12 diff --git a/tests/keyctl.c b/tests/keyctl.c new file mode 100644 index 0000000..3351c97 --- /dev/null +++ b/tests/keyctl.c @@ -0,0 +1,713 @@ +#include "tests.h" + +#include <asm/unistd.h> + +#ifdef __NR_keyctl + +# include <linux/types.h> +# include <linux/keyctl.h> + +# include <errno.h> +# include <inttypes.h> +# include <stdarg.h> +# include <stdio.h> +# include <stdlib.h> +# include <string.h> +# include <unistd.h> + +#include <sys/uio.h> + + +# if !defined(HAVE___KERNEL_ULONG_T) || !HAVE___KERNEL_ULONG_T +typedef unsigned long __kernel_ulong_t; +# endif + +/* This check should be before #include "xlat/keyctl_commands.h" */ +# ifndef KEYCTL_DH_COMPUTE +struct keyctl_dh_params { + int32_t private; + int32_t prime; + int32_t base; +}; +# endif + +# include "xlat.h" +# include "xlat/keyctl_commands.h" + +# ifndef KEY_SPEC_REQKEY_AUTH_KEY +# define KEY_SPEC_REQKEY_AUTH_KEY -7 +# endif + +# ifndef KEY_SPEC_REQUESTOR_KEYRING +# define KEY_SPEC_REQUESTOR_KEYRING -8 +# endif + +static const size_t limit = 10; + +void +print_quoted_string_limit(const char *str, ssize_t size, long rc) +{ + size_t abs_size = abs(size); + size_t limited_size = abs_size > limit ? limit : abs_size; + + if ((rc == -1) && (size > 0)) { + printf("%p", str); + return; + } + + if (strnlen(str, limited_size) == limited_size) { + printf("\""); + print_quoted_memory(str, limited_size); + if (abs_size > limit) + printf("\"..."); + else + printf("\""); + } else { + printf("\""); + print_quoted_string(str); + printf("\""); + } +} + +static void +print_arg(__kernel_ulong_t arg, const char *str, const char *fmt, ssize_t size, + long rc) +{ + if (str) { + printf("%s", str); + } else { + if (size == sizeof(uint64_t)) + printf(fmt, (uint64_t)arg); + else if (size == sizeof(uint32_t)) + printf(fmt, (uint32_t)arg); + else + print_quoted_string_limit((void *)arg, size, rc); + } +} + +/* + * Arguments are passed as sz, val, str, fmt. Arguments are read until 4 + * arguments are retrieved or size of 0 is occurred. + * + * str == NULL && fmt == NULL && sz not in {4, 8} - print_quoted_string_limit is + * used for argument printing. If sz is negative, in argument is assumed, out + * otherwise. + */ +void +do_keyctl(__kernel_ulong_t cmd, const char *cmd_str, ...) +{ + __kernel_ulong_t args[4] = { + (__kernel_ulong_t) 0xdeadfee1badc0de5ULL, + (__kernel_ulong_t) 0xdeadfee2badc0de6ULL, + (__kernel_ulong_t) 0xdeadfee3badc0de7ULL, + (__kernel_ulong_t) 0xdeadfee4badc0de8ULL, + }; + const char *arg_str[4] = { NULL }; + const char *arg_fmt[4] = { "%llu", "%llu", "%llu", "%llu" }; + ssize_t arg_sz[4] = { + sizeof(__kernel_ulong_t), + sizeof(__kernel_ulong_t), + sizeof(__kernel_ulong_t), + sizeof(__kernel_ulong_t), + }; + long rc; + unsigned i; + unsigned cnt = 0; + + va_list ap; + + va_start(ap, cmd_str); + + do { + arg_sz[cnt] = va_arg(ap, size_t); + if (!arg_sz[cnt]) + break; + + if (arg_sz[cnt] == sizeof(uint64_t)) + args[cnt] = va_arg(ap, uint64_t); + else if (arg_sz[cnt] == sizeof(uint32_t)) + args[cnt] = va_arg(ap, uint32_t); + else + args[cnt] = (uintptr_t) va_arg(ap, void *); + + arg_str[cnt] = va_arg(ap, char *); + arg_fmt[cnt] = va_arg(ap, char *); + } while (++cnt < 4); + + rc = syscall(__NR_keyctl, cmd, args[0], args[1], args[2], args[3]); + printf("keyctl(%s", cmd_str); + for (i = 0; i < cnt; i++) { + printf(", "); + print_arg(args[i], arg_str[i], arg_fmt[i], arg_sz[i], rc); + } + printf(") = %s\n", sprintrc(rc)); +} + +# define _STR(_arg) #_arg +# define ARG_STR(_arg) (_arg), #_arg + +int +main(void) +{ + enum { PR_LIMIT = 10, IOV_SIZE = 11, IOV_STR_SIZE = 4096 }; + + static const char *kulong_fmt = + sizeof(__kernel_ulong_t) == sizeof(uint64_t) ? "%#llx" : "%#x"; + static const char *ksize_fmt = + sizeof(__kernel_ulong_t) == sizeof(uint64_t) ? "%llu" : "%u"; + static const char *ptr_fmt = + sizeof(void *) == sizeof(uint64_t) ? "%#llx" : "%#x"; + static const char unterminated1[] = { '\1', '\2', '\3', '\4', '\5' }; + static const char unterminated2[] = { '\6', '\7', '\10', '\11', '\12' }; + static const char short_type_str[] = "shrt type"; + static const char short_desc_str[] = "shrt desc"; + static const char long_type_str[] = "overly long key type"; + static const char long_desc_str[] = "overly long key description"; + static const int32_t bogus_key1 = 0xdeadf00d; + static const int32_t bogus_key2 = 0x1eefdead; + static const __kernel_ulong_t bogus_key3 = + (__kernel_ulong_t) 0xdec0ded1dec0ded2ULL; + static const char *bogus_key3_str = "-557785390"; + + static const struct keyctl_dh_params kcdhp_data = { + KEY_SPEC_GROUP_KEYRING, 1234567890, 3141592653U }; + static const char *kcdhp_str = "{private=KEY_SPEC_GROUP_KEYRING, " + "prime=1234567890, base=-1153374643}"; + + char *bogus_str = tail_memdup(unterminated1, sizeof(unterminated1)); + char *bogus_desc = tail_memdup(unterminated2, sizeof(unterminated2)); + char *short_type = tail_memdup(short_type_str, sizeof(short_type_str)); + char *short_desc = tail_memdup(short_desc_str, sizeof(short_desc_str)); + char *long_type = tail_memdup(long_type_str, sizeof(long_type_str)); + char *long_desc = tail_memdup(long_desc_str, sizeof(long_desc_str)); + char *kcdhp = tail_memdup(&kcdhp_data, sizeof(kcdhp_data)); + struct iovec *key_iov = tail_alloc(sizeof(*key_iov) * IOV_SIZE); + char *bogus_buf1 = tail_alloc(9); + char *bogus_buf2 = tail_alloc(256); + char *key_iov_str1; + char *key_iov_str2 = malloc(4096); + ssize_t ret; + ssize_t kis_size = 0; + int i; + + key_iov[0].iov_base = short_type; + key_iov[0].iov_len = sizeof(short_type_str); + key_iov[1].iov_base = long_type; + key_iov[1].iov_len = sizeof(long_type_str); + key_iov[2].iov_base = short_desc; + key_iov[2].iov_len = sizeof(short_desc_str); + key_iov[3].iov_base = long_desc; + key_iov[3].iov_len = sizeof(long_desc_str); + key_iov[4].iov_base = bogus_str; + key_iov[4].iov_len = 32; + + for (i = 5; i < IOV_SIZE; i++) { + key_iov[i].iov_base = + (void *) (uintptr_t) (0xfffffacefffff00dULL + + 0x100000001ULL * i); + key_iov[i].iov_len = (size_t) (0xcaffeeeddefaced7ULL + + 0x100000001ULL * i); + } + + asprintf(&key_iov_str1, "[{iov_base=%p, iov_len=%zu}, " + "{iov_base=%p, iov_len=%zu}, {iov_base=%p, iov_len=%zu}, " + "{iov_base=%p, iov_len=%zu}]", + key_iov[IOV_SIZE - 4].iov_base, key_iov[IOV_SIZE - 4].iov_len, + key_iov[IOV_SIZE - 3].iov_base, key_iov[IOV_SIZE - 3].iov_len, + key_iov[IOV_SIZE - 2].iov_base, key_iov[IOV_SIZE - 2].iov_len, + key_iov[IOV_SIZE - 1].iov_base, key_iov[IOV_SIZE - 1].iov_len); + + ret = snprintf(key_iov_str2, IOV_STR_SIZE, + "[{iov_base=\"%s\\0\", iov_len=%zu}, " + "{iov_base=\"%.10s\"..., iov_len=%zu}, " + "{iov_base=\"%s\\0\", iov_len=%zu}, " + "{iov_base=\"%.10s\"..., iov_len=%zu}, ", + (char *) key_iov[0].iov_base, key_iov[0].iov_len, + (char *) key_iov[1].iov_base, key_iov[1].iov_len, + (char *) key_iov[2].iov_base, key_iov[2].iov_len, + (char *) key_iov[3].iov_base, key_iov[3].iov_len); + + if ((ret < 0) || (ret >= IOV_STR_SIZE)) + error_msg_and_fail("snprintf"); + + for (i = 4; i < PR_LIMIT; i++) { + kis_size += ret; + + ret = snprintf(key_iov_str2 + kis_size, IOV_STR_SIZE - kis_size, + "{iov_base=%p, iov_len=%zu}, ", + key_iov[i].iov_base, key_iov[i].iov_len); + + if ((ret < 0) || (ret >= (IOV_STR_SIZE - kis_size))) + error_msg_and_fail("snprintf"); + } + + kis_size += ret; + snprintf(key_iov_str2 + kis_size, IOV_STR_SIZE - kis_size, "...]"); + + + /* Invalid command */ + do_keyctl((__kernel_ulong_t) 0xbadc0dedfacefeedULL, + "0xfacefeed /* KEYCTL_??? */", + sizeof(__kernel_ulong_t), + (__kernel_ulong_t) 0xdeadfee1badc0de5ULL, NULL, kulong_fmt, + sizeof(__kernel_ulong_t), + (__kernel_ulong_t) 0xdeadfee2badc0de6ULL, NULL, kulong_fmt, + sizeof(__kernel_ulong_t), + (__kernel_ulong_t) 0xdeadfee3badc0de7ULL, NULL, kulong_fmt, + sizeof(__kernel_ulong_t), + (__kernel_ulong_t) 0xdeadfee4badc0de8ULL, NULL, kulong_fmt); + + + /* GET_KEYRING_ID */ + do_keyctl(ARG_STR(KEYCTL_GET_KEYRING_ID), + sizeof(int32_t), bogus_key1, NULL, "%d", + sizeof(int), (__kernel_ulong_t) 0xbadc0dedffffffffLLU, "-1", + NULL, 0UL); + do_keyctl(ARG_STR(KEYCTL_GET_KEYRING_ID), + sizeof(int32_t), ARG_STR(KEY_SPEC_THREAD_KEYRING), "%d", + sizeof(int), 3141592653U, NULL, "%d", + NULL, 0UL); + + + /* KEYCTL_JOIN_SESSION_KEYRING */ + do_keyctl(ARG_STR(KEYCTL_JOIN_SESSION_KEYRING), + sizeof(char *), ARG_STR(NULL), NULL, 0UL); + do_keyctl(ARG_STR(KEYCTL_JOIN_SESSION_KEYRING), + sizeof(char *), (char *) 0xfffffacefffffeedULL, NULL, ptr_fmt, + 0UL); + do_keyctl(ARG_STR(KEYCTL_JOIN_SESSION_KEYRING), + sizeof(char *), bogus_str, NULL, ptr_fmt, 0UL); + do_keyctl(ARG_STR(KEYCTL_JOIN_SESSION_KEYRING), + sizeof(char *), ARG_STR("bogus name"), NULL, 0UL); + do_keyctl(ARG_STR(KEYCTL_JOIN_SESSION_KEYRING), + sizeof(char *), "very long keyring name", "\"very long \"...", + NULL, 0UL); + + + /* KEYCTL_UPDATE */ + do_keyctl(ARG_STR(KEYCTL_UPDATE), + sizeof(int32_t), ARG_STR(KEY_SPEC_REQUESTOR_KEYRING), NULL, + sizeof(char *), ARG_STR(NULL), NULL, + sizeof(__kernel_ulong_t), + (__kernel_ulong_t) 0, NULL, ksize_fmt, 0UL); + do_keyctl(ARG_STR(KEYCTL_UPDATE), + sizeof(int32_t), bogus_key1, NULL, "%d", + sizeof(char *), (char *) 0xfffffacefffffeedULL, NULL, ptr_fmt, + sizeof(__kernel_ulong_t), + (__kernel_ulong_t) 0xdeadfee4badc0de8ULL, NULL, ksize_fmt, 0UL); + do_keyctl(ARG_STR(KEYCTL_UPDATE), + sizeof(int32_t), bogus_key2, NULL, "%d", + sizeof(char *), bogus_str, NULL, ptr_fmt, + sizeof(__kernel_ulong_t), + (__kernel_ulong_t) 0xdeadfee4badc0de8ULL, NULL, ksize_fmt, 0UL); + do_keyctl(ARG_STR(KEYCTL_UPDATE), + sizeof(__kernel_ulong_t), bogus_key3, bogus_key3_str, NULL, + -sizeof(short_desc_str), short_desc, NULL, NULL, + sizeof(__kernel_ulong_t), + (__kernel_ulong_t) sizeof(short_desc_str) - 1, NULL, ksize_fmt, + 0UL); + + + /* KEYCTL_REVOKE */ + do_keyctl(ARG_STR(KEYCTL_REVOKE), + sizeof(int32_t), ARG_STR(KEY_SPEC_GROUP_KEYRING), NULL, 0UL); + do_keyctl(ARG_STR(KEYCTL_REVOKE), + sizeof(int32_t), bogus_key1, NULL, "%d", 0UL); + do_keyctl(ARG_STR(KEYCTL_REVOKE), + sizeof(int32_t), bogus_key2, NULL, "%d", 0UL); + do_keyctl(ARG_STR(KEYCTL_REVOKE), + sizeof(__kernel_ulong_t), bogus_key3, bogus_key3_str, NULL, + 0UL); + + + /* KEYCTL_CHOWN */ + do_keyctl(ARG_STR(KEYCTL_CHOWN), + sizeof(int32_t), ARG_STR(KEY_SPEC_REQUESTOR_KEYRING), NULL, + sizeof(uid_t), ARG_STR(-1), NULL, + sizeof(gid_t), ARG_STR(-1), NULL, 0UL); + do_keyctl(ARG_STR(KEYCTL_CHOWN), + sizeof(int32_t), bogus_key1, NULL, "%d", + sizeof(uid_t), 2718281828U, NULL, "%u", + sizeof(gid_t), 3141592653U, NULL, "%u", 0UL); + + + /* KEYCTL_SETPERM */ + do_keyctl(ARG_STR(KEYCTL_SETPERM), + sizeof(int32_t), ARG_STR(KEY_SPEC_REQKEY_AUTH_KEY), NULL, + sizeof(uint32_t), 0xffffffffU, + "KEY_POS_VIEW|KEY_POS_READ|KEY_POS_WRITE|" + "KEY_POS_SEARCH|KEY_POS_LINK|KEY_POS_SETATTR|" + "KEY_USR_VIEW|KEY_USR_READ|KEY_USR_WRITE|" + "KEY_USR_SEARCH|KEY_USR_LINK|KEY_USR_SETATTR|" + "KEY_GRP_VIEW|KEY_GRP_READ|KEY_GRP_WRITE|" + "KEY_GRP_SEARCH|KEY_GRP_LINK|KEY_GRP_SETATTR|" + "KEY_OTH_VIEW|KEY_OTH_READ|KEY_OTH_WRITE|" + "KEY_OTH_SEARCH|KEY_OTH_LINK|KEY_OTH_SETATTR|" + "0xc0c0c0c0", NULL, 0UL); + do_keyctl(ARG_STR(KEYCTL_SETPERM), + sizeof(int32_t), bogus_key1, NULL, "%d", + sizeof(uint32_t), 0, NULL, "%#x", 0UL); + do_keyctl(ARG_STR(KEYCTL_SETPERM), + sizeof(__kernel_ulong_t), bogus_key3, bogus_key3_str, NULL, + sizeof(uint32_t), 0xc0c0c0c0, "0xc0c0c0c0 /* KEY_??? */", NULL, + 0UL); + + + /* KEYCTL_DESCRIBE */ + do_keyctl(ARG_STR(KEYCTL_DESCRIBE), + sizeof(int32_t), bogus_key1, NULL, "%d", + sizeof(char *), ARG_STR(NULL), ptr_fmt, + sizeof(__kernel_ulong_t), + (__kernel_ulong_t) 0xfeedf157badc0dedLLU, NULL, ksize_fmt, 0UL); + do_keyctl(ARG_STR(KEYCTL_DESCRIBE), + sizeof(__kernel_ulong_t), bogus_key3, bogus_key3_str, NULL, + sizeof(char *), ARG_STR(NULL), ptr_fmt, + sizeof(__kernel_ulong_t), + (__kernel_ulong_t) 0xfeedf157badc0dedLLU, NULL, ksize_fmt, 0UL); + do_keyctl(ARG_STR(KEYCTL_DESCRIBE), + sizeof(int32_t), ARG_STR(KEY_SPEC_THREAD_KEYRING), NULL, + 9, (uintptr_t) bogus_buf1, NULL, NULL, + sizeof(__kernel_ulong_t), + (__kernel_ulong_t) 9, NULL, ksize_fmt, 0UL); + do_keyctl(ARG_STR(KEYCTL_DESCRIBE), + sizeof(int32_t), ARG_STR(KEY_SPEC_THREAD_KEYRING), NULL, + 256, (uintptr_t) bogus_buf2, NULL, NULL, + sizeof(__kernel_ulong_t), + (__kernel_ulong_t) 256, NULL, ksize_fmt, 0UL); + + + /* KEYCTL_CLEAR */ + do_keyctl(ARG_STR(KEYCTL_CLEAR), + sizeof(int32_t), ARG_STR(KEY_SPEC_GROUP_KEYRING), NULL, 0UL); + do_keyctl(ARG_STR(KEYCTL_CLEAR), + sizeof(int32_t), bogus_key1, NULL, "%d", 0UL); + do_keyctl(ARG_STR(KEYCTL_CLEAR), + sizeof(int32_t), bogus_key2, NULL, "%d", 0UL); + do_keyctl(ARG_STR(KEYCTL_CLEAR), + sizeof(__kernel_ulong_t), bogus_key3, bogus_key3_str, NULL, + 0UL); + + + /* KEYCTL_LINK */ + do_keyctl(ARG_STR(KEYCTL_LINK), + sizeof(int32_t), bogus_key1, NULL, "%d", + sizeof(int32_t), ARG_STR(KEY_SPEC_GROUP_KEYRING), NULL, 0UL); + do_keyctl(ARG_STR(KEYCTL_LINK), + sizeof(int32_t), ARG_STR(KEY_SPEC_REQUESTOR_KEYRING), NULL, + sizeof(int32_t), bogus_key2, NULL, "%d", 0UL); + do_keyctl(ARG_STR(KEYCTL_LINK), + sizeof(int32_t), ARG_STR(KEY_SPEC_REQUESTOR_KEYRING), NULL, + sizeof(__kernel_ulong_t), bogus_key3, bogus_key3_str, NULL, + 0UL); + + + /* KEYCTL_UNLINK */ + do_keyctl(ARG_STR(KEYCTL_UNLINK), + sizeof(int32_t), bogus_key1, NULL, "%d", + sizeof(int32_t), ARG_STR(KEY_SPEC_GROUP_KEYRING), NULL, + 0UL); + do_keyctl(ARG_STR(KEYCTL_UNLINK), + sizeof(int32_t), ARG_STR(KEY_SPEC_REQUESTOR_KEYRING), NULL, + sizeof(int32_t), bogus_key2, NULL, "%d", 0UL); + do_keyctl(ARG_STR(KEYCTL_UNLINK), + sizeof(int32_t), ARG_STR(KEY_SPEC_REQUESTOR_KEYRING), NULL, + sizeof(__kernel_ulong_t), bogus_key3, bogus_key3_str, NULL, + 0UL); + + + /* KEYCTL_SEARCH */ + do_keyctl(ARG_STR(KEYCTL_SEARCH), + sizeof(int32_t), ARG_STR(KEY_SPEC_REQUESTOR_KEYRING), NULL, + sizeof(char *), ARG_STR(NULL), NULL, + sizeof(char *), ARG_STR(NULL), NULL, + sizeof(int32_t), 0, NULL, "%d"); + do_keyctl(ARG_STR(KEYCTL_SEARCH), + sizeof(int32_t), bogus_key1, NULL, "%d", + sizeof(char *), (char *) 0xfffffacefffffeedULL, NULL, ptr_fmt, + sizeof(char *), (char *) 0xfffff00dfffff157ULL, NULL, ptr_fmt, + sizeof(int32_t), ARG_STR(KEY_SPEC_USER_SESSION_KEYRING), NULL); + do_keyctl(ARG_STR(KEYCTL_SEARCH), + sizeof(int32_t), bogus_key2, NULL, "%d", + sizeof(char *), bogus_str, NULL, ptr_fmt, + sizeof(char *), bogus_desc, NULL, ptr_fmt, + sizeof(int32_t), bogus_key1, NULL, "%d"); + do_keyctl(ARG_STR(KEYCTL_SEARCH), + sizeof(__kernel_ulong_t), bogus_key3, bogus_key3_str, NULL, + -sizeof(short_type_str), short_type, NULL, NULL, + -sizeof(short_desc_str), short_desc, NULL, NULL, + sizeof(int32_t), bogus_key2, NULL, "%d"); + do_keyctl(ARG_STR(KEYCTL_SEARCH), + sizeof(int32_t), 0, NULL, "%d", + -sizeof(long_type_str), long_type, NULL, NULL, + -sizeof(long_type_str), long_desc, NULL, NULL, + sizeof(__kernel_ulong_t), bogus_key3, bogus_key3_str, NULL); + + + /* KEYCTL_READ */ + + /* Empty result is expected for these */ + bogus_buf1[0] = '\0'; + bogus_buf2[0] = '\0'; + + do_keyctl(ARG_STR(KEYCTL_READ), + sizeof(int32_t), bogus_key1, NULL, "%d", + sizeof(char *), ARG_STR(NULL), ptr_fmt, + sizeof(__kernel_ulong_t), + (__kernel_ulong_t) 0xfeedf157badc0dedLLU, NULL, ksize_fmt, 0UL); + do_keyctl(ARG_STR(KEYCTL_READ), + sizeof(__kernel_ulong_t), bogus_key3, bogus_key3_str, NULL, + sizeof(char *), ARG_STR(NULL), ptr_fmt, + sizeof(__kernel_ulong_t), + (__kernel_ulong_t) 0xfeedf157badc0dedLLU, NULL, ksize_fmt, 0UL); + do_keyctl(ARG_STR(KEYCTL_READ), + sizeof(int32_t), ARG_STR(KEY_SPEC_THREAD_KEYRING), NULL, + 9, (uintptr_t) bogus_buf1, NULL, NULL, + sizeof(__kernel_ulong_t), + (__kernel_ulong_t) 9, NULL, ksize_fmt, 0UL); + do_keyctl(ARG_STR(KEYCTL_READ), + sizeof(int32_t), ARG_STR(KEY_SPEC_THREAD_KEYRING), NULL, + 256, (uintptr_t) bogus_buf2, NULL, NULL, + sizeof(__kernel_ulong_t), + (__kernel_ulong_t) 256, NULL, ksize_fmt, 0UL); + + + /* KEYCTL_INSTANTIATE */ + do_keyctl(ARG_STR(KEYCTL_INSTANTIATE), + sizeof(int32_t), 0, NULL, "%d", + sizeof(char *), ARG_STR(NULL), ptr_fmt, + sizeof(__kernel_ulong_t), + (__kernel_ulong_t) 0xfeedf157badc0dedLLU, NULL, ksize_fmt, + sizeof(int32_t), 0, NULL, "%d"); + do_keyctl(ARG_STR(KEYCTL_INSTANTIATE), + sizeof(int32_t), bogus_key1, NULL, "%d", + sizeof(char *), (char *) 0xfffffacefffffeedULL, NULL, ptr_fmt, + sizeof(__kernel_ulong_t), + (__kernel_ulong_t) 0xdeadfeedLLU, NULL, ksize_fmt, + sizeof(int32_t), bogus_key1, NULL, "%d"); + do_keyctl(ARG_STR(KEYCTL_INSTANTIATE), + sizeof(int32_t), bogus_key2, NULL, "%d", + sizeof(char *), bogus_str, NULL, ptr_fmt, + sizeof(__kernel_ulong_t), + (__kernel_ulong_t) 32LLU, NULL, ksize_fmt, + sizeof(int32_t), bogus_key2, NULL, "%d"); + do_keyctl(ARG_STR(KEYCTL_INSTANTIATE), + sizeof(__kernel_ulong_t), bogus_key3, bogus_key3_str, NULL, + -sizeof(short_type_str), short_desc, NULL, NULL, + sizeof(__kernel_ulong_t), + (__kernel_ulong_t) sizeof(short_type_str) - 1, NULL, ksize_fmt, + sizeof(__kernel_ulong_t), bogus_key3, bogus_key3_str, NULL); + do_keyctl(ARG_STR(KEYCTL_INSTANTIATE), + sizeof(int32_t), ARG_STR(KEY_SPEC_GROUP_KEYRING), NULL, + -sizeof(long_type_str), long_desc, NULL, NULL, + sizeof(__kernel_ulong_t), + (__kernel_ulong_t) sizeof(long_type_str), NULL, ksize_fmt, + sizeof(int32_t), ARG_STR(KEY_SPEC_GROUP_KEYRING), NULL); + + + /* KEYCTL_NEGATE */ + do_keyctl(ARG_STR(KEYCTL_NEGATE), + sizeof(int32_t), 0, NULL, "%d", + sizeof(uint32_t), 0, NULL, "%u", + sizeof(int32_t), 0, NULL, "%d", 0UL); + do_keyctl(ARG_STR(KEYCTL_NEGATE), + sizeof(int32_t), bogus_key1, NULL, "%d", + sizeof(uint32_t), 3141592653U, NULL, "%u", + sizeof(int32_t), bogus_key1, NULL, "%d", 0UL); + do_keyctl(ARG_STR(KEYCTL_NEGATE), + sizeof(int32_t), bogus_key2, NULL, "%d", + sizeof(__kernel_ulong_t), + (__kernel_ulong_t) 0xfeedf157badc0dedLLU, "3134983661", NULL, + sizeof(int32_t), bogus_key2, NULL, "%d", 0UL); + do_keyctl(ARG_STR(KEYCTL_NEGATE), + sizeof(__kernel_ulong_t), bogus_key3, bogus_key3_str, NULL, + sizeof(__kernel_ulong_t), + (__kernel_ulong_t) 0xfeedf157badc0dedLLU, "3134983661", NULL, + sizeof(__kernel_ulong_t), bogus_key3, bogus_key3_str, NULL, + 0UL); + + + /* KEYCTL_SET_REQKEY_KEYRING */ + do_keyctl(ARG_STR(KEYCTL_SET_REQKEY_KEYRING), + sizeof(int32_t), ARG_STR(KEY_REQKEY_DEFL_NO_CHANGE), NULL, 0UL); + /* do_keyctl(ARG_STR(KEYCTL_SET_REQKEY_KEYRING), + sizeof(int32_t), + ARG_STR(KEY_REQKEY_DEFL_REQUESTOR_KEYRING), NULL, 0UL); */ + do_keyctl(ARG_STR(KEYCTL_SET_REQKEY_KEYRING), + sizeof(__kernel_ulong_t), + (__kernel_ulong_t) 0xfeedf157badc0dedLLU, + "0xbadc0ded /* KEY_REQKEY_DEFL_??? */", NULL, 0UL); + + + /* KEYCTL_SET_TIMEOUT */ + do_keyctl(ARG_STR(KEYCTL_SET_TIMEOUT), + sizeof(int32_t), 0, NULL, "%d", + sizeof(uint32_t), 0, NULL, "%u", 0UL); + do_keyctl(ARG_STR(KEYCTL_SET_TIMEOUT), + sizeof(int32_t), bogus_key1, NULL, "%d", + sizeof(uint32_t), 3141592653U, NULL, "%u", 0UL); + do_keyctl(ARG_STR(KEYCTL_SET_TIMEOUT), + sizeof(__kernel_ulong_t), bogus_key3, bogus_key3_str, NULL, + sizeof(__kernel_ulong_t), + (__kernel_ulong_t) 0xfeedf157badc0dedLLU, "3134983661", NULL, + 0UL); + + + /* KEYCTL_ASSUME_AUTHORITY */ + do_keyctl(ARG_STR(KEYCTL_ASSUME_AUTHORITY), + sizeof(int32_t), ARG_STR(KEY_SPEC_GROUP_KEYRING), NULL, 0UL); + do_keyctl(ARG_STR(KEYCTL_ASSUME_AUTHORITY), + sizeof(int32_t), bogus_key1, NULL, "%d", 0UL); + do_keyctl(ARG_STR(KEYCTL_ASSUME_AUTHORITY), + sizeof(int32_t), bogus_key2, NULL, "%d", 0UL); + do_keyctl(ARG_STR(KEYCTL_ASSUME_AUTHORITY), + sizeof(__kernel_ulong_t), bogus_key3, bogus_key3_str, NULL, + 0UL); + + + /* KEYCTL_GET_SECURITY */ + + /* Empty result is expected for these */ + bogus_buf1[0] = '\0'; + bogus_buf2[0] = '\0'; + + do_keyctl(ARG_STR(KEYCTL_GET_SECURITY), + sizeof(int32_t), bogus_key1, NULL, "%d", + sizeof(char *), ARG_STR(NULL), ptr_fmt, + sizeof(uint32_t), 0xbadc0dedU, NULL, "%u", 0UL); + do_keyctl(ARG_STR(KEYCTL_GET_SECURITY), + sizeof(__kernel_ulong_t), bogus_key3, bogus_key3_str, NULL, + sizeof(char *), ARG_STR(NULL), ptr_fmt, + sizeof(__kernel_ulong_t), + (__kernel_ulong_t) 0xfeedf157badc0dedLLU, NULL, ksize_fmt, 0UL); + do_keyctl(ARG_STR(KEYCTL_GET_SECURITY), + sizeof(int32_t), ARG_STR(KEY_SPEC_THREAD_KEYRING), NULL, + 9, (uintptr_t) bogus_buf1, NULL, NULL, + sizeof(__kernel_ulong_t), + (__kernel_ulong_t) 9, NULL, ksize_fmt, 0UL); + do_keyctl(ARG_STR(KEYCTL_GET_SECURITY), + sizeof(int32_t), ARG_STR(KEY_SPEC_THREAD_KEYRING), NULL, + 256, (uintptr_t) bogus_buf2, NULL, NULL, + sizeof(__kernel_ulong_t), + (__kernel_ulong_t) 256, NULL, ksize_fmt, 0UL); + + + /* KEYCTL_SESSION_TO_PARENT */ + do_keyctl(ARG_STR(KEYCTL_SESSION_TO_PARENT), 0UL); + + + /* KEYCTL_REJECT */ + do_keyctl(ARG_STR(KEYCTL_REJECT), + sizeof(int32_t), 0, NULL, "%d", + sizeof(uint32_t), 0, NULL, "%u", + sizeof(uint32_t), 0, NULL, "%u", + sizeof(int32_t), 0, NULL, "%d"); + do_keyctl(ARG_STR(KEYCTL_REJECT), + sizeof(int32_t), bogus_key1, NULL, "%d", + sizeof(uint32_t), 3141592653U, NULL, "%u", + sizeof(uint32_t), 2718281828U, NULL, "%u", + sizeof(int32_t), bogus_key1, NULL, "%d"); + do_keyctl(ARG_STR(KEYCTL_REJECT), + sizeof(int32_t), bogus_key2, NULL, "%d", + sizeof(__kernel_ulong_t), + (__kernel_ulong_t) 0xdeadca75facef157LLU, "4207866199", NULL, + sizeof(__kernel_ulong_t), + (__kernel_ulong_t) 0xfeedf157badc0dedLLU, "3134983661", NULL, + sizeof(int32_t), bogus_key2, NULL, "%d"); + do_keyctl(ARG_STR(KEYCTL_REJECT), + sizeof(__kernel_ulong_t), bogus_key3, bogus_key3_str, NULL, + sizeof(__kernel_ulong_t), + (__kernel_ulong_t) 0xfeedf157badc0dedLLU, "3134983661", NULL, + sizeof(uint32_t), ARG_STR(ENODEV), NULL, + sizeof(__kernel_ulong_t), bogus_key3, bogus_key3_str, NULL); + + + /* KEYCTL_INSTANTIATE_IOV */ + do_keyctl(ARG_STR(KEYCTL_INSTANTIATE_IOV), + sizeof(int32_t), 0, NULL, "%d", + sizeof(char *), ARG_STR(NULL), ptr_fmt, + sizeof(__kernel_ulong_t), + (__kernel_ulong_t) 0xfeedf157badc0dedLLU, NULL, ksize_fmt, + sizeof(int32_t), 0, NULL, "%d"); + do_keyctl(ARG_STR(KEYCTL_INSTANTIATE_IOV), + sizeof(int32_t), bogus_key1, NULL, "%d", + sizeof(char *), (char *) 0xfffffacefffffeedULL, NULL, ptr_fmt, + sizeof(__kernel_ulong_t), + (__kernel_ulong_t) 0xdeadfeedLLU, NULL, ksize_fmt, + sizeof(int32_t), bogus_key1, NULL, "%d"); + do_keyctl(ARG_STR(KEYCTL_INSTANTIATE_IOV), + sizeof(int32_t), bogus_key2, NULL, "%d", + sizeof(char *), key_iov + IOV_SIZE, NULL, ptr_fmt, + sizeof(__kernel_ulong_t), + (__kernel_ulong_t) 32LLU, NULL, ksize_fmt, + sizeof(int32_t), bogus_key2, NULL, "%d"); + do_keyctl(ARG_STR(KEYCTL_INSTANTIATE_IOV), + sizeof(__kernel_ulong_t), bogus_key3, bogus_key3_str, NULL, + sizeof(key_iov), key_iov + IOV_SIZE - 4, key_iov_str1, NULL, + sizeof(__kernel_ulong_t), (__kernel_ulong_t) 4, NULL, ksize_fmt, + sizeof(__kernel_ulong_t), bogus_key3, bogus_key3_str, NULL); + do_keyctl(ARG_STR(KEYCTL_INSTANTIATE_IOV), + sizeof(int32_t), ARG_STR(KEY_SPEC_GROUP_KEYRING), NULL, + sizeof(key_iov), key_iov, key_iov_str2, NULL, + sizeof(__kernel_ulong_t), + (__kernel_ulong_t) IOV_SIZE, NULL, ksize_fmt, + sizeof(int32_t), ARG_STR(KEY_SPEC_GROUP_KEYRING), NULL); + + + /* KEYCTL_INVALIDATE */ + do_keyctl(ARG_STR(KEYCTL_INVALIDATE), + sizeof(int32_t), ARG_STR(KEY_SPEC_GROUP_KEYRING), NULL, 0UL); + do_keyctl(ARG_STR(KEYCTL_INVALIDATE), + sizeof(int32_t), bogus_key1, NULL, "%d", 0UL); + do_keyctl(ARG_STR(KEYCTL_INVALIDATE), + sizeof(int32_t), bogus_key2, NULL, "%d", 0UL); + do_keyctl(ARG_STR(KEYCTL_INVALIDATE), + sizeof(__kernel_ulong_t), bogus_key3, bogus_key3_str, NULL, + 0UL); + + + /* KEYCTL_GET_PERSISTENT */ + do_keyctl(ARG_STR(KEYCTL_GET_PERSISTENT), + sizeof(uid_t), ARG_STR(-1), NULL, + sizeof(int32_t), ARG_STR(KEY_SPEC_GROUP_KEYRING), NULL, 0UL); + do_keyctl(ARG_STR(KEYCTL_GET_PERSISTENT), + sizeof(uid_t), 2718281828U, NULL, "%u", + sizeof(int32_t), bogus_key1, NULL, "%d", 0UL); + do_keyctl(ARG_STR(KEYCTL_GET_PERSISTENT), + sizeof(uid_t), 2718281828U, NULL, "%u", + sizeof(__kernel_ulong_t), bogus_key3, bogus_key3_str, NULL, + 0UL); + + + /* KEYCTL_DH_COMPUTE */ + do_keyctl(ARG_STR(KEYCTL_DH_COMPUTE), + sizeof(char *), ARG_STR(NULL), ptr_fmt, + sizeof(char *), ARG_STR(NULL), ptr_fmt, + sizeof(__kernel_ulong_t), + (__kernel_ulong_t) 0xfeedf157badc0dedLLU, NULL, ksize_fmt, 0UL); + do_keyctl(ARG_STR(KEYCTL_DH_COMPUTE), + sizeof(char *), kcdhp + 1, NULL, ptr_fmt, + sizeof(char *), (char *) 0xfffff157ffffdeadULL, NULL, ptr_fmt, + sizeof(__kernel_ulong_t), + (__kernel_ulong_t) 0xfeedf157badc0dedLLU, NULL, ksize_fmt, 0UL); + do_keyctl(ARG_STR(KEYCTL_DH_COMPUTE), + sizeof(kcdhp), kcdhp, kcdhp_str, NULL, + 9, (uintptr_t) bogus_buf1, NULL, NULL, + sizeof(__kernel_ulong_t), + (__kernel_ulong_t) 9, NULL, ksize_fmt, 0UL); + do_keyctl(ARG_STR(KEYCTL_DH_COMPUTE), + sizeof(kcdhp), kcdhp, kcdhp_str, NULL, + 256, (uintptr_t) bogus_buf2, NULL, NULL, + sizeof(__kernel_ulong_t), + (__kernel_ulong_t) 256, NULL, ksize_fmt, 0UL); + + + puts("+++ exited with 0 +++"); + + return 0; +} + +#else + +SKIP_MAIN_UNDEFINED("__NR_keyctl"); + +#endif diff --git a/tests/keyctl.test b/tests/keyctl.test new file mode 100755 index 0000000..59b4713 --- /dev/null +++ b/tests/keyctl.test @@ -0,0 +1,6 @@ +#!/bin/sh + +# Check keyctl syscall decoding. + +. "${srcdir=.}/init.sh" +run_strace_match_diff -a1 -s10 diff --git a/tests/request_key.c b/tests/request_key.c new file mode 100644 index 0000000..457e446 --- /dev/null +++ b/tests/request_key.c @@ -0,0 +1,124 @@ +#include "tests.h" + +#include <asm/unistd.h> + +#ifdef __NR_request_key + +# include <inttypes.h> +# include <stdio.h> +# include <unistd.h> + +void +print_val_str(const void *ptr, const char *str) +{ + if (str) + printf("%s, ", str); + else + printf("%p, ", ptr); +} + +void +do_request_key(const char *type, const char *type_str, const char *desc, + const char *desc_str, const char *info, const char *info_str, + int32_t keyring, const char *keyring_str) +{ + long rc; + + rc = syscall(__NR_request_key, type, desc, info, keyring); + printf("request_key("); + print_val_str(type, type_str); + print_val_str(desc, desc_str); + print_val_str(info, info_str); + if (keyring_str) + printf("%s", keyring_str); + else + printf("%d", keyring); + printf(") = %s\n", sprintrc(rc)); +} + +# define _STR(_arg) #_arg +# define ARG_STR(_arg) (_arg), #_arg + +int +main(void) +{ + static const char unterminated1[] = { '\1', '\2', '\3', '\4', '\5' }; + static const char unterminated2[] = { '\6', '\7', '\10', '\11', '\12' }; + static const char unterminated3[] = + { '\16', '\17', '\20', '\21', '\22' }; + + char *bogus_type = tail_memdup(unterminated1, sizeof(unterminated1)); + char *bogus_desc = tail_memdup(unterminated2, sizeof(unterminated2)); + char *bogus_info = tail_memdup(unterminated3, sizeof(unterminated3)); + + unsigned i; + unsigned j; + unsigned k; + unsigned l; + + struct { + const char *type; + const char *str; + } types[] = { + { ARG_STR(NULL) }, + { (const char *) 0xfffffee1fffffbadULL, NULL }, + { bogus_type, NULL }, + { ARG_STR("\20\21\22\23\24") }, + { ARG_STR("user") }, + }; + + struct { + const char *desc; + const char *str; + } descs[] = { + { ARG_STR(NULL) }, + { (const char *) 0xfffff00dfffffca7ULL, NULL }, + { bogus_desc, NULL }, + { ARG_STR("\25\26\27\30\31") }, + { ARG_STR("desc") }, + { "overly long description", _STR("overly long ") "..." }, + }; + + struct { + const char *info; + const char *str; + } infos[] = { + { ARG_STR(NULL) }, + { (const char *) 0xfffffacefffff157ULL, NULL }, + { bogus_info, NULL }, + { ARG_STR("\32\33\34\35\36") }, + { ARG_STR("info") }, + { "overly long info", _STR("overly long ") "..." }, + }; + + struct { + uint32_t keyring; + const char *str; + } keyrings[] = { + { ARG_STR(0) }, + { ARG_STR(1234567890) }, + { ARG_STR(-1234567890) }, + { -1, "KEY_SPEC_THREAD_KEYRING" }, + }; + + for (i = 0; i < ARRAY_SIZE(types); i++) + for (j = 0; j < ARRAY_SIZE(descs); j++) + for (k = 0; k < ARRAY_SIZE(infos); k++) + for (l = 0; l < ARRAY_SIZE(keyrings); l++) + do_request_key( + types[i].type, types[i].str, + descs[j].desc, descs[j].str, + infos[k].info, infos[k].str, + keyrings[l].keyring, + keyrings[l].str); + + puts("+++ exited with 0 +++"); + + return 0; +} + +#else + +SKIP_MAIN_UNDEFINED("__NR_request_key"); + +#endif diff --git a/tests/request_key.test b/tests/request_key.test new file mode 100755 index 0000000..c5a1629 --- /dev/null +++ b/tests/request_key.test @@ -0,0 +1,6 @@ +#!/bin/sh + +# Check request_key syscall decoding. + +. "${srcdir=.}/init.sh" +run_strace_match_diff -a1 -s12 -- 1.7.10.4 ------------------------------------------------------------------------------ _______________________________________________ Strace-devel mailing list Strace-devel@lists.sourceforge.net https://lists.sourceforge.net/lists/listinfo/strace-devel