From: Dmitry V. Levin Date: Fri, 2 Feb 2018 19:39:23 +0000 (+0000) Subject: Use kernel's fcntl.h header instead of libc's for open_mode_flags X-Git-Tag: v4.21~56 X-Git-Url: https://granicus.if.org/sourcecode?a=commitdiff_plain;h=11d1c182bae0fee61986ee79eef141a28bbbf77b;p=strace Use kernel's fcntl.h header instead of libc's for open_mode_flags As definitions of O_* macros provided by various libc implementations are usually less reliable than those provided by kernel headers, switch to use kernel's fcntl.h header. * open.c: Include instead of . Remove O_LARGEFILE fallback definitions assuming that the kernel headers provide them. * xlat/open_mode_flags.in: Add __O_SYNC after O_SYNC. Add O_TMPFILE and __O_TMPFILE before O_DIRECTORY. Remove "O_TMPFILE & ~O_DIRECTORY". * tests/open.c: Include instead of . Remove workarounds for libc O_TMPFILE implementations. * tests/openat.c: Include instead of . (test_mode_flag): New function. (main): Use it to check decoding of all access modes and file flags. * tests/gen_tests.in (openat): Add -a option. Co-Authored-by: Eugene Syromyatnikov --- diff --git a/open.c b/open.c index 90f83906..1cf82157 100644 --- a/open.c +++ b/open.c @@ -36,7 +36,7 @@ #include "defs.h" #include "xstring.h" -#include +#include /* some libcs are guilty of messing up with O_ACCMODE */ #undef O_ACCMODE @@ -45,11 +45,6 @@ #ifdef O_LARGEFILE # if O_LARGEFILE == 0 /* biarch platforms in 64-bit mode */ # undef O_LARGEFILE -# ifdef SPARC64 -# define O_LARGEFILE 0x40000 -# elif defined X86_64 || defined S390X -# define O_LARGEFILE 0100000 -# endif # endif #endif diff --git a/tests/gen_tests.in b/tests/gen_tests.in index 18f36408..7824df9d 100644 --- a/tests/gen_tests.in +++ b/tests/gen_tests.in @@ -257,7 +257,7 @@ oldselect-efault -a13 -e trace=select oldselect-efault-P -a13 -e trace=select -P /dev/full 9>>/dev/full oldstat -a32 -v -P stat.sample -P /dev/full open -a30 -P $NAME.sample -openat -P $NAME.sample +openat -a36 -P $NAME.sample osf_utimes -a21 pause -a8 -esignal=none perf_event_open -a1 diff --git a/tests/open.c b/tests/open.c index 01e89b0f..ebe96736 100644 --- a/tests/open.c +++ b/tests/open.c @@ -30,7 +30,7 @@ #ifdef __NR_open -# include +# include # include # include @@ -56,16 +56,11 @@ main(void) sample, sprintrc(fd)); } -#ifdef O_TMPFILE -# if O_TMPFILE == (O_TMPFILE & ~O_DIRECTORY) -# define STR_O_TMPFILE "O_TMPFILE" -# else -# define STR_O_TMPFILE "O_DIRECTORY|O_TMPFILE" -# endif +# ifdef O_TMPFILE fd = syscall(__NR_open, sample, O_WRONLY|O_TMPFILE, 0600); - printf("open(\"%s\", O_WRONLY|%s, 0600) = %s\n", - sample, STR_O_TMPFILE, sprintrc(fd)); -#endif /* O_TMPFILE */ + printf("open(\"%s\", O_WRONLY|O_TMPFILE, 0600) = %s\n", + sample, sprintrc(fd)); +# endif /* O_TMPFILE */ puts("+++ exited with 0 +++"); return 0; diff --git a/tests/openat.c b/tests/openat.c index 1d6765cf..8c97441a 100644 --- a/tests/openat.c +++ b/tests/openat.c @@ -1,5 +1,6 @@ /* * Copyright (c) 2016 Katerina Koukiou + * Copyright (c) 2016-2018 The strace developers. * All rights reserved. * * Redistribution and use in source and binary forms, with or without @@ -28,17 +29,36 @@ #include "tests.h" #include -#if defined __NR_openat +#ifdef __NR_openat -# include +# include # include # include +#ifdef O_TMPFILE +/* The kernel & C libraries often inline O_DIRECTORY. */ +# define STRACE_O_TMPFILE (O_TMPFILE & ~O_DIRECTORY) +#else +# define STRACE_O_TMPFILE 0 +#endif + +static const char sample[] = "openat.sample"; + +static void +test_mode_flag(unsigned int mode_val, const char *mode_str, + unsigned int flag_val, const char *flag_str) +{ + long rc = syscall(__NR_openat, -1, sample, mode_val | flag_val, 0); + printf("openat(-1, \"%s\", %s%s%s%s) = %s\n", + sample, mode_str, + flag_val ? "|" : "", flag_str, + flag_val & (O_CREAT | STRACE_O_TMPFILE) ? ", 000" : "", + sprintrc(rc)); +} + int main(void) { - static const char sample[] = "openat.sample"; - long fd = syscall(__NR_openat, -100, sample, O_RDONLY|O_CREAT, 0400); printf("openat(AT_FDCWD, \"%s\", O_RDONLY|O_CREAT, 0400) = %s\n", sample, sprintrc(fd)); @@ -53,6 +73,54 @@ main(void) sample, sprintrc(fd)); } + struct { + unsigned int val; + const char *str; + } modes[] = { + { ARG_STR(O_RDONLY) }, + { ARG_STR(O_WRONLY) }, + { ARG_STR(O_RDWR) }, + { ARG_STR(O_ACCMODE) } + }, flags[] = { + { ARG_STR(O_APPEND) }, + { ARG_STR(O_DIRECT) }, + { ARG_STR(O_DIRECTORY) }, + { ARG_STR(O_EXCL) }, + { ARG_STR(O_LARGEFILE) }, + { ARG_STR(O_NOATIME) }, + { ARG_STR(O_NOCTTY) }, + { ARG_STR(O_NOFOLLOW) }, + { ARG_STR(O_NONBLOCK) }, + { ARG_STR(O_SYNC) }, + { ARG_STR(O_TRUNC) }, + { ARG_STR(O_CREAT) }, +# ifdef O_CLOEXEC + { ARG_STR(O_CLOEXEC) }, +# endif +# ifdef O_DSYNC + { ARG_STR(O_DSYNC) }, +# endif +# ifdef __O_SYNC + { ARG_STR(__O_SYNC) }, +# endif +# ifdef O_PATH + { ARG_STR(O_PATH) }, +# endif +# ifdef O_TMPFILE + { ARG_STR(O_TMPFILE) }, +# endif +# ifdef __O_TMPFILE + { ARG_STR(__O_TMPFILE) }, +# endif + { ARG_STR(0x80000000) }, + { 0, "" } + }; + + for (unsigned int m = 0; m < ARRAY_SIZE(modes); ++m) + for (unsigned int f = 0; f < ARRAY_SIZE(flags); ++f) + test_mode_flag(modes[m].val, modes[m].str, + flags[f].val, flags[f].str); + puts("+++ exited with 0 +++"); return 0; } diff --git a/xlat/open_mode_flags.in b/xlat/open_mode_flags.in index 30bed260..e2371055 100644 --- a/xlat/open_mode_flags.in +++ b/xlat/open_mode_flags.in @@ -4,7 +4,9 @@ O_NOCTTY O_TRUNC O_APPEND O_NONBLOCK +/* O_SYNC should be listed before O_DSYNC and __O_SYNC */ O_SYNC +__O_SYNC O_ASYNC O_DSYNC O_RSYNC @@ -14,15 +16,14 @@ O_NDELAY O_PRIV O_DIRECT O_LARGEFILE -O_DIRECTORY O_NOFOLLOW O_NOATIME O_CLOEXEC O_PATH -#if defined(O_TMPFILE) && defined(O_DIRECTORY) -/* The kernel & C libraries often inline O_DIRECTORY */ -{ O_TMPFILE & ~O_DIRECTORY, "O_TMPFILE" }, -#endif +/* O_TMPFILE should be listed before O_DIRECTORY and __O_TMPFILE */ +O_TMPFILE +__O_TMPFILE +O_DIRECTORY FNDELAY FAPPEND FMARK