]> granicus.if.org Git - strace/blobdiff - basic_filters.c
tests: move F_OFD_SETLK* checks from fcntl64.c to fcntl-common.c
[strace] / basic_filters.c
index be0c4c5120327b79e20e6313e069c4eb95d8d869..4ea23b54044227dcfaa2cb8dd0814fd42459cf7c 100644 (file)
@@ -1,6 +1,6 @@
 /*
  * Copyright (c) 2016 Dmitry V. Levin <ldv@altlinux.org>
- * Copyright (c) 2016-2017 The strace developers.
+ * Copyright (c) 2016-2018 The strace developers.
  * All rights reserved.
  *
  * Redistribution and use in source and binary forms, with or without
@@ -38,14 +38,12 @@ qualify_syscall_number(const char *s, struct number_set *set)
        if (n < 0)
                return false;
 
-       unsigned int p;
        bool done = false;
 
-       for (p = 0; p < SUPPORTED_PERSONALITIES; ++p) {
-               if ((unsigned) n >= nsyscall_vec[p]) {
+       for (unsigned int p = 0; p < SUPPORTED_PERSONALITIES; ++p) {
+               if ((unsigned) n >= nsyscall_vec[p])
                        continue;
-               }
-               add_number_to_set(n, &set[p]);
+               add_number_to_set_array(n, set, p);
                done = true;
        }
 
@@ -71,12 +69,10 @@ qualify_syscall_regex(const char *s, struct number_set *set)
        if ((rc = regcomp(&preg, s, REG_EXTENDED | REG_NOSUB)) != 0)
                regerror_msg_and_die(rc, &preg, "regcomp", s);
 
-       unsigned int p;
        bool found = false;
-       for (p = 0; p < SUPPORTED_PERSONALITIES; ++p) {
-               unsigned int i;
 
-               for (i = 0; i < nsyscall_vec[p]; ++i) {
+       for (unsigned int p = 0; p < SUPPORTED_PERSONALITIES; ++p) {
+               for (unsigned int i = 0; i < nsyscall_vec[p]; ++i) {
                        if (!sysent_vec[p][i].sys_name)
                                continue;
                        rc = regexec(&preg, sysent_vec[p][i].sys_name,
@@ -85,7 +81,7 @@ qualify_syscall_regex(const char *s, struct number_set *set)
                                continue;
                        else if (rc)
                                regerror_msg_and_die(rc, &preg, "regexec", s);
-                       add_number_to_set(i, &set[p]);
+                       add_number_to_set_array(i, set, p);
                        found = true;
                }
        }
@@ -101,13 +97,6 @@ lookup_class(const char *s)
                const char *name;
                unsigned int value;
        } syscall_class[] = {
-               { "desc",       TRACE_DESC      },
-               { "file",       TRACE_FILE      },
-               { "memory",     TRACE_MEMORY    },
-               { "process",    TRACE_PROCESS   },
-               { "signal",     TRACE_SIGNAL    },
-               { "ipc",        TRACE_IPC       },
-               { "network",    TRACE_NETWORK   },
                { "%desc",      TRACE_DESC      },
                { "%file",      TRACE_FILE      },
                { "%memory",    TRACE_MEMORY    },
@@ -122,13 +111,20 @@ lookup_class(const char *s)
                { "%statfs",    TRACE_STATFS    },
                { "%fstatfs",   TRACE_FSTATFS   },
                { "%%statfs",   TRACE_STATFS_LIKE       },
+               { "%pure",      TRACE_PURE      },
+               /* legacy class names */
+               { "desc",       TRACE_DESC      },
+               { "file",       TRACE_FILE      },
+               { "memory",     TRACE_MEMORY    },
+               { "process",    TRACE_PROCESS   },
+               { "signal",     TRACE_SIGNAL    },
+               { "ipc",        TRACE_IPC       },
+               { "network",    TRACE_NETWORK   },
        };
 
-       unsigned int i;
-       for (i = 0; i < ARRAY_SIZE(syscall_class); ++i) {
-               if (strcmp(s, syscall_class[i].name) == 0) {
+       for (unsigned int i = 0; i < ARRAY_SIZE(syscall_class); ++i) {
+               if (strcmp(s, syscall_class[i].name) == 0)
                        return syscall_class[i].value;
-               }
        }
 
        return 0;
@@ -141,37 +137,42 @@ qualify_syscall_class(const char *s, struct number_set *set)
        if (!n)
                return false;
 
-       unsigned int p;
-       for (p = 0; p < SUPPORTED_PERSONALITIES; ++p) {
-               unsigned int i;
-
-               for (i = 0; i < nsyscall_vec[p]; ++i) {
-                       if (!sysent_vec[p][i].sys_name
-                           || (sysent_vec[p][i].sys_flags & n) != n) {
-                               continue;
-                       }
-                       add_number_to_set(i, &set[p]);
+       for (unsigned int p = 0; p < SUPPORTED_PERSONALITIES; ++p) {
+               for (unsigned int i = 0; i < nsyscall_vec[p]; ++i) {
+                       if (sysent_vec[p][i].sys_name &&
+                           (sysent_vec[p][i].sys_flags & n) == n)
+                               add_number_to_set_array(i, set, p);
                }
        }
 
        return true;
 }
 
+kernel_long_t
+scno_by_name(const char *s, unsigned int p, kernel_long_t start)
+{
+       if (p >= SUPPORTED_PERSONALITIES)
+               return -1;
+
+       for (kernel_ulong_t i = start; i < nsyscall_vec[p]; ++i) {
+               if (sysent_vec[p][i].sys_name &&
+                   strcmp(s, sysent_vec[p][i].sys_name) == 0)
+                       return i;
+       }
+
+       return -1;
+}
+
 static bool
 qualify_syscall_name(const char *s, struct number_set *set)
 {
-       unsigned int p;
        bool found = false;
 
-       for (p = 0; p < SUPPORTED_PERSONALITIES; ++p) {
-               unsigned int i;
-
-               for (i = 0; i < nsyscall_vec[p]; ++i) {
-                       if (!sysent_vec[p][i].sys_name
-                           || strcmp(s, sysent_vec[p][i].sys_name)) {
-                               continue;
-                       }
-                       add_number_to_set(i, &set[p]);
+       for (unsigned int p = 0; p < SUPPORTED_PERSONALITIES; ++p) {
+               for (kernel_long_t scno = 0;
+                    (scno = scno_by_name(s, p, scno)) >= 0;
+                    ++scno) {
+                       add_number_to_set_array(scno, set, p);
                        found = true;
                }
        }
@@ -202,41 +203,32 @@ qualify_syscall(const char *token, struct number_set *set)
  * according to STR specification.
  */
 void
-qualify_syscall_tokens(const char *const str, struct number_set *const set,
-                      const char *const name)
+qualify_syscall_tokens(const char *const str, struct number_set *const set)
 {
        /* Clear all sets. */
-       unsigned int p;
-       for (p = 0; p < SUPPORTED_PERSONALITIES; ++p) {
-               if (set[p].nslots)
-                       memset(set[p].vec, 0,
-                              sizeof(*set[p].vec) * set[p].nslots);
-               set[p].not = false;
-       }
+       clear_number_set_array(set, SUPPORTED_PERSONALITIES);
 
        /*
         * Each leading ! character means inversion
         * of the remaining specification.
         */
        const char *s = str;
-handle_inversion:
        while (*s == '!') {
-               for (p = 0; p < SUPPORTED_PERSONALITIES; ++p) {
-                       set[p].not = !set[p].not;
-               }
+               invert_number_set_array(set, SUPPORTED_PERSONALITIES);
                ++s;
        }
 
        if (strcmp(s, "none") == 0) {
                /*
                 * No syscall numbers are added to sets.
-                * Subsequent is_number_in_set invocations
+                * Subsequent is_number_in_set* invocations
                 * will return set[p]->not.
                 */
                return;
        } else if (strcmp(s, "all") == 0) {
-               s = "!none";
-               goto handle_inversion;
+               /* "all" == "!none" */
+               invert_number_set_array(set, SUPPORTED_PERSONALITIES);
+               return;
        }
 
        /*
@@ -248,22 +240,19 @@ handle_inversion:
         */
        char *copy = xstrdup(s);
        char *saveptr = NULL;
-       const char *token;
        bool done = false;
 
-       for (token = strtok_r(copy, ",", &saveptr); token;
-            token = strtok_r(NULL, ",", &saveptr)) {
+       for (const char *token = strtok_r(copy, ",", &saveptr);
+            token; token = strtok_r(NULL, ",", &saveptr)) {
                done = qualify_syscall(token, set);
-               if (!done) {
-                       error_msg_and_die("invalid %s '%s'", name, token);
-               }
+               if (!done)
+                       error_msg_and_die("invalid system call '%s'", token);
        }
 
        free(copy);
 
-       if (!done) {
-               error_msg_and_die("invalid %s '%s'", name, str);
-       }
+       if (!done)
+               error_msg_and_die("invalid system call '%s'", str);
 }
 
 /*
@@ -274,30 +263,29 @@ qualify_tokens(const char *const str, struct number_set *const set,
               string_to_uint_func func, const char *const name)
 {
        /* Clear the set. */
-       if (set->nslots)
-               memset(set->vec, 0, sizeof(*set->vec) * set->nslots);
-       set->not = false;
+       clear_number_set_array(set, 1);
 
        /*
         * Each leading ! character means inversion
         * of the remaining specification.
         */
        const char *s = str;
-handle_inversion:
        while (*s == '!') {
-               set->not = !set->not;
+               invert_number_set_array(set, 1);
                ++s;
        }
 
        if (strcmp(s, "none") == 0) {
                /*
                 * No numbers are added to the set.
-                * Subsequent is_number_in_set invocations will return set->not.
+                * Subsequent is_number_in_set* invocations
+                * will return set->not.
                 */
                return;
        } else if (strcmp(s, "all") == 0) {
-               s = "!none";
-               goto handle_inversion;
+               /* "all" == "!none" */
+               invert_number_set_array(set, 1);
+               return;
        }
 
        /*
@@ -309,22 +297,19 @@ handle_inversion:
         */
        char *copy = xstrdup(s);
        char *saveptr = NULL;
-       const char *token;
        int number = -1;
 
-       for (token = strtok_r(copy, ",", &saveptr); token;
-            token = strtok_r(NULL, ",", &saveptr)) {
+       for (const char *token = strtok_r(copy, ",", &saveptr);
+            token; token = strtok_r(NULL, ",", &saveptr)) {
                number = func(token);
-               if (number < 0) {
+               if (number < 0)
                        error_msg_and_die("invalid %s '%s'", name, token);
-               }
 
                add_number_to_set(number, set);
        }
 
        free(copy);
 
-       if (number < 0) {
+       if (number < 0)
                error_msg_and_die("invalid %s '%s'", name, str);
-       }
 }