-/* GDB-specific functions for operating on agent expressions
- Copyright 1998, 1999, 2000, 2001 Free Software Foundation, Inc.
+/* GDB-specific functions for operating on agent expressions.
+
+ Copyright (C) 1998, 1999, 2000, 2001, 2003, 2007
+ Free Software Foundation, Inc.
This file is part of GDB.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
- Foundation, Inc., 59 Temple Place - Suite 330,
- Boston, MA 02111-1307, USA. */
+ Foundation, Inc., 51 Franklin Street, Fifth Floor,
+ Boston, MA 02110-1301, USA. */
#include "defs.h"
#include "symtab.h"
#include "target.h"
#include "ax.h"
#include "ax-gdb.h"
+#include "gdb_string.h"
+#include "block.h"
+#include "regcache.h"
/* To make sense of this file, you should read doc/agentexpr.texi.
Then look at the types and enums in ax-gdb.h. For the code itself,
static void gen_expr (union exp_element **pc,
struct agent_expr *ax, struct axs_value *value);
-static void print_axs_value (struct ui_file *f, struct axs_value * value);
static void agent_command (char *exp, int from_tty);
\f
{
/* Do we need to sign-extend this? */
if (!TYPE_UNSIGNED (type))
- ax_ext (ax, type->length * TARGET_CHAR_BIT);
+ ax_ext (ax, TYPE_LENGTH (type) * TARGET_CHAR_BIT);
}
static void
gen_extend (struct agent_expr *ax, struct type *type)
{
- int bits = type->length * TARGET_CHAR_BIT;
+ int bits = TYPE_LENGTH (type) * TARGET_CHAR_BIT;
/* I just had to. */
((TYPE_UNSIGNED (type) ? ax_zero_ext : ax_ext) (ax, bits));
}
ax_trace_quick (ax, TYPE_LENGTH (type));
}
- switch (type->code)
+ switch (TYPE_CODE (type))
{
case TYPE_CODE_PTR:
case TYPE_CODE_ENUM:
case TYPE_CODE_CHAR:
/* It's a scalar value, so we know how to dereference it. How
many bytes long is it? */
- switch (type->length)
+ switch (TYPE_LENGTH (type))
{
case 8 / TARGET_CHAR_BIT:
ax_simple (ax, aop_ref8);
In any case, it's a bug the user shouldn't see. */
default:
internal_error (__FILE__, __LINE__,
- "gen_fetch: strange size");
+ _("gen_fetch: strange size"));
}
gen_sign_extend (ax, type);
something we should be (this code's fault). In any case,
it's a bug the user shouldn't see. */
internal_error (__FILE__, __LINE__,
- "gen_fetch: bad type code");
+ _("gen_fetch: bad type code"));
}
}
static void
gen_frame_args_address (struct agent_expr *ax)
{
- long frame_reg, frame_offset;
+ int frame_reg;
+ LONGEST frame_offset;
TARGET_VIRTUAL_FRAME_POINTER (ax->scope, &frame_reg, &frame_offset);
ax_reg (ax, frame_reg);
static void
gen_frame_locals_address (struct agent_expr *ax)
{
- long frame_reg, frame_offset;
+ int frame_reg;
+ LONGEST frame_offset;
TARGET_VIRTUAL_FRAME_POINTER (ax->scope, &frame_reg, &frame_offset);
ax_reg (ax, frame_reg);
case LOC_CONST_BYTES:
internal_error (__FILE__, __LINE__,
- "gen_var_ref: LOC_CONST_BYTES symbols are not supported");
+ _("gen_var_ref: LOC_CONST_BYTES symbols are not supported"));
/* Variable at a fixed location in memory. Easy. */
case LOC_STATIC:
break;
case LOC_TYPEDEF:
- error ("Cannot compute value of typedef `%s'.",
- SYMBOL_SOURCE_NAME (var));
+ error (_("Cannot compute value of typedef `%s'."),
+ SYMBOL_PRINT_NAME (var));
break;
case LOC_BLOCK:
case LOC_UNRESOLVED:
{
struct minimal_symbol *msym
- = lookup_minimal_symbol (SYMBOL_NAME (var), NULL, NULL);
+ = lookup_minimal_symbol (DEPRECATED_SYMBOL_NAME (var), NULL, NULL);
if (!msym)
- error ("Couldn't resolve symbol `%s'.", SYMBOL_SOURCE_NAME (var));
+ error (_("Couldn't resolve symbol `%s'."), SYMBOL_PRINT_NAME (var));
/* Push the address of the variable. */
ax_const_l (ax, SYMBOL_VALUE_ADDRESS (msym));
}
break;
+ case LOC_COMPUTED:
+ case LOC_COMPUTED_ARG:
+ /* FIXME: cagney/2004-01-26: It should be possible to
+ unconditionally call the SYMBOL_OPS method when available.
+ Unfortunately DWARF 2 stores the frame-base (instead of the
+ function) location in a function's symbol. Oops! For the
+ moment enable this when/where applicable. */
+ SYMBOL_OPS (var)->tracepoint_var_ref (var, ax, value);
+ break;
+
case LOC_OPTIMIZED_OUT:
- error ("The variable `%s' has been optimized out.",
- SYMBOL_SOURCE_NAME (var));
+ error (_("The variable `%s' has been optimized out."),
+ SYMBOL_PRINT_NAME (var));
break;
default:
- error ("Cannot find value of botched symbol `%s'.",
- SYMBOL_SOURCE_NAME (var));
+ error (_("Cannot find value of botched symbol `%s'."),
+ SYMBOL_PRINT_NAME (var));
break;
}
}
the stack. Should we tweak the type? */
/* Some types require special handling. */
- switch (value->type->code)
+ switch (TYPE_CODE (value->type))
{
/* Functions get converted to a pointer to the function. */
case TYPE_CODE_FUNC:
/* Dereference typedefs. */
type = check_typedef (type);
- switch (type->code)
+ switch (TYPE_CODE (type))
{
case TYPE_CODE_PTR:
/* It's implementation-defined, and I'll bet this is what GCC
case TYPE_CODE_STRUCT:
case TYPE_CODE_UNION:
case TYPE_CODE_FUNC:
- error ("Illegal type cast: intended type must be scalar.");
+ error (_("Invalid type cast: intended type must be scalar."));
case TYPE_CODE_ENUM:
/* We don't have to worry about the size of the value, because
break;
default:
- error ("Casts to requested type are not yet implemented.");
+ error (_("Casts to requested type are not yet implemented."));
}
value->type = type;
{
struct type *element = TYPE_TARGET_TYPE (type);
- if (element->length != 1)
+ if (TYPE_LENGTH (element) != 1)
{
- ax_const_l (ax, element->length);
+ ax_const_l (ax, TYPE_LENGTH (element));
ax_simple (ax, op);
}
}
struct axs_value *value1, struct axs_value *value2, char *name)
{
/* Is it INT+PTR? */
- if (value1->type->code == TYPE_CODE_INT
- && value2->type->code == TYPE_CODE_PTR)
+ if (TYPE_CODE (value1->type) == TYPE_CODE_INT
+ && TYPE_CODE (value2->type) == TYPE_CODE_PTR)
{
/* Swap the values and proceed normally. */
ax_simple (ax, aop_swap);
}
/* Is it PTR+INT? */
- else if (value1->type->code == TYPE_CODE_PTR
- && value2->type->code == TYPE_CODE_INT)
+ else if (TYPE_CODE (value1->type) == TYPE_CODE_PTR
+ && TYPE_CODE (value2->type) == TYPE_CODE_INT)
{
gen_scale (ax, aop_mul, value1->type);
ax_simple (ax, aop_add);
/* Must be number + number; the usual binary conversions will have
brought them both to the same width. */
- else if (value1->type->code == TYPE_CODE_INT
- && value2->type->code == TYPE_CODE_INT)
+ else if (TYPE_CODE (value1->type) == TYPE_CODE_INT
+ && TYPE_CODE (value2->type) == TYPE_CODE_INT)
{
ax_simple (ax, aop_add);
gen_extend (ax, value1->type); /* Catch overflow. */
}
else
- error ("Illegal combination of types in %s.", name);
+ error (_("Invalid combination of types in %s."), name);
value->kind = axs_rvalue;
}
gen_sub (struct agent_expr *ax, struct axs_value *value,
struct axs_value *value1, struct axs_value *value2)
{
- if (value1->type->code == TYPE_CODE_PTR)
+ if (TYPE_CODE (value1->type) == TYPE_CODE_PTR)
{
/* Is it PTR - INT? */
- if (value2->type->code == TYPE_CODE_INT)
+ if (TYPE_CODE (value2->type) == TYPE_CODE_INT)
{
gen_scale (ax, aop_mul, value1->type);
ax_simple (ax, aop_sub);
/* Is it PTR - PTR? Strictly speaking, the types ought to
match, but this is what the normal GDB expression evaluator
tests for. */
- else if (value2->type->code == TYPE_CODE_PTR
+ else if (TYPE_CODE (value2->type) == TYPE_CODE_PTR
&& (TYPE_LENGTH (TYPE_TARGET_TYPE (value1->type))
== TYPE_LENGTH (TYPE_TARGET_TYPE (value2->type))))
{
value->type = builtin_type_long; /* FIXME --- should be ptrdiff_t */
}
else
- error ("\
+ error (_("\
First argument of `-' is a pointer, but second argument is neither\n\
-an integer nor a pointer of the same type.");
+an integer nor a pointer of the same type."));
}
/* Must be number + number. */
- else if (value1->type->code == TYPE_CODE_INT
- && value2->type->code == TYPE_CODE_INT)
+ else if (TYPE_CODE (value1->type) == TYPE_CODE_INT
+ && TYPE_CODE (value2->type) == TYPE_CODE_INT)
{
ax_simple (ax, aop_sub);
gen_extend (ax, value1->type); /* Catch overflow. */
}
else
- error ("Illegal combination of types in subtraction.");
+ error (_("Invalid combination of types in subtraction."));
value->kind = axs_rvalue;
}
enum agent_op op_unsigned, int may_carry, char *name)
{
/* We only handle INT op INT. */
- if ((value1->type->code != TYPE_CODE_INT)
- || (value2->type->code != TYPE_CODE_INT))
- error ("Illegal combination of types in %s.", name);
+ if ((TYPE_CODE (value1->type) != TYPE_CODE_INT)
+ || (TYPE_CODE (value2->type) != TYPE_CODE_INT))
+ error (_("Invalid combination of types in %s."), name);
ax_simple (ax,
TYPE_UNSIGNED (value1->type) ? op_unsigned : op);
{
if (TYPE_CODE (value->type) != TYPE_CODE_INT
&& TYPE_CODE (value->type) != TYPE_CODE_PTR)
- error ("Illegal type of operand to `!'.");
+ error (_("Invalid type of operand to `!'."));
gen_usual_unary (ax, value);
ax_simple (ax, aop_log_not);
gen_complement (struct agent_expr *ax, struct axs_value *value)
{
if (TYPE_CODE (value->type) != TYPE_CODE_INT)
- error ("Illegal type of operand to `~'.");
+ error (_("Invalid type of operand to `~'."));
gen_usual_unary (ax, value);
gen_integral_promotions (ax, value);
{
/* The caller should check the type, because several operators use
this, and we don't know what error message to generate. */
- if (value->type->code != TYPE_CODE_PTR)
+ if (TYPE_CODE (value->type) != TYPE_CODE_PTR)
internal_error (__FILE__, __LINE__,
- "gen_deref: expected a pointer");
+ _("gen_deref: expected a pointer"));
/* We've got an rvalue now, which is a pointer. We want to yield an
lvalue, whose address is exactly that pointer. So we don't
T" to "T", and mark the value as an lvalue in memory. Leave it
to the consumer to actually dereference it. */
value->type = check_typedef (TYPE_TARGET_TYPE (value->type));
- value->kind = ((value->type->code == TYPE_CODE_FUNC)
+ value->kind = ((TYPE_CODE (value->type) == TYPE_CODE_FUNC)
? axs_rvalue : axs_lvalue_memory);
}
/* Special case for taking the address of a function. The ANSI
standard describes this as a special case, too, so this
arrangement is not without motivation. */
- if (value->type->code == TYPE_CODE_FUNC)
+ if (TYPE_CODE (value->type) == TYPE_CODE_FUNC)
/* The value's already an rvalue on the stack, so we just need to
change the type. */
value->type = lookup_pointer_type (value->type);
switch (value->kind)
{
case axs_rvalue:
- error ("Operand of `&' is an rvalue, which has no address.");
+ error (_("Operand of `&' is an rvalue, which has no address."));
case axs_lvalue_register:
- error ("Operand of `&' is in a register, and has no address.");
+ error (_("Operand of `&' is in a register, and has no address."));
case axs_lvalue_memory:
value->kind = axs_rvalue;
/* Make sure this isn't C++. */
if (TYPE_N_BASECLASSES (type) != 0)
internal_error (__FILE__, __LINE__,
- "find_field: derived classes supported");
+ _("find_field: derived classes supported"));
for (i = 0; i < TYPE_NFIELDS (type); i++)
{
char *this_name = TYPE_FIELD_NAME (type, i);
- if (this_name && STREQ (name, this_name))
+ if (this_name && strcmp (name, this_name) == 0)
return i;
if (this_name[0] == '\0')
internal_error (__FILE__, __LINE__,
- "find_field: anonymous unions not supported");
+ _("find_field: anonymous unions not supported"));
}
- error ("Couldn't find member named `%s' in struct/union `%s'",
- name, type->tag_name);
+ error (_("Couldn't find member named `%s' in struct/union `%s'"),
+ name, TYPE_TAG_NAME (type));
return 0;
}
/* Can we fetch the number of bits requested at all? */
if ((end - start) > ((1 << num_ops) * 8))
internal_error (__FILE__, __LINE__,
- "gen_bitfield_ref: bitfield too wide");
+ _("gen_bitfield_ref: bitfield too wide"));
/* Note that we know here that we only need to try each opcode once.
That may not be true on machines with weird byte sizes. */
the sign/zero extension will wipe them out.
- If we're in the interior of the word, then there is no garbage
on either end, because the ref operators zero-extend. */
- if (TARGET_BYTE_ORDER == BIG_ENDIAN)
+ if (TARGET_BYTE_ORDER == BFD_ENDIAN_BIG)
gen_left_shift (ax, end - (offset + op_size));
else
gen_left_shift (ax, offset - start);
/* Follow pointers until we reach a non-pointer. These aren't the C
semantics, but they're what the normal GDB evaluator does, so we
should at least be consistent. */
- while (value->type->code == TYPE_CODE_PTR)
+ while (TYPE_CODE (value->type) == TYPE_CODE_PTR)
{
gen_usual_unary (ax, value);
gen_deref (ax, value);
/* This must yield a structure or a union. */
if (TYPE_CODE (type) != TYPE_CODE_STRUCT
&& TYPE_CODE (type) != TYPE_CODE_UNION)
- error ("The left operand of `%s' is not a %s.",
+ error (_("The left operand of `%s' is not a %s."),
operator_name, operand_name);
/* And it must be in memory; we don't deal with structure rvalues,
or structures living in registers. */
if (value->kind != axs_lvalue_memory)
- error ("Structure does not live in memory.");
+ error (_("Structure does not live in memory."));
i = find_field (type, field);
here. */
gen_expr (pc, ax, &value1);
if (value1.kind != axs_lvalue_memory)
- error ("Left operand of `@' must be an object in memory.");
+ error (_("Left operand of `@' must be an object in memory."));
/* Evaluate the length; it had better be a constant. */
{
int length;
if (!v)
- error ("Right operand of `@' must be a constant, in agent expressions.");
- if (v->type->code != TYPE_CODE_INT)
- error ("Right operand of `@' must be an integer.");
+ error (_("Right operand of `@' must be a constant, in agent expressions."));
+ if (TYPE_CODE (value_type (v)) != TYPE_CODE_INT)
+ error (_("Right operand of `@' must be an integer."));
length = value_as_long (v);
if (length <= 0)
- error ("Right operand of `@' must be positive.");
+ error (_("Right operand of `@' must be positive."));
/* The top of the stack is already the address of the object, so
all we need to do is frob the type of the lvalue. */
/* Generating bytecode from GDB expressions: general recursive thingy */
+/* XXX: i18n */
/* A gen_expr function written by a Gen-X'er guy.
Append code for the subexpression of EXPR starting at *POS_P to AX. */
static void
{
ax_const_l (ax, value_as_long (v));
value->kind = axs_rvalue;
- value->type = check_typedef (VALUE_TYPE (v));
+ value->type = check_typedef (value_type (v));
return;
}
}
case BINOP_SUBSCRIPT:
gen_add (ax, value, &value1, &value2, "array subscripting");
if (TYPE_CODE (value->type) != TYPE_CODE_PTR)
- error ("Illegal combination of types in array subscripting.");
+ error (_("Invalid combination of types in array subscripting."));
gen_deref (ax, value);
break;
case BINOP_BITWISE_AND:
/* We should only list operators in the outer case statement
that we actually handle in the inner case statement. */
internal_error (__FILE__, __LINE__,
- "gen_expr: op case sets don't match");
+ _("gen_expr: op case sets don't match"));
}
break;
(*pc) += 3;
value->kind = axs_lvalue_register;
value->u.reg = reg;
- value->type = REGISTER_VIRTUAL_TYPE (reg);
+ value->type = register_type (current_gdbarch, reg);
}
break;
case OP_INTERNALVAR:
- error ("GDB agent expressions cannot use convenience variables.");
+ error (_("GDB agent expressions cannot use convenience variables."));
/* Weirdo operator: see comments for gen_repeat for details. */
case BINOP_REPEAT:
if (value->kind != axs_rvalue)
/* This would be weird. */
internal_error (__FILE__, __LINE__,
- "gen_expr: OP_MEMVAL operand isn't an rvalue???");
+ _("gen_expr: OP_MEMVAL operand isn't an rvalue???"));
value->type = type;
value->kind = axs_lvalue_memory;
}
break;
+ case UNOP_PLUS:
+ (*pc)++;
+ /* + FOO is equivalent to 0 + FOO, which can be optimized. */
+ gen_expr (pc, ax, value);
+ gen_usual_unary (ax, value);
+ break;
+
case UNOP_NEG:
(*pc)++;
/* -FOO is equivalent to 0 - FOO. */
gen_expr (pc, ax, value);
gen_usual_unary (ax, value);
if (TYPE_CODE (value->type) != TYPE_CODE_PTR)
- error ("Argument of unary `*' is not a pointer.");
+ error (_("Argument of unary `*' is not a pointer."));
gen_deref (ax, value);
break;
/* If this `if' chain doesn't handle it, then the case list
shouldn't mention it, and we shouldn't be here. */
internal_error (__FILE__, __LINE__,
- "gen_expr: unhandled struct case");
+ _("gen_expr: unhandled struct case"));
}
break;
case OP_TYPE:
- error ("Attempt to use a type name as an expression.");
+ error (_("Attempt to use a type name as an expression."));
default:
- error ("Unsupported operator in expression.");
+ error (_("Unsupported operator in expression."));
}
}
\f
if (value.kind != axs_lvalue_memory)
{
free_agent_expr (ax);
- error ("Expression does not denote an object in memory.");
+ error (_("Expression does not denote an object in memory."));
}
/* Push the object's size on the stack. */
discard_cleanups (old_chain);
return ax;
}
-\f
-
-
-/* The "agent" command, for testing: compile and disassemble an expression. */
-
-static void
-print_axs_value (struct ui_file *f, struct axs_value *value)
-{
- switch (value->kind)
- {
- case axs_rvalue:
- fputs_filtered ("rvalue", f);
- break;
-
- case axs_lvalue_memory:
- fputs_filtered ("memory lvalue", f);
- break;
-
- case axs_lvalue_register:
- fprintf_filtered (f, "register %d lvalue", value->u.reg);
- break;
- }
-
- fputs_filtered (" : ", f);
- type_print (value->type, "", f, -1);
-}
-
static void
agent_command (char *exp, int from_tty)
another command, change the error message; the user shouldn't
have to know anything about agent expressions. */
if (overlay_debugging)
- error ("GDB can't do agent expression translation with overlays.");
+ error (_("GDB can't do agent expression translation with overlays."));
if (exp == 0)
- error_no_arg ("expression to translate");
+ error_no_arg (_("expression to translate"));
expr = parse_expression (exp);
old_chain = make_cleanup (free_current_contents, &expr);
- agent = gen_trace_for_expr (fi->pc, expr);
+ agent = gen_trace_for_expr (get_frame_pc (fi), expr);
make_cleanup_free_agent_expr (agent);
ax_print (gdb_stdout, agent);
_initialize_ax_gdb (void)
{
add_cmd ("agent", class_maintenance, agent_command,
- "Translate an expression into remote agent bytecode.",
+ _("Translate an expression into remote agent bytecode."),
&maintenancelist);
}