On Fri, Aug 11, 2017 at 05:43:52PM +0700, Nikolay Marchuk wrote: > * tests/filtering_fd-syntax.test: New file. > * tests/filtering_fd.c: Likewise. > * tests/filtering_fd.test: Likewise. > * tests/options-syntax.test: Remove fd filtering checks. > * tests/.gitignore: Add filtering_fd. > * tests/Makefile.am (check_PROGRAMS): Add filtering_fd. > (MISC_TESTS): Add filering_fd-syntax.test, filtering_fd.test. > --- > tests/.gitignore | 1 + > tests/Makefile.am | 3 + > tests/filtering_fd-syntax.test | 71 +++++++++++++++ > tests/filtering_fd.c | 202 > +++++++++++++++++++++++++++++++++++++++++ > tests/filtering_fd.test | 29 ++++++ > tests/options-syntax.test | 11 --- > 6 files changed, 306 insertions(+), 11 deletions(-) > create mode 100755 tests/filtering_fd-syntax.test > create mode 100644 tests/filtering_fd.c > create mode 100755 tests/filtering_fd.test > > diff --git a/tests/.gitignore b/tests/.gitignore > index 16c2ca07..d08bea1d 100644 > --- a/tests/.gitignore > +++ b/tests/.gitignore > @@ -70,6 +70,7 @@ fflush > file_handle > file_ioctl > filter-unavailable > +filtering_fd > finit_module > flock > fork-f > diff --git a/tests/Makefile.am b/tests/Makefile.am > index 6b90d710..5db04749 100644 > --- a/tests/Makefile.am > +++ b/tests/Makefile.am > @@ -92,6 +92,7 @@ check_PROGRAMS = $(PURE_EXECUTABLES) \ > execve-v \ > execveat-v \ > filter-unavailable \ > + filtering_fd \ > fork-f \ > getpid \ > getppid \ > @@ -257,6 +258,8 @@ MISC_TESTS = \ > detach-stopped.test \ > filter-unavailable.test \ > fflush.test \ > + filtering_fd-syntax.test \ > + filtering_fd.test \ > filtering_syscall-syntax.test \ > get_regs.test \ > interactive_block.test \ > diff --git a/tests/filtering_fd-syntax.test b/tests/filtering_fd-syntax.test > new file mode 100755 > index 00000000..c885aa88 > --- /dev/null > +++ b/tests/filtering_fd-syntax.test > @@ -0,0 +1,71 @@ > +#!/bin/sh > +# > +# Check fd set parsing syntax. > +# > +# Copyright (c) 2017 Nikolay Marchuk <marchuk.nikola...@gmail.com> > +# All rights reserved. > +# > +# Redistribution and use in source and binary forms, with or without > +# modification, are permitted provided that the following conditions > +# are met: > +# 1. Redistributions of source code must retain the above copyright > +# notice, this list of conditions and the following disclaimer. > +# 2. Redistributions in binary form must reproduce the above copyright > +# notice, this list of conditions and the following disclaimer in the > +# documentation and/or other materials provided with the distribution. > +# 3. The name of the author may not be used to endorse or promote products > +# derived from this software without specific prior written permission. > +# > +# THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR > +# IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES > +# OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. > +# IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, > +# INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT > +# NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, > +# DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY > +# THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT > +# (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF > +# THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. > + > +. "${srcdir=.}/syntax.sh" > + > +check_fd_invalid() > +{ > + check_e "invalid descriptor '$1'" -e "trace(fd $2 && fd 0)" > + check_e "invalid descriptor '$1'" -e "read=$2" > + check_e "invalid descriptor '$1'" -e "write=$2" > +} > + > +for arg in '' , ,, \ > + \! \ > + -1 -42 \ > + not_fd \ > + 2147483648 \ > + 4294967296 \ > + ; do > + check_fd_invalid "$arg" "$arg" > +done > + > +check_fd_invalid '!' '0,!' > + > +check_e "invalid descriptor '!'" -e "trace(fd !, && fd 0)" > +check_e "invalid descriptor '!,'" -e "read=!," > +check_e "invalid descriptor '!,'" -e "write=!," > + > +check_fd_inversion() > +{ > + check_e "invalid descriptor '!$1'" -e "trace(fd !$2 && fd 0)" > + check_e "invalid descriptor '$1'" -e "read=!$2" > + check_e "invalid descriptor '$1'" -e "write=!$2" > +} > + > +for arg in -1 -42 \ > + not_fd \ > + 2147483648 \ > + 4294967296 \ > + ; do > + check_fd_inversion "$arg" "$arg" > +done > + > +check_e "invalid descriptor '!1'" -e "trace(fd \!1)" > +check_e "invalid descriptor '!2'" -e "trace(fd \!2)" > diff --git a/tests/filtering_fd.c b/tests/filtering_fd.c > new file mode 100644 > index 00000000..f09a6782 > --- /dev/null > +++ b/tests/filtering_fd.c > @@ -0,0 +1,202 @@ > +/* > + * Check decoding of non-standard fd filters > + * > + * Copyright (c) 2017 Nikolay Marchuk <marchuk.nikola...@gmail.com> > + * All rights reserved. > + * > + * Redistribution and use in source and binary forms, with or without > + * modification, are permitted provided that the following conditions > + * are met: > + * 1. Redistributions of source code must retain the above copyright > + * notice, this list of conditions and the following disclaimer. > + * 2. Redistributions in binary form must reproduce the above copyright > + * notice, this list of conditions and the following disclaimer in the > + * documentation and/or other materials provided with the distribution. > + * 3. The name of the author may not be used to endorse or promote products > + * derived from this software without specific prior written permission. > + * > + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR > + * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES > + * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. > + * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, > + * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT > + * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, > + * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY > + * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT > + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF > + * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. > + */ > + > +#include "tests.h" > +#include <asm/unistd.h> > +#include <stdio.h> > +#include <stdlib.h> > +#include <unistd.h> > +#include <sys/mman.h> > + > +#define FD_TRACED_DEFAULT 5 > + > +#ifdef __NR_dup2 > +void > +test_dup2(int fd_base) > +{ > + int rc = dup2(fd_base, -1); > + printf("dup2(%d, -1) = %s\n", fd_base, sprintrc(rc)); > + dup2(fd_base + 1, -1); > + > + rc = dup2(-1, fd_base); > + printf("dup2(-1, %d) = %s\n", fd_base, sprintrc(rc)); > + dup2(-1, fd_base + 1); > +} > +#else > +void > +test_dup2(int fd_base) > +{ > +} You can write it in a single line:
void test_dup2(int fd_base) {} but it's more lake a matter of taste. > +#endif > + > +#ifdef __NR_linkat > +void > +test_linkat(int fd_base) > +{ > + int rc = linkat(fd_base, "old", -1, "new", 0); > + printf("linkat(%d, \"old\", -1, \"new\", 0) = %s\n", > + fd_base, sprintrc(rc)); > + linkat(fd_base + 1, "old", -1, "new", 0); > + > + rc = linkat(-1, "old", fd_base, "new", 0); > + printf("linkat(-1, \"old\", %d, \"new\", 0) = %s\n", > + fd_base, sprintrc(rc)); > + linkat(-1, "old", fd_base + 1, "new", 0); > +} > +#else > +void > +test_linkat(int fd_base) > +{ > +} > +#endif > + > +#ifdef __NR_symlinkat > +void > +test_symlinkat(int fd_base) > +{ > + int rc = symlinkat("new", fd_base, "old"); > + printf("symlinkat(\"new\", %d, \"old\") = %s\n", > + fd_base, sprintrc(rc)); > + symlinkat("new", fd_base + 1, "old"); > +} > +#else > +void > +test_symlinkat(int fd_base) > +{ > +} > +#endif > + > +#ifdef __NR_epoll_ctl > +# include <sys/epoll.h> > +void > +test_epoll(int fd_base) > +{ > + int rc = epoll_ctl(-1, EPOLL_CTL_ADD, fd_base, NULL); > + printf("epoll_ctl(-1, EPOLL_CTL_ADD, %d, NULL) = %s\n", > + fd_base, sprintrc(rc)); > + epoll_ctl(-1, EPOLL_CTL_ADD, fd_base + 1, NULL); > +} > +#else > +void > +test_epoll(int fd_base) > +{ > +} > +#endif > + > +#if defined HAVE_SYS_FANOTIFY_H && defined HAVE_FANOTIFY_MARK && \ > + defined __NR_fanotify_mark > +# include <sys/fanotify.h> > +void > +test_fanotify_mark(int fd_base) > +{ > + int rc = fanotify_mark(-1, 0, 0, fd_base, "."); > + printf("fanotify_mark(-1, 0, 0, %d, \".\") = %s\n", > + fd_base, sprintrc(rc)); > + fanotify_mark(-1, 0, 0, fd_base + 1, "."); > +} > +#else > +void > +test_fanotify_mark(int fd_base) > +{ > +} > +#endif > + > +#if defined __NR_select || defined __NR__newselect > +# include <sys/select.h> > +void > +test_select(int fd_base) > +{ > + int rc; > + fd_set positive_set, negative_set; > + > + FD_ZERO(&positive_set); > + FD_SET(fd_base, &positive_set); > + FD_ZERO(&negative_set); > + FD_SET(fd_base + 1, &negative_set); > +# ifndef __NR__newselect > + rc = syscall(__NR_select, fd_base + 1, &positive_set, NULL, NULL, NULL); > + printf("select(%d, [%d], NULL, NULL, NULL) = %s\n", > + fd_base + 1, fd_base, sprintrc(rc)); > + syscall(__NR_select, fd_base + 2, &negative_set, NULL, NULL,NULL); > +# else > + rc = syscall(__NR__newselect, fd_base + 1, &positive_set, NULL, NULL, > + NULL); > + printf("_newselect(%d, [%d], NULL, NULL, NULL) = %s\n", > + fd_base + 1, fd_base, sprintrc(rc)); > + syscall(__NR__newselect, fd_base + 2, &negative_set, NULL, NULL, NULL); > +# endif > +} > +#else > +void > +test_select(int fd_base) > +{ > +} > +#endif > + > +#ifdef __NR_poll > +# include <poll.h> > +void > +test_poll(int fd_base) > +{ > + struct pollfd positive_fds = {.fd = fd_base, .events = POLLIN}; > + struct pollfd negative_fds = {.fd = fd_base + 1, .events = POLLIN}; > + > + poll(&positive_fds, 1, 1); > + printf("poll([{fd=%d, events=POLLIN}], 1, 1) = 1 " > + "([{fd=%d, revents=POLLNVAL}])\n", fd_base, fd_base); > + poll(&negative_fds, 1, 1); > +} > +#else > +void > +test_poll(int fd_base) > +{ > +} > +#endif > + > +int > +main(int argc, char **argv) > +{ > + const char *const name = argc > 1 ? argv[1] : "mmap"; > + int fd_base = argc > 2 ? atoi(argv[2]) : FD_TRACED_DEFAULT; Ugh. strtol is better than atoi. > + > + Excess empty line. > + test_dup2(fd_base); > + test_linkat(fd_base); > + mmap(NULL, 0, PROT_NONE, MAP_FILE, fd_base, 0); > + printf("%s(NULL, 0, PROT_NONE, MAP_FILE, %d, 0) = -1 EBADF (%m)\n", > + name, fd_base); > + test_symlinkat(fd_base); > + test_epoll(fd_base); > + test_fanotify_mark(fd_base); > + test_select(fd_base); > + test_poll(fd_base); I'm not quite sure in which order these are sorted. If there's no particular order, moving mmap() to the beginning or end of the check call part would be preferable. > + > + puts("+++ exited with 0 +++"); > + return 0; > +} > diff --git a/tests/filtering_fd.test b/tests/filtering_fd.test > new file mode 100755 > index 00000000..5c0b1743 > --- /dev/null > +++ b/tests/filtering_fd.test > @@ -0,0 +1,29 @@ > +#!/bin/sh > + > +# Check fd filtering > + > +. "${srcdir=.}/init.sh" > + > +check_prog grep > +check_prog sed > +run_prog > /dev/null > + > +fd_base=5 > + > +syscall= > +for n in mmap mmap2; do > + $STRACE -e$n -h > /dev/null && syscall=$syscall,$n > +done > +run_strace -e "trace(syscall $syscall && fd $fd_base)" $args > /dev/null > + > +if grep '^mmap(NULL, 0, PROT_NONE,' < "$LOG" > /dev/null; then > + mmap=mmap > +elif grep '^mmap2(NULL, 0, PROT_NONE,' < "$LOG" > /dev/null; then > + mmap=mmap2 > +else > + dump_log_and_fail_with "mmap/mmap2 not found in $STRACE $args output" > +fi > + > +run_prog "../$NAME" "$mmap" "$fd_base" > /dev/null > +run_strace -a12 -e "trace(fd $fd_base)" $args > "$EXP" > +match_diff "$LOG" "$EXP" > diff --git a/tests/options-syntax.test b/tests/options-syntax.test > index 47f6b66e..f13506ea 100755 > --- a/tests/options-syntax.test > +++ b/tests/options-syntax.test > @@ -37,17 +37,6 @@ check_e "Invalid process id: 'a'" -p 1,a > check_e "Syscall 'chdir' for -b isn't supported" -b chdir > check_e "Syscall 'chdir' for -b isn't supported" -b execve -b chdir > > -check_e "invalid descriptor '-1'" -eread=-1 > -check_e "invalid descriptor '-42'" -ewrite=-42 > -check_e "invalid descriptor '2147483648'" -eread=2147483648 > -check_e "invalid descriptor '4294967296'" -ewrite=4294967296 > -check_e "invalid descriptor 'foo'" -eread=foo > -check_e "invalid descriptor ''" -ewrite= > -check_e "invalid descriptor ','" -eread=, > -check_e "invalid descriptor '!'" -ewrite='!' > -check_e "invalid descriptor '!'" -eread='0,!' > -check_e "invalid descriptor '!,'" -ewrite='!,' Note that added checks have quite a different syntax than these. > - > check_h 'must have PROG [ARGS] or -p PID' > check_h 'PROG [ARGS] must be specified with -D' -D -p $$ > check_h '-c and -C are mutually exclusive' -c -C true > -- > 2.11.0 ------------------------------------------------------------------------------ Check out the vibrant tech community on one of the world's most engaging tech sites, Slashdot.org! http://sdm.link/slashdot _______________________________________________ Strace-devel mailing list Strace-devel@lists.sourceforge.net https://lists.sourceforge.net/lists/listinfo/strace-devel