Add support for personality designation in syscall qualifications
* syscall.c (personality_designators): New array. * defs.h (personality_designators): New declaration. * basic_filters.c (qualify_syscall_separate_personality, qualify_syscall_number_personality): New functions. (qualify_syscall_number): Use qualify_syscall_separate_personality for checking for a personality specification, call qualify_syscall_number_personality for setting number set for specific personality. (qualify_syscall_name_personality): New function. (qualify_syscall_name): Use qualify_syscall_separate_personality for checking for a personality specification, call qualify_syscall_name_personality for setting number set for specific personality. * strace.1.in (.SS Filtering): Document it. * NEWS: Mention it. Co-Authored-by: Dmitry V. Levin <ldv@altlinux.org> Closes: https://github.com/strace/strace/issues/35
This commit is contained in:
parent
4a329a0677
commit
3fedf07869
2
NEWS
2
NEWS
@ -19,6 +19,8 @@ Noteworthy changes in release ?.?? (????-??-??)
|
||||
using --enable-stacktrace option.
|
||||
* Added -X option for configuring xlat output formatting (addresses
|
||||
Debian bug #692915).
|
||||
* Added support for personality designation ("64", "32", or "x32") to syscall
|
||||
qualifications in -e trace expressions.
|
||||
* Implemented injection of syscalls with no side effects as an alternative
|
||||
to injection of an invalid syscall (-e inject=SET:syscall= expression).
|
||||
* Improved support for reproducible builds (addresses Debian bug #896016).
|
||||
|
109
basic_filters.c
109
basic_filters.c
@ -27,25 +27,82 @@
|
||||
*/
|
||||
|
||||
#include "defs.h"
|
||||
#include "number_set.h"
|
||||
#include "filter.h"
|
||||
|
||||
#include <regex.h>
|
||||
|
||||
#include "filter.h"
|
||||
#include "number_set.h"
|
||||
#include "xstring.h"
|
||||
|
||||
|
||||
/**
|
||||
* Checks whether a @-separated personality specification suffix is present.
|
||||
* Personality suffix is a one of strings stored in personality_designators
|
||||
* array.
|
||||
*
|
||||
* @param[in] s Specification string to check.
|
||||
* @param[out] p Where to store personality number if it is found.
|
||||
* @return If personality is found, the provided string is copied without
|
||||
* suffix and returned as a result (callee should de-alllocate it
|
||||
* with free() after use), and personality number is written to p.
|
||||
* Otherwise, NULL is returned and p is untouched.
|
||||
*/
|
||||
static char *
|
||||
qualify_syscall_separate_personality(const char *s, unsigned int *p)
|
||||
{
|
||||
char *pos = strchr(s, '@');
|
||||
|
||||
if (!pos)
|
||||
return NULL;
|
||||
|
||||
for (unsigned int i = 0; i < SUPPORTED_PERSONALITIES; i++) {
|
||||
if (!strcmp(pos + 1, personality_designators[i])) {
|
||||
*p = i;
|
||||
return xstrndup(s, pos - s);
|
||||
}
|
||||
}
|
||||
|
||||
error_msg_and_help("incorrect personality designator '%s'"
|
||||
" in qualification '%s'", pos + 1, s);
|
||||
}
|
||||
|
||||
static bool
|
||||
qualify_syscall_number_personality(int n, unsigned int p,
|
||||
struct number_set *set)
|
||||
{
|
||||
if ((unsigned int) n >= nsyscall_vec[p])
|
||||
return false;
|
||||
|
||||
add_number_to_set_array(n, set, p);
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
static bool
|
||||
qualify_syscall_number(const char *s, struct number_set *set)
|
||||
{
|
||||
int n = string_to_uint(s);
|
||||
unsigned int p;
|
||||
char *num_str = qualify_syscall_separate_personality(s, &p);
|
||||
int n;
|
||||
|
||||
if (num_str) {
|
||||
n = string_to_uint(num_str);
|
||||
free(num_str);
|
||||
|
||||
if (n < 0)
|
||||
return false;
|
||||
|
||||
return qualify_syscall_number_personality(n, p, set);
|
||||
}
|
||||
|
||||
n = string_to_uint(s);
|
||||
if (n < 0)
|
||||
return false;
|
||||
|
||||
bool done = false;
|
||||
|
||||
for (unsigned int p = 0; p < SUPPORTED_PERSONALITIES; ++p) {
|
||||
if ((unsigned) n >= nsyscall_vec[p])
|
||||
continue;
|
||||
add_number_to_set_array(n, set, p);
|
||||
done = true;
|
||||
}
|
||||
for (p = 0; p < SUPPORTED_PERSONALITIES; ++p)
|
||||
done |= qualify_syscall_number_personality(n, p, set);
|
||||
|
||||
return done;
|
||||
}
|
||||
@ -164,22 +221,40 @@ scno_by_name(const char *s, unsigned int p, kernel_long_t start)
|
||||
}
|
||||
|
||||
static bool
|
||||
qualify_syscall_name(const char *s, struct number_set *set)
|
||||
qualify_syscall_name_personality(const char *s, unsigned int p,
|
||||
struct number_set *set)
|
||||
{
|
||||
bool found = false;
|
||||
|
||||
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;
|
||||
}
|
||||
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;
|
||||
}
|
||||
|
||||
return found;
|
||||
}
|
||||
|
||||
static bool
|
||||
qualify_syscall_name(const char *s, struct number_set *set)
|
||||
{
|
||||
unsigned int p;
|
||||
char *name_str = qualify_syscall_separate_personality(s, &p);
|
||||
bool found = false;
|
||||
|
||||
if (name_str) {
|
||||
found = qualify_syscall_name_personality(name_str, p, set);
|
||||
free(name_str);
|
||||
|
||||
return found;
|
||||
}
|
||||
|
||||
for (p = 0; p < SUPPORTED_PERSONALITIES; ++p)
|
||||
found |= qualify_syscall_name_personality(s, p, set);
|
||||
|
||||
return found;
|
||||
}
|
||||
|
||||
static bool
|
||||
qualify_syscall(const char *token, struct number_set *set)
|
||||
{
|
||||
|
2
defs.h
2
defs.h
@ -1370,6 +1370,8 @@ extern const struct_sysent sysent0[];
|
||||
extern const struct_ioctlent ioctlent0[];
|
||||
|
||||
extern const char *const personality_names[];
|
||||
/* Personality designators to be used for specifying personality */
|
||||
extern const char *const personality_designators[];
|
||||
|
||||
#if SUPPORTED_PERSONALITIES > 1
|
||||
extern const struct_sysent *sysent;
|
||||
|
@ -446,6 +446,9 @@ means to trace every system call except
|
||||
.BR open .
|
||||
Question mark before the syscall qualification allows suppression of error
|
||||
in case no syscalls matched the qualification provided.
|
||||
Appending one of "@64", "@32", or "@x32" suffixes to the syscall qualification
|
||||
allows specifying syscalls only for the 64-bit, 32-bit, or 32-on-64-bit
|
||||
personality, respectively.
|
||||
In addition, the special values
|
||||
.B all
|
||||
and
|
||||
|
12
syscall.c
12
syscall.c
@ -191,6 +191,18 @@ const char *const personality_names[] =
|
||||
# endif
|
||||
;
|
||||
|
||||
const char *const personality_designators[] =
|
||||
# if defined X86_64
|
||||
{ "64", "32", "x32" }
|
||||
# elif defined X32
|
||||
{ "x32", "32" }
|
||||
# elif SUPPORTED_PERSONALITIES == 2
|
||||
{ "64", "32" }
|
||||
# else
|
||||
{ STRINGIFY_VAL(__WORDSIZE) }
|
||||
# endif
|
||||
;
|
||||
|
||||
#if SUPPORTED_PERSONALITIES > 1
|
||||
|
||||
unsigned current_personality;
|
||||
|
Loading…
x
Reference in New Issue
Block a user