Convert stap probes to create operations

This changes the stap probe code to create operations, rather than
exp_elements.

gdb/ChangeLog
2021-03-08  Tom Tromey  <tom@tromey.com>

	* stap-probe.c (binop_maker_ftype): New typedef.
	(stap_maker_map): New global.
	(stap_make_binop): New function.
	(stap_parse_register_operand): Return operation_up.
	(stap_parse_single_operand, stap_parse_argument_conditionally)
	(stap_parse_argument_1): Likewise.
	(stap_parse_argument): Create operations.
	(stap_probe::parse_arguments): Update.
	(_initialize_stap_probe): Initialize stap_maker_map.
	* ppc-linux-tdep.c (ppc_stap_parse_special_token): Change return
	type.
	* i386-tdep.h (i386_stap_parse_special_token): Change return
	type.
	* i386-tdep.c (i386_stap_parse_special_token_triplet)
	(i386_stap_parse_special_token_three_arg_disp)
	(i386_stap_parse_special_token): Change return type.
	* gdbarch.sh (stap_parse_special_token): Change return type.
	* gdbarch.c: Rebuild.
	* gdbarch.h: Rebuild.
	* arm-linux-tdep.c (arm_stap_parse_special_token): Change return
	type.
	* aarch64-linux-tdep.c (aarch64_stap_parse_special_token): Change
	return type.
This commit is contained in:
Tom Tromey 2021-03-08 07:27:57 -07:00
parent 482ddd69c5
commit 4c5e7a930a
10 changed files with 288 additions and 303 deletions

View File

@ -1,3 +1,29 @@
2021-03-08 Tom Tromey <tom@tromey.com>
* stap-probe.c (binop_maker_ftype): New typedef.
(stap_maker_map): New global.
(stap_make_binop): New function.
(stap_parse_register_operand): Return operation_up.
(stap_parse_single_operand, stap_parse_argument_conditionally)
(stap_parse_argument_1): Likewise.
(stap_parse_argument): Create operations.
(stap_probe::parse_arguments): Update.
(_initialize_stap_probe): Initialize stap_maker_map.
* ppc-linux-tdep.c (ppc_stap_parse_special_token): Change return
type.
* i386-tdep.h (i386_stap_parse_special_token): Change return
type.
* i386-tdep.c (i386_stap_parse_special_token_triplet)
(i386_stap_parse_special_token_three_arg_disp)
(i386_stap_parse_special_token): Change return type.
* gdbarch.sh (stap_parse_special_token): Change return type.
* gdbarch.c: Rebuild.
* gdbarch.h: Rebuild.
* arm-linux-tdep.c (arm_stap_parse_special_token): Change return
type.
* aarch64-linux-tdep.c (aarch64_stap_parse_special_token): Change
return type.
2021-03-08 Tom Tromey <tom@tromey.com> 2021-03-08 Tom Tromey <tom@tromey.com>
* gdbarch.sh (dtrace_parse_probe_argument): Change return type. * gdbarch.sh (dtrace_parse_probe_argument): Change return type.

View File

@ -31,6 +31,7 @@
#include "tramp-frame.h" #include "tramp-frame.h"
#include "trad-frame.h" #include "trad-frame.h"
#include "target/target.h" #include "target/target.h"
#include "expop.h"
#include "regcache.h" #include "regcache.h"
#include "regset.h" #include "regset.h"
@ -753,7 +754,7 @@ aarch64_stap_is_single_operand (struct gdbarch *gdbarch, const char *s)
It returns one if the special token has been parsed successfully, It returns one if the special token has been parsed successfully,
or zero if the current token is not considered special. */ or zero if the current token is not considered special. */
static int static expr::operation_up
aarch64_stap_parse_special_token (struct gdbarch *gdbarch, aarch64_stap_parse_special_token (struct gdbarch *gdbarch,
struct stap_parse_info *p) struct stap_parse_info *p)
{ {
@ -764,11 +765,9 @@ aarch64_stap_parse_special_token (struct gdbarch *gdbarch,
char *endp; char *endp;
/* Used to save the register name. */ /* Used to save the register name. */
const char *start; const char *start;
char *regname;
int len; int len;
int got_minus = 0; int got_minus = 0;
long displacement; long displacement;
struct stoken str;
++tmp; ++tmp;
start = tmp; start = tmp;
@ -778,17 +777,14 @@ aarch64_stap_parse_special_token (struct gdbarch *gdbarch,
++tmp; ++tmp;
if (*tmp != ',') if (*tmp != ',')
return 0; return {};
len = tmp - start; len = tmp - start;
regname = (char *) alloca (len + 2); std::string regname (start, len);
strncpy (regname, start, len); if (user_reg_map_name_to_regnum (gdbarch, regname.c_str (), len) == -1)
regname[len] = '\0';
if (user_reg_map_name_to_regnum (gdbarch, regname, len) == -1)
error (_("Invalid register name `%s' on expression `%s'."), error (_("Invalid register name `%s' on expression `%s'."),
regname, p->saved_arg); regname.c_str (), p->saved_arg);
++tmp; ++tmp;
tmp = skip_spaces (tmp); tmp = skip_spaces (tmp);
@ -806,45 +802,39 @@ aarch64_stap_parse_special_token (struct gdbarch *gdbarch,
++tmp; ++tmp;
if (!isdigit (*tmp)) if (!isdigit (*tmp))
return 0; return {};
displacement = strtol (tmp, &endp, 10); displacement = strtol (tmp, &endp, 10);
tmp = endp; tmp = endp;
/* Skipping last `]'. */ /* Skipping last `]'. */
if (*tmp++ != ']') if (*tmp++ != ']')
return 0; return {};
p->arg = tmp;
using namespace expr;
/* The displacement. */ /* The displacement. */
write_exp_elt_opcode (&p->pstate, OP_LONG); struct type *long_type = builtin_type (gdbarch)->builtin_long;
write_exp_elt_type (&p->pstate, builtin_type (gdbarch)->builtin_long);
write_exp_elt_longcst (&p->pstate, displacement);
write_exp_elt_opcode (&p->pstate, OP_LONG);
if (got_minus) if (got_minus)
write_exp_elt_opcode (&p->pstate, UNOP_NEG); displacement = -displacement;
operation_up disp = make_operation<long_const_operation> (long_type,
displacement);
/* The register name. */ /* The register name. */
write_exp_elt_opcode (&p->pstate, OP_REGISTER); operation_up reg
str.ptr = regname; = make_operation<register_operation> (std::move (regname));
str.length = len;
write_exp_string (&p->pstate, str);
write_exp_elt_opcode (&p->pstate, OP_REGISTER);
write_exp_elt_opcode (&p->pstate, BINOP_ADD); operation_up sum
= make_operation<add_operation> (std::move (reg), std::move (disp));
/* Casting to the expected type. */ /* Casting to the expected type. */
write_exp_elt_opcode (&p->pstate, UNOP_CAST); struct type *arg_ptr_type = lookup_pointer_type (p->arg_type);
write_exp_elt_type (&p->pstate, lookup_pointer_type (p->arg_type)); sum = make_operation<unop_cast_operation> (std::move (sum),
write_exp_elt_opcode (&p->pstate, UNOP_CAST); arg_ptr_type);
return make_operation<unop_ind_operation> (std::move (sum));
write_exp_elt_opcode (&p->pstate, UNOP_IND);
p->arg = tmp;
} }
else return {};
return 0;
return 1;
} }
/* AArch64 process record-replay constructs: syscall, signal etc. */ /* AArch64 process record-replay constructs: syscall, signal etc. */

View File

@ -32,6 +32,7 @@
#include "breakpoint.h" #include "breakpoint.h"
#include "auxv.h" #include "auxv.h"
#include "xml-syscall.h" #include "xml-syscall.h"
#include "expop.h"
#include "aarch32-tdep.h" #include "aarch32-tdep.h"
#include "arch/arm.h" #include "arch/arm.h"
@ -1146,7 +1147,7 @@ arm_stap_is_single_operand (struct gdbarch *gdbarch, const char *s)
It returns one if the special token has been parsed successfully, It returns one if the special token has been parsed successfully,
or zero if the current token is not considered special. */ or zero if the current token is not considered special. */
static int static expr::operation_up
arm_stap_parse_special_token (struct gdbarch *gdbarch, arm_stap_parse_special_token (struct gdbarch *gdbarch,
struct stap_parse_info *p) struct stap_parse_info *p)
{ {
@ -1161,7 +1162,6 @@ arm_stap_parse_special_token (struct gdbarch *gdbarch,
int len, offset; int len, offset;
int got_minus = 0; int got_minus = 0;
long displacement; long displacement;
struct stoken str;
++tmp; ++tmp;
start = tmp; start = tmp;
@ -1171,7 +1171,7 @@ arm_stap_parse_special_token (struct gdbarch *gdbarch,
++tmp; ++tmp;
if (*tmp != ',') if (*tmp != ',')
return 0; return {};
len = tmp - start; len = tmp - start;
regname = (char *) alloca (len + 2); regname = (char *) alloca (len + 2);
@ -1212,38 +1212,33 @@ arm_stap_parse_special_token (struct gdbarch *gdbarch,
/* Skipping last `]'. */ /* Skipping last `]'. */
if (*tmp++ != ']') if (*tmp++ != ']')
return 0; return {};
p->arg = tmp;
using namespace expr;
/* The displacement. */ /* The displacement. */
write_exp_elt_opcode (&p->pstate, OP_LONG); struct type *long_type = builtin_type (gdbarch)->builtin_long;
write_exp_elt_type (&p->pstate, builtin_type (gdbarch)->builtin_long);
write_exp_elt_longcst (&p->pstate, displacement);
write_exp_elt_opcode (&p->pstate, OP_LONG);
if (got_minus) if (got_minus)
write_exp_elt_opcode (&p->pstate, UNOP_NEG); displacement = -displacement;
operation_up disp = make_operation<long_const_operation> (long_type,
displacement);
/* The register name. */ /* The register name. */
write_exp_elt_opcode (&p->pstate, OP_REGISTER); operation_up reg
str.ptr = regname; = make_operation<register_operation> (regname);
str.length = len;
write_exp_string (&p->pstate, str);
write_exp_elt_opcode (&p->pstate, OP_REGISTER);
write_exp_elt_opcode (&p->pstate, BINOP_ADD); operation_up sum
= make_operation<add_operation> (std::move (reg), std::move (disp));
/* Casting to the expected type. */ /* Casting to the expected type. */
write_exp_elt_opcode (&p->pstate, UNOP_CAST); struct type *arg_ptr_type = lookup_pointer_type (p->arg_type);
write_exp_elt_type (&p->pstate, lookup_pointer_type (p->arg_type)); sum = make_operation<unop_cast_operation> (std::move (sum),
write_exp_elt_opcode (&p->pstate, UNOP_CAST); arg_ptr_type);
return make_operation<unop_ind_operation> (std::move (sum));
write_exp_elt_opcode (&p->pstate, UNOP_IND);
p->arg = tmp;
} }
else
return 0;
return 1; return {};
} }
/* ARM process record-replay constructs: syscall, signal etc. */ /* ARM process record-replay constructs: syscall, signal etc. */

View File

@ -4589,7 +4589,7 @@ gdbarch_stap_parse_special_token_p (struct gdbarch *gdbarch)
return gdbarch->stap_parse_special_token != NULL; return gdbarch->stap_parse_special_token != NULL;
} }
int expr::operation_up
gdbarch_stap_parse_special_token (struct gdbarch *gdbarch, struct stap_parse_info *p) gdbarch_stap_parse_special_token (struct gdbarch *gdbarch, struct stap_parse_info *p)
{ {
gdb_assert (gdbarch != NULL); gdb_assert (gdbarch != NULL);

View File

@ -1346,8 +1346,8 @@ extern void set_gdbarch_stap_is_single_operand (struct gdbarch *gdbarch, gdbarch
extern bool gdbarch_stap_parse_special_token_p (struct gdbarch *gdbarch); extern bool gdbarch_stap_parse_special_token_p (struct gdbarch *gdbarch);
typedef int (gdbarch_stap_parse_special_token_ftype) (struct gdbarch *gdbarch, struct stap_parse_info *p); typedef expr::operation_up (gdbarch_stap_parse_special_token_ftype) (struct gdbarch *gdbarch, struct stap_parse_info *p);
extern int gdbarch_stap_parse_special_token (struct gdbarch *gdbarch, struct stap_parse_info *p); extern expr::operation_up gdbarch_stap_parse_special_token (struct gdbarch *gdbarch, struct stap_parse_info *p);
extern void set_gdbarch_stap_parse_special_token (struct gdbarch *gdbarch, gdbarch_stap_parse_special_token_ftype *stap_parse_special_token); extern void set_gdbarch_stap_parse_special_token (struct gdbarch *gdbarch, gdbarch_stap_parse_special_token_ftype *stap_parse_special_token);
/* Perform arch-dependent adjustments to a register name. /* Perform arch-dependent adjustments to a register name.

View File

@ -994,7 +994,7 @@ M;int;stap_is_single_operand;const char *s;s
# if the token was not recognized as a special token (in this case, returning # if the token was not recognized as a special token (in this case, returning
# zero means that the special parser is deferring the parsing to the generic # zero means that the special parser is deferring the parsing to the generic
# parser), and should advance the buffer pointer (p->arg). # parser), and should advance the buffer pointer (p->arg).
M;int;stap_parse_special_token;struct stap_parse_info *p;p M;expr::operation_up;stap_parse_special_token;struct stap_parse_info *p;p
# Perform arch-dependent adjustments to a register name. # Perform arch-dependent adjustments to a register name.
# #

View File

@ -48,6 +48,7 @@
#include "i387-tdep.h" #include "i387-tdep.h"
#include "gdbsupport/x86-xstate.h" #include "gdbsupport/x86-xstate.h"
#include "x86-tdep.h" #include "x86-tdep.h"
#include "expop.h"
#include "record.h" #include "record.h"
#include "record-full.h" #include "record-full.h"
@ -4069,7 +4070,7 @@ i386_stap_is_single_operand (struct gdbarch *gdbarch, const char *s)
Return true if the operand was parsed successfully, false Return true if the operand was parsed successfully, false
otherwise. */ otherwise. */
static bool static expr::operation_up
i386_stap_parse_special_token_triplet (struct gdbarch *gdbarch, i386_stap_parse_special_token_triplet (struct gdbarch *gdbarch,
struct stap_parse_info *p) struct stap_parse_info *p)
{ {
@ -4081,9 +4082,7 @@ i386_stap_parse_special_token_triplet (struct gdbarch *gdbarch,
int i; int i;
long displacements[3]; long displacements[3];
const char *start; const char *start;
char *regname;
int len; int len;
struct stoken str;
char *endp; char *endp;
got_minus[0] = false; got_minus[0] = false;
@ -4096,7 +4095,7 @@ i386_stap_parse_special_token_triplet (struct gdbarch *gdbarch,
} }
if (!isdigit ((unsigned char) *s)) if (!isdigit ((unsigned char) *s))
return false; return {};
displacements[0] = strtol (s, &endp, 10); displacements[0] = strtol (s, &endp, 10);
s = endp; s = endp;
@ -4104,7 +4103,7 @@ i386_stap_parse_special_token_triplet (struct gdbarch *gdbarch,
if (*s != '+' && *s != '-') if (*s != '+' && *s != '-')
{ {
/* We are not dealing with a triplet. */ /* We are not dealing with a triplet. */
return false; return {};
} }
got_minus[1] = false; got_minus[1] = false;
@ -4117,7 +4116,7 @@ i386_stap_parse_special_token_triplet (struct gdbarch *gdbarch,
} }
if (!isdigit ((unsigned char) *s)) if (!isdigit ((unsigned char) *s))
return false; return {};
displacements[1] = strtol (s, &endp, 10); displacements[1] = strtol (s, &endp, 10);
s = endp; s = endp;
@ -4125,7 +4124,7 @@ i386_stap_parse_special_token_triplet (struct gdbarch *gdbarch,
if (*s != '+' && *s != '-') if (*s != '+' && *s != '-')
{ {
/* We are not dealing with a triplet. */ /* We are not dealing with a triplet. */
return false; return {};
} }
got_minus[2] = false; got_minus[2] = false;
@ -4138,13 +4137,13 @@ i386_stap_parse_special_token_triplet (struct gdbarch *gdbarch,
} }
if (!isdigit ((unsigned char) *s)) if (!isdigit ((unsigned char) *s))
return false; return {};
displacements[2] = strtol (s, &endp, 10); displacements[2] = strtol (s, &endp, 10);
s = endp; s = endp;
if (*s != '(' || s[1] != '%') if (*s != '(' || s[1] != '%')
return false; return {};
s += 2; s += 2;
start = s; start = s;
@ -4153,57 +4152,46 @@ i386_stap_parse_special_token_triplet (struct gdbarch *gdbarch,
++s; ++s;
if (*s++ != ')') if (*s++ != ')')
return false; return {};
len = s - start - 1; len = s - start - 1;
regname = (char *) alloca (len + 1); std::string regname (start, len);
strncpy (regname, start, len); if (user_reg_map_name_to_regnum (gdbarch, regname.c_str (), len) == -1)
regname[len] = '\0';
if (user_reg_map_name_to_regnum (gdbarch, regname, len) == -1)
error (_("Invalid register name `%s' on expression `%s'."), error (_("Invalid register name `%s' on expression `%s'."),
regname, p->saved_arg); regname.c_str (), p->saved_arg);
LONGEST value = 0;
for (i = 0; i < 3; i++) for (i = 0; i < 3; i++)
{ {
write_exp_elt_opcode (&p->pstate, OP_LONG); LONGEST this_val = displacements[i];
write_exp_elt_type
(&p->pstate, builtin_type (gdbarch)->builtin_long);
write_exp_elt_longcst (&p->pstate, displacements[i]);
write_exp_elt_opcode (&p->pstate, OP_LONG);
if (got_minus[i]) if (got_minus[i])
write_exp_elt_opcode (&p->pstate, UNOP_NEG); this_val = -this_val;
value += this_val;
} }
write_exp_elt_opcode (&p->pstate, OP_REGISTER);
str.ptr = regname;
str.length = len;
write_exp_string (&p->pstate, str);
write_exp_elt_opcode (&p->pstate, OP_REGISTER);
write_exp_elt_opcode (&p->pstate, UNOP_CAST);
write_exp_elt_type (&p->pstate,
builtin_type (gdbarch)->builtin_data_ptr);
write_exp_elt_opcode (&p->pstate, UNOP_CAST);
write_exp_elt_opcode (&p->pstate, BINOP_ADD);
write_exp_elt_opcode (&p->pstate, BINOP_ADD);
write_exp_elt_opcode (&p->pstate, BINOP_ADD);
write_exp_elt_opcode (&p->pstate, UNOP_CAST);
write_exp_elt_type (&p->pstate,
lookup_pointer_type (p->arg_type));
write_exp_elt_opcode (&p->pstate, UNOP_CAST);
write_exp_elt_opcode (&p->pstate, UNOP_IND);
p->arg = s; p->arg = s;
return true; using namespace expr;
struct type *long_type = builtin_type (gdbarch)->builtin_long;
operation_up offset
= make_operation<long_const_operation> (long_type, value);
operation_up reg
= make_operation<register_operation> (std::move (regname));
struct type *void_ptr = builtin_type (gdbarch)->builtin_data_ptr;
reg = make_operation<unop_cast_operation> (std::move (reg), void_ptr);
operation_up sum
= make_operation<add_operation> (std::move (reg), std::move (offset));
struct type *arg_ptr_type = lookup_pointer_type (p->arg_type);
sum = make_operation<unop_cast_operation> (std::move (sum),
arg_ptr_type);
return make_operation<unop_ind_operation> (std::move (sum));
} }
return false; return {};
} }
/* Helper function for i386_stap_parse_special_token. /* Helper function for i386_stap_parse_special_token.
@ -4215,7 +4203,7 @@ i386_stap_parse_special_token_triplet (struct gdbarch *gdbarch,
Return true if the operand was parsed successfully, false Return true if the operand was parsed successfully, false
otherwise. */ otherwise. */
static bool static expr::operation_up
i386_stap_parse_special_token_three_arg_disp (struct gdbarch *gdbarch, i386_stap_parse_special_token_three_arg_disp (struct gdbarch *gdbarch,
struct stap_parse_info *p) struct stap_parse_info *p)
{ {
@ -4228,11 +4216,8 @@ i386_stap_parse_special_token_three_arg_disp (struct gdbarch *gdbarch,
bool size_minus = false; bool size_minus = false;
long size = 0; long size = 0;
const char *start; const char *start;
char *base;
int len_base; int len_base;
char *index;
int len_index; int len_index;
struct stoken base_token, index_token;
if (*s == '+') if (*s == '+')
++s; ++s;
@ -4243,7 +4228,7 @@ i386_stap_parse_special_token_three_arg_disp (struct gdbarch *gdbarch,
} }
if (offset_minus && !isdigit (*s)) if (offset_minus && !isdigit (*s))
return false; return {};
if (isdigit (*s)) if (isdigit (*s))
{ {
@ -4254,7 +4239,7 @@ i386_stap_parse_special_token_three_arg_disp (struct gdbarch *gdbarch,
} }
if (*s != '(' || s[1] != '%') if (*s != '(' || s[1] != '%')
return false; return {};
s += 2; s += 2;
start = s; start = s;
@ -4263,16 +4248,14 @@ i386_stap_parse_special_token_three_arg_disp (struct gdbarch *gdbarch,
++s; ++s;
if (*s != ',' || s[1] != '%') if (*s != ',' || s[1] != '%')
return false; return {};
len_base = s - start; len_base = s - start;
base = (char *) alloca (len_base + 1); std::string base (start, len_base);
strncpy (base, start, len_base);
base[len_base] = '\0';
if (user_reg_map_name_to_regnum (gdbarch, base, len_base) == -1) if (user_reg_map_name_to_regnum (gdbarch, base.c_str (), len_base) == -1)
error (_("Invalid register name `%s' on expression `%s'."), error (_("Invalid register name `%s' on expression `%s'."),
base, p->saved_arg); base.c_str (), p->saved_arg);
s += 2; s += 2;
start = s; start = s;
@ -4281,16 +4264,15 @@ i386_stap_parse_special_token_three_arg_disp (struct gdbarch *gdbarch,
++s; ++s;
len_index = s - start; len_index = s - start;
index = (char *) alloca (len_index + 1); std::string index (start, len_index);
strncpy (index, start, len_index);
index[len_index] = '\0';
if (user_reg_map_name_to_regnum (gdbarch, index, len_index) == -1) if (user_reg_map_name_to_regnum (gdbarch, index.c_str (),
len_index) == -1)
error (_("Invalid register name `%s' on expression `%s'."), error (_("Invalid register name `%s' on expression `%s'."),
index, p->saved_arg); index.c_str (), p->saved_arg);
if (*s != ',' && *s != ')') if (*s != ',' && *s != ')')
return false; return {};
if (*s == ',') if (*s == ',')
{ {
@ -4309,85 +4291,60 @@ i386_stap_parse_special_token_three_arg_disp (struct gdbarch *gdbarch,
s = endp; s = endp;
if (*s != ')') if (*s != ')')
return false; return {};
} }
++s; ++s;
if (offset)
{
write_exp_elt_opcode (&p->pstate, OP_LONG);
write_exp_elt_type (&p->pstate,
builtin_type (gdbarch)->builtin_long);
write_exp_elt_longcst (&p->pstate, offset);
write_exp_elt_opcode (&p->pstate, OP_LONG);
if (offset_minus)
write_exp_elt_opcode (&p->pstate, UNOP_NEG);
}
write_exp_elt_opcode (&p->pstate, OP_REGISTER);
base_token.ptr = base;
base_token.length = len_base;
write_exp_string (&p->pstate, base_token);
write_exp_elt_opcode (&p->pstate, OP_REGISTER);
if (offset)
write_exp_elt_opcode (&p->pstate, BINOP_ADD);
write_exp_elt_opcode (&p->pstate, OP_REGISTER);
index_token.ptr = index;
index_token.length = len_index;
write_exp_string (&p->pstate, index_token);
write_exp_elt_opcode (&p->pstate, OP_REGISTER);
if (size)
{
write_exp_elt_opcode (&p->pstate, OP_LONG);
write_exp_elt_type (&p->pstate,
builtin_type (gdbarch)->builtin_long);
write_exp_elt_longcst (&p->pstate, size);
write_exp_elt_opcode (&p->pstate, OP_LONG);
if (size_minus)
write_exp_elt_opcode (&p->pstate, UNOP_NEG);
write_exp_elt_opcode (&p->pstate, BINOP_MUL);
}
write_exp_elt_opcode (&p->pstate, BINOP_ADD);
write_exp_elt_opcode (&p->pstate, UNOP_CAST);
write_exp_elt_type (&p->pstate,
lookup_pointer_type (p->arg_type));
write_exp_elt_opcode (&p->pstate, UNOP_CAST);
write_exp_elt_opcode (&p->pstate, UNOP_IND);
p->arg = s; p->arg = s;
return true; using namespace expr;
struct type *long_type = builtin_type (gdbarch)->builtin_long;
operation_up reg = make_operation<register_operation> (std::move (base));
if (offset != 0)
{
if (offset_minus)
offset = -offset;
operation_up value
= make_operation<long_const_operation> (long_type, offset);
reg = make_operation<add_operation> (std::move (reg),
std::move (value));
}
operation_up ind_reg
= make_operation<register_operation> (std::move (index));
if (size != 0)
{
if (size_minus)
size = -size;
operation_up value
= make_operation<long_const_operation> (long_type, size);
ind_reg = make_operation<mul_operation> (std::move (ind_reg),
std::move (value));
}
operation_up sum
= make_operation<add_operation> (std::move (reg),
std::move (ind_reg));
struct type *arg_ptr_type = lookup_pointer_type (p->arg_type);
sum = make_operation<unop_cast_operation> (std::move (sum),
arg_ptr_type);
return make_operation<unop_ind_operation> (std::move (sum));
} }
return false; return {};
} }
/* Implementation of `gdbarch_stap_parse_special_token', as defined in /* Implementation of `gdbarch_stap_parse_special_token', as defined in
gdbarch.h. */ gdbarch.h. */
int expr::operation_up
i386_stap_parse_special_token (struct gdbarch *gdbarch, i386_stap_parse_special_token (struct gdbarch *gdbarch,
struct stap_parse_info *p) struct stap_parse_info *p)
{ {
/* In order to parse special tokens, we use a state-machine that go
through every known token and try to get a match. */
enum
{
TRIPLET,
THREE_ARG_DISPLACEMENT,
DONE
};
int current_state;
current_state = TRIPLET;
/* The special tokens to be parsed here are: /* The special tokens to be parsed here are:
- `register base + (register index * size) + offset', as represented - `register base + (register index * size) + offset', as represented
@ -4396,26 +4353,13 @@ i386_stap_parse_special_token (struct gdbarch *gdbarch,
- Operands of the form `-8+3+1(%rbp)', which must be interpreted as - Operands of the form `-8+3+1(%rbp)', which must be interpreted as
`*(-8 + 3 - 1 + (void *) $eax)'. */ `*(-8 + 3 - 1 + (void *) $eax)'. */
while (current_state != DONE) expr::operation_up result
{ = i386_stap_parse_special_token_triplet (gdbarch, p);
switch (current_state)
{
case TRIPLET:
if (i386_stap_parse_special_token_triplet (gdbarch, p))
return 1;
break;
case THREE_ARG_DISPLACEMENT: if (result == nullptr)
if (i386_stap_parse_special_token_three_arg_disp (gdbarch, p)) result = i386_stap_parse_special_token_three_arg_disp (gdbarch, p);
return 1;
break;
}
/* Advancing to the next state. */ return result;
++current_state;
}
return 0;
} }
/* Implementation of 'gdbarch_stap_adjust_register', as defined in /* Implementation of 'gdbarch_stap_adjust_register', as defined in

View File

@ -22,6 +22,7 @@
#include "gdbarch.h" #include "gdbarch.h"
#include "infrun.h" #include "infrun.h"
#include "expression.h"
struct frame_info; struct frame_info;
struct gdbarch; struct gdbarch;
@ -485,7 +486,7 @@ extern int i386bsd_sc_reg_offset[];
extern int i386_stap_is_single_operand (struct gdbarch *gdbarch, extern int i386_stap_is_single_operand (struct gdbarch *gdbarch,
const char *s); const char *s);
extern int i386_stap_parse_special_token (struct gdbarch *gdbarch, extern expr::operation_up i386_stap_parse_special_token
struct stap_parse_info *p); (struct gdbarch *gdbarch, struct stap_parse_info *p);
#endif /* i386-tdep.h */ #endif /* i386-tdep.h */

View File

@ -52,6 +52,7 @@
#include "linux-record.h" #include "linux-record.h"
#include "record-full.h" #include "record-full.h"
#include "infrun.h" #include "infrun.h"
#include "expop.h"
#include "stap-probe.h" #include "stap-probe.h"
#include "ax.h" #include "ax.h"
@ -1674,7 +1675,7 @@ ppc_stap_is_single_operand (struct gdbarch *gdbarch, const char *s)
/* Implementation of `gdbarch_stap_parse_special_token', as defined in /* Implementation of `gdbarch_stap_parse_special_token', as defined in
gdbarch.h. */ gdbarch.h. */
static int static expr::operation_up
ppc_stap_parse_special_token (struct gdbarch *gdbarch, ppc_stap_parse_special_token (struct gdbarch *gdbarch,
struct stap_parse_info *p) struct stap_parse_info *p)
{ {
@ -1686,7 +1687,6 @@ ppc_stap_parse_special_token (struct gdbarch *gdbarch,
const char *s = p->arg; const char *s = p->arg;
char *regname; char *regname;
int len; int len;
struct stoken str;
while (isdigit (*s)) while (isdigit (*s))
++s; ++s;
@ -1695,7 +1695,7 @@ ppc_stap_parse_special_token (struct gdbarch *gdbarch,
{ {
/* It is a register displacement indeed. Returning 0 means we are /* It is a register displacement indeed. Returning 0 means we are
deferring the treatment of this case to the generic parser. */ deferring the treatment of this case to the generic parser. */
return 0; return {};
} }
len = s - p->arg; len = s - p->arg;
@ -1710,22 +1710,14 @@ ppc_stap_parse_special_token (struct gdbarch *gdbarch,
error (_("Invalid register name `%s' on expression `%s'."), error (_("Invalid register name `%s' on expression `%s'."),
regname, p->saved_arg); regname, p->saved_arg);
write_exp_elt_opcode (&p->pstate, OP_REGISTER);
str.ptr = regname;
str.length = len;
write_exp_string (&p->pstate, str);
write_exp_elt_opcode (&p->pstate, OP_REGISTER);
p->arg = s; p->arg = s;
}
else return expr::make_operation<expr::register_operation> (regname);
{
/* All the other tokens should be handled correctly by the generic
parser. */
return 0;
} }
return 1; /* All the other tokens should be handled correctly by the generic
parser. */
return {};
} }
/* Initialize linux_record_tdep if not initialized yet. /* Initialize linux_record_tdep if not initialized yet.

View File

@ -36,6 +36,8 @@
#include "parser-defs.h" #include "parser-defs.h"
#include "language.h" #include "language.h"
#include "elf-bfd.h" #include "elf-bfd.h"
#include "expop.h"
#include <unordered_map>
#include <ctype.h> #include <ctype.h>
@ -262,10 +264,13 @@ enum stap_operand_prec
STAP_OPERAND_PREC_MUL STAP_OPERAND_PREC_MUL
}; };
static void stap_parse_argument_1 (struct stap_parse_info *p, bool has_lhs, static expr::operation_up stap_parse_argument_1 (struct stap_parse_info *p,
enum stap_operand_prec prec); expr::operation_up &&lhs,
enum stap_operand_prec prec)
ATTRIBUTE_UNUSED_RESULT;
static void stap_parse_argument_conditionally (struct stap_parse_info *p); static expr::operation_up stap_parse_argument_conditionally
(struct stap_parse_info *p) ATTRIBUTE_UNUSED_RESULT;
/* Returns true if *S is an operator, false otherwise. */ /* Returns true if *S is an operator, false otherwise. */
@ -427,6 +432,22 @@ stap_get_opcode (const char **s)
return op; return op;
} }
typedef expr::operation_up binop_maker_ftype (expr::operation_up &&,
expr::operation_up &&);
/* Map from an expression opcode to a function that can create a
binary operation of that type. */
static std::unordered_map<exp_opcode, binop_maker_ftype *> stap_maker_map;
/* Helper function to create a binary operation. */
static expr::operation_up
stap_make_binop (enum exp_opcode opcode, expr::operation_up &&lhs,
expr::operation_up &&rhs)
{
auto iter = stap_maker_map.find (opcode);
gdb_assert (iter != stap_maker_map.end ());
return iter->second (std::move (lhs), std::move (rhs));
}
/* Given the bitness of the argument, represented by B, return the /* Given the bitness of the argument, represented by B, return the
corresponding `struct type *', or throw an error if B is corresponding `struct type *', or throw an error if B is
unknown. */ unknown. */
@ -676,19 +697,16 @@ stap_check_register_indirection_suffix (struct gdbarch *gdbarch, const char *s,
language (e.g., `15' is the 15th general-purpose register), but inside language (e.g., `15' is the 15th general-purpose register), but inside
GDB they have a prefix (the letter `r') appended. */ GDB they have a prefix (the letter `r') appended. */
static void static expr::operation_up
stap_parse_register_operand (struct stap_parse_info *p) stap_parse_register_operand (struct stap_parse_info *p)
{ {
/* Simple flag to indicate whether we have seen a minus signal before /* Simple flag to indicate whether we have seen a minus signal before
certain number. */ certain number. */
bool got_minus = false; bool got_minus = false;
/* Flags to indicate whether this register access is being displaced and/or /* Flag to indicate whether this register access is being
indirected. */ indirected. */
bool disp_p = false;
bool indirect_p = false; bool indirect_p = false;
struct gdbarch *gdbarch = p->gdbarch; struct gdbarch *gdbarch = p->gdbarch;
/* Needed to generate the register name as a part of an expression. */
struct stoken str;
/* Variables used to extract the register name from the probe's /* Variables used to extract the register name from the probe's
argument. */ argument. */
const char *start; const char *start;
@ -699,6 +717,8 @@ stap_parse_register_operand (struct stap_parse_info *p)
const char *reg_suffix; const char *reg_suffix;
const char *reg_ind_suffix; const char *reg_ind_suffix;
using namespace expr;
/* Checking for a displacement argument. */ /* Checking for a displacement argument. */
if (*p->arg == '+') if (*p->arg == '+')
{ {
@ -712,23 +732,21 @@ stap_parse_register_operand (struct stap_parse_info *p)
++p->arg; ++p->arg;
} }
struct type *long_type = builtin_type (gdbarch)->builtin_long;
operation_up disp_op;
if (isdigit (*p->arg)) if (isdigit (*p->arg))
{ {
/* The value of the displacement. */ /* The value of the displacement. */
long displacement; long displacement;
char *endp; char *endp;
disp_p = true;
displacement = strtol (p->arg, &endp, 10); displacement = strtol (p->arg, &endp, 10);
p->arg = endp; p->arg = endp;
/* Generating the expression for the displacement. */ /* Generating the expression for the displacement. */
write_exp_elt_opcode (&p->pstate, OP_LONG);
write_exp_elt_type (&p->pstate, builtin_type (gdbarch)->builtin_long);
write_exp_elt_longcst (&p->pstate, displacement);
write_exp_elt_opcode (&p->pstate, OP_LONG);
if (got_minus) if (got_minus)
write_exp_elt_opcode (&p->pstate, UNOP_NEG); displacement = -displacement;
disp_op = make_operation<long_const_operation> (long_type, displacement);
} }
/* Getting rid of register indirection prefix. */ /* Getting rid of register indirection prefix. */
@ -738,7 +756,7 @@ stap_parse_register_operand (struct stap_parse_info *p)
p->arg += strlen (reg_ind_prefix); p->arg += strlen (reg_ind_prefix);
} }
if (disp_p && !indirect_p) if (disp_op != nullptr && !indirect_p)
error (_("Invalid register displacement syntax on expression `%s'."), error (_("Invalid register displacement syntax on expression `%s'."),
p->saved_arg); p->saved_arg);
@ -796,27 +814,23 @@ stap_parse_register_operand (struct stap_parse_info *p)
" (previous name was '%s')"), " (previous name was '%s')"),
newregname.c_str (), regname.c_str ()); newregname.c_str (), regname.c_str ());
regname = newregname; regname = std::move (newregname);
} }
} }
write_exp_elt_opcode (&p->pstate, OP_REGISTER); operation_up reg = make_operation<register_operation> (std::move (regname));
str.ptr = regname.c_str ();
str.length = regname.size ();
write_exp_string (&p->pstate, str);
write_exp_elt_opcode (&p->pstate, OP_REGISTER);
if (indirect_p) if (indirect_p)
{ {
if (disp_p) if (disp_op != nullptr)
write_exp_elt_opcode (&p->pstate, BINOP_ADD); reg = make_operation<add_operation> (std::move (disp_op),
std::move (reg));
/* Casting to the expected type. */ /* Casting to the expected type. */
write_exp_elt_opcode (&p->pstate, UNOP_CAST); struct type *arg_ptr_type = lookup_pointer_type (p->arg_type);
write_exp_elt_type (&p->pstate, lookup_pointer_type (p->arg_type)); reg = make_operation<unop_cast_operation> (std::move (reg),
write_exp_elt_opcode (&p->pstate, UNOP_CAST); arg_ptr_type);
reg = make_operation<unop_ind_operation> (std::move (reg));
write_exp_elt_opcode (&p->pstate, UNOP_IND);
} }
/* Getting rid of the register name suffix. */ /* Getting rid of the register name suffix. */
@ -836,6 +850,8 @@ stap_parse_register_operand (struct stap_parse_info *p)
error (_("Missing indirection suffix on expression `%s'."), error (_("Missing indirection suffix on expression `%s'."),
p->saved_arg); p->saved_arg);
} }
return reg;
} }
/* This function is responsible for parsing a single operand. /* This function is responsible for parsing a single operand.
@ -853,23 +869,24 @@ stap_parse_register_operand (struct stap_parse_info *p)
unrecognized operands, allowing arch-specific parsers to be unrecognized operands, allowing arch-specific parsers to be
created. */ created. */
static void static expr::operation_up
stap_parse_single_operand (struct stap_parse_info *p) stap_parse_single_operand (struct stap_parse_info *p)
{ {
struct gdbarch *gdbarch = p->gdbarch; struct gdbarch *gdbarch = p->gdbarch;
const char *int_prefix = NULL; const char *int_prefix = NULL;
/* We first try to parse this token as a "special token". */ using namespace expr;
if (gdbarch_stap_parse_special_token_p (gdbarch)
&& (gdbarch_stap_parse_special_token (gdbarch, p) != 0))
{
/* If the return value of the above function is not zero,
it means it successfully parsed the special token.
If it is NULL, we try to parse it using our method. */ /* We first try to parse this token as a "special token". */
return; if (gdbarch_stap_parse_special_token_p (gdbarch))
{
operation_up token = gdbarch_stap_parse_special_token (gdbarch, p);
if (token != nullptr)
return token;
} }
struct type *long_type = builtin_type (gdbarch)->builtin_long;
operation_up result;
if (*p->arg == '-' || *p->arg == '~' || *p->arg == '+' || *p->arg == '!') if (*p->arg == '-' || *p->arg == '~' || *p->arg == '+' || *p->arg == '!')
{ {
char c = *p->arg; char c = *p->arg;
@ -912,20 +929,22 @@ stap_parse_single_operand (struct stap_parse_info *p)
error (_("Invalid operator `%c' for register displacement " error (_("Invalid operator `%c' for register displacement "
"on expression `%s'."), c, p->saved_arg); "on expression `%s'."), c, p->saved_arg);
stap_parse_register_operand (p); result = stap_parse_register_operand (p);
} }
else else
{ {
/* This is not a displacement. We skip the operator, and /* This is not a displacement. We skip the operator, and
deal with it when the recursion returns. */ deal with it when the recursion returns. */
++p->arg; ++p->arg;
stap_parse_argument_conditionally (p); result = stap_parse_argument_conditionally (p);
if (c == '-') if (c == '-')
write_exp_elt_opcode (&p->pstate, UNOP_NEG); result = make_operation<unary_neg_operation> (std::move (result));
else if (c == '~') else if (c == '~')
write_exp_elt_opcode (&p->pstate, UNOP_COMPLEMENT); result = (make_operation<unary_complement_operation>
(std::move (result)));
else if (c == '!') else if (c == '!')
write_exp_elt_opcode (&p->pstate, UNOP_LOGICAL_NOT); result = (make_operation<unary_logical_not_operation>
(std::move (result)));
} }
} }
else if (isdigit (*p->arg)) else if (isdigit (*p->arg))
@ -953,11 +972,7 @@ stap_parse_single_operand (struct stap_parse_info *p)
const char *int_suffix; const char *int_suffix;
/* We are dealing with a numeric constant. */ /* We are dealing with a numeric constant. */
write_exp_elt_opcode (&p->pstate, OP_LONG); result = make_operation<long_const_operation> (long_type, number);
write_exp_elt_type (&p->pstate,
builtin_type (gdbarch)->builtin_long);
write_exp_elt_longcst (&p->pstate, number);
write_exp_elt_opcode (&p->pstate, OP_LONG);
p->arg = tmp; p->arg = tmp;
@ -968,7 +983,7 @@ stap_parse_single_operand (struct stap_parse_info *p)
p->saved_arg); p->saved_arg);
} }
else if (stap_is_register_indirection_prefix (gdbarch, tmp, NULL)) else if (stap_is_register_indirection_prefix (gdbarch, tmp, NULL))
stap_parse_register_operand (p); result = stap_parse_register_operand (p);
else else
error (_("Unknown numeric token on expression `%s'."), error (_("Unknown numeric token on expression `%s'."),
p->saved_arg); p->saved_arg);
@ -984,10 +999,7 @@ stap_parse_single_operand (struct stap_parse_info *p)
number = strtol (p->arg, &endp, 10); number = strtol (p->arg, &endp, 10);
p->arg = endp; p->arg = endp;
write_exp_elt_opcode (&p->pstate, OP_LONG); result = make_operation<long_const_operation> (long_type, number);
write_exp_elt_type (&p->pstate, builtin_type (gdbarch)->builtin_long);
write_exp_elt_longcst (&p->pstate, number);
write_exp_elt_opcode (&p->pstate, OP_LONG);
if (stap_check_integer_suffix (gdbarch, p->arg, &int_suffix)) if (stap_check_integer_suffix (gdbarch, p->arg, &int_suffix))
p->arg += strlen (int_suffix); p->arg += strlen (int_suffix);
@ -997,10 +1009,12 @@ stap_parse_single_operand (struct stap_parse_info *p)
} }
else if (stap_is_register_prefix (gdbarch, p->arg, NULL) else if (stap_is_register_prefix (gdbarch, p->arg, NULL)
|| stap_is_register_indirection_prefix (gdbarch, p->arg, NULL)) || stap_is_register_indirection_prefix (gdbarch, p->arg, NULL))
stap_parse_register_operand (p); result = stap_parse_register_operand (p);
else else
error (_("Operator `%c' not recognized on expression `%s'."), error (_("Operator `%c' not recognized on expression `%s'."),
*p->arg, p->saved_arg); *p->arg, p->saved_arg);
return result;
} }
/* This function parses an argument conditionally, based on single or /* This function parses an argument conditionally, based on single or
@ -1009,15 +1023,16 @@ stap_parse_single_operand (struct stap_parse_info *p)
starts with `-', `~', `+' (i.e., unary operators), a digit, or starts with `-', `~', `+' (i.e., unary operators), a digit, or
something recognized by `gdbarch_stap_is_single_operand'. */ something recognized by `gdbarch_stap_is_single_operand'. */
static void static expr::operation_up
stap_parse_argument_conditionally (struct stap_parse_info *p) stap_parse_argument_conditionally (struct stap_parse_info *p)
{ {
gdb_assert (gdbarch_stap_is_single_operand_p (p->gdbarch)); gdb_assert (gdbarch_stap_is_single_operand_p (p->gdbarch));
expr::operation_up result;
if (*p->arg == '-' || *p->arg == '~' || *p->arg == '+' || *p->arg == '!' if (*p->arg == '-' || *p->arg == '~' || *p->arg == '+' || *p->arg == '!'
|| isdigit (*p->arg) || isdigit (*p->arg)
|| gdbarch_stap_is_single_operand (p->gdbarch, p->arg)) || gdbarch_stap_is_single_operand (p->gdbarch, p->arg))
stap_parse_single_operand (p); result = stap_parse_single_operand (p);
else if (*p->arg == '(') else if (*p->arg == '(')
{ {
/* We are dealing with a parenthesized operand. It means we /* We are dealing with a parenthesized operand. It means we
@ -1027,7 +1042,7 @@ stap_parse_argument_conditionally (struct stap_parse_info *p)
p->arg = skip_spaces (p->arg); p->arg = skip_spaces (p->arg);
++p->inside_paren_p; ++p->inside_paren_p;
stap_parse_argument_1 (p, 0, STAP_OPERAND_PREC_NONE); result = stap_parse_argument_1 (p, {}, STAP_OPERAND_PREC_NONE);
p->arg = skip_spaces (p->arg); p->arg = skip_spaces (p->arg);
if (*p->arg != ')') if (*p->arg != ')')
@ -1041,13 +1056,16 @@ stap_parse_argument_conditionally (struct stap_parse_info *p)
} }
else else
error (_("Cannot parse expression `%s'."), p->saved_arg); error (_("Cannot parse expression `%s'."), p->saved_arg);
return result;
} }
/* Helper function for `stap_parse_argument'. Please, see its comments to /* Helper function for `stap_parse_argument'. Please, see its comments to
better understand what this function does. */ better understand what this function does. */
static void static expr::operation_up ATTRIBUTE_UNUSED_RESULT
stap_parse_argument_1 (struct stap_parse_info *p, bool has_lhs, stap_parse_argument_1 (struct stap_parse_info *p,
expr::operation_up &&lhs_in,
enum stap_operand_prec prec) enum stap_operand_prec prec)
{ {
/* This is an operator-precedence parser. /* This is an operator-precedence parser.
@ -1061,13 +1079,15 @@ stap_parse_argument_1 (struct stap_parse_info *p, bool has_lhs,
if (p->inside_paren_p) if (p->inside_paren_p)
p->arg = skip_spaces (p->arg); p->arg = skip_spaces (p->arg);
if (!has_lhs) using namespace expr;
operation_up lhs = std::move (lhs_in);
if (lhs == nullptr)
{ {
/* We were called without a left-side, either because this is the /* We were called without a left-side, either because this is the
first call, or because we were called to parse a parenthesized first call, or because we were called to parse a parenthesized
expression. It doesn't really matter; we have to parse the expression. It doesn't really matter; we have to parse the
left-side in order to continue the process. */ left-side in order to continue the process. */
stap_parse_argument_conditionally (p); lhs = stap_parse_argument_conditionally (p);
} }
if (p->inside_paren_p) if (p->inside_paren_p)
@ -1117,12 +1137,12 @@ stap_parse_argument_1 (struct stap_parse_info *p, bool has_lhs,
processing this part of the expression before continuing. */ processing this part of the expression before continuing. */
bool paren_subexp = *p->arg == '('; bool paren_subexp = *p->arg == '(';
stap_parse_argument_conditionally (p); operation_up rhs = stap_parse_argument_conditionally (p);
if (p->inside_paren_p) if (p->inside_paren_p)
p->arg = skip_spaces (p->arg); p->arg = skip_spaces (p->arg);
if (paren_subexp) if (paren_subexp)
{ {
write_exp_elt_opcode (&p->pstate, opcode); lhs = stap_make_binop (opcode, std::move (lhs), std::move (rhs));
continue; continue;
} }
@ -1146,15 +1166,18 @@ stap_parse_argument_1 (struct stap_parse_info *p, bool has_lhs,
break; break;
} }
/* Parse the right-side of the expression, but since we already /* Parse the right-side of the expression, using the current
have a left-side at this point, set `has_lhs' to 1. */ right-hand-side as the left-hand-side of the new
stap_parse_argument_1 (p, 1, lookahead_prec); subexpression. */
rhs = stap_parse_argument_1 (p, std::move (rhs), lookahead_prec);
if (p->inside_paren_p) if (p->inside_paren_p)
p->arg = skip_spaces (p->arg); p->arg = skip_spaces (p->arg);
} }
write_exp_elt_opcode (&p->pstate, opcode); lhs = stap_make_binop (opcode, std::move (lhs), std::move (rhs));
} }
return lhs;
} }
/* Parse a probe's argument. /* Parse a probe's argument.
@ -1194,14 +1217,14 @@ stap_parse_argument (const char **arg, struct type *atype,
struct stap_parse_info p (*arg, atype, language_def (language_c), struct stap_parse_info p (*arg, atype, language_def (language_c),
gdbarch); gdbarch);
stap_parse_argument_1 (&p, 0, STAP_OPERAND_PREC_NONE); using namespace expr;
operation_up result = stap_parse_argument_1 (&p, {}, STAP_OPERAND_PREC_NONE);
gdb_assert (p.inside_paren_p == 0); gdb_assert (p.inside_paren_p == 0);
/* Casting the final expression to the appropriate type. */ /* Casting the final expression to the appropriate type. */
write_exp_elt_opcode (&p.pstate, UNOP_CAST); result = make_operation<unop_cast_operation> (std::move (result), atype);
write_exp_elt_type (&p.pstate, atype); p.pstate.set_operation (std::move (result));
write_exp_elt_opcode (&p.pstate, UNOP_CAST);
p.arg = skip_spaces (p.arg); p.arg = skip_spaces (p.arg);
*arg = p.arg; *arg = p.arg;
@ -1290,12 +1313,6 @@ stap_probe::parse_arguments (struct gdbarch *gdbarch)
expression_up expr = stap_parse_argument (&cur, atype, gdbarch); expression_up expr = stap_parse_argument (&cur, atype, gdbarch);
if (stap_expression_debug)
dump_raw_expression (expr.get (), gdb_stdlog,
"before conversion to prefix form");
prefixify_expression (expr.get ());
if (stap_expression_debug) if (stap_expression_debug)
dump_prefix_expression (expr.get (), gdb_stdlog); dump_prefix_expression (expr.get (), gdb_stdlog);
@ -1747,4 +1764,24 @@ NAME matches the probe names.\n\
OBJECT matches the executable or shared library name."), OBJECT matches the executable or shared library name."),
info_probes_cmdlist_get ()); info_probes_cmdlist_get ());
using namespace expr;
stap_maker_map[BINOP_ADD] = make_operation<add_operation>;
stap_maker_map[BINOP_BITWISE_AND] = make_operation<bitwise_and_operation>;
stap_maker_map[BINOP_BITWISE_IOR] = make_operation<bitwise_ior_operation>;
stap_maker_map[BINOP_BITWISE_XOR] = make_operation<bitwise_xor_operation>;
stap_maker_map[BINOP_DIV] = make_operation<div_operation>;
stap_maker_map[BINOP_EQUAL] = make_operation<equal_operation>;
stap_maker_map[BINOP_GEQ] = make_operation<geq_operation>;
stap_maker_map[BINOP_GTR] = make_operation<gtr_operation>;
stap_maker_map[BINOP_LEQ] = make_operation<leq_operation>;
stap_maker_map[BINOP_LESS] = make_operation<less_operation>;
stap_maker_map[BINOP_LOGICAL_AND] = make_operation<logical_and_operation>;
stap_maker_map[BINOP_LOGICAL_OR] = make_operation<logical_or_operation>;
stap_maker_map[BINOP_LSH] = make_operation<lsh_operation>;
stap_maker_map[BINOP_MUL] = make_operation<mul_operation>;
stap_maker_map[BINOP_NOTEQUAL] = make_operation<notequal_operation>;
stap_maker_map[BINOP_REM] = make_operation<rem_operation>;
stap_maker_map[BINOP_RSH] = make_operation<rsh_operation>;
stap_maker_map[BINOP_SUB] = make_operation<sub_operation>;
} }