summaryrefslogtreecommitdiffstats
path: root/contrib/gdb/gdb/eval.c
diff options
context:
space:
mode:
Diffstat (limited to 'contrib/gdb/gdb/eval.c')
-rw-r--r--contrib/gdb/gdb/eval.c359
1 files changed, 284 insertions, 75 deletions
diff --git a/contrib/gdb/gdb/eval.c b/contrib/gdb/gdb/eval.c
index ed9fd53..d3c3465 100644
--- a/contrib/gdb/gdb/eval.c
+++ b/contrib/gdb/gdb/eval.c
@@ -1,5 +1,5 @@
/* Evaluate expressions for GDB.
- Copyright 1986, 1987, 1989, 1991, 1992, 1993, 1994, 1995
+ Copyright 1986, 87, 89, 91, 92, 93, 94, 95, 96, 97, 1998
Free Software Foundation, Inc.
This file is part of GDB.
@@ -30,6 +30,13 @@ Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */
#include "language.h" /* For CAST_IS_CONVERSION */
#include "f-lang.h" /* for array bound stuff */
+/* Defined in symtab.c */
+extern int hp_som_som_object_present;
+
+/* This is defined in valops.c */
+extern int overload_resolution;
+
+
/* Prototypes for local functions. */
static value_ptr evaluate_subexp_for_sizeof PARAMS ((struct expression *,
@@ -38,6 +45,19 @@ static value_ptr evaluate_subexp_for_sizeof PARAMS ((struct expression *,
static value_ptr evaluate_subexp_for_address PARAMS ((struct expression *,
int *, enum noside));
+static value_ptr evaluate_subexp PARAMS ((struct type *, struct expression *,
+ int *, enum noside));
+
+static char *get_label PARAMS ((struct expression *, int *));
+
+static value_ptr
+evaluate_struct_tuple PARAMS ((value_ptr, struct expression *, int *,
+ enum noside, int));
+
+static LONGEST
+init_array_element PARAMS ((value_ptr, value_ptr, struct expression *,
+ int *, enum noside, LONGEST, LONGEST));
+
#ifdef __GNUC__
inline
#endif
@@ -61,7 +81,7 @@ parse_and_eval_address (exp)
struct expression *expr = parse_expression (exp);
register CORE_ADDR addr;
register struct cleanup *old_chain =
- make_cleanup (free_current_contents, &expr);
+ make_cleanup ((make_cleanup_func) free_current_contents, &expr);
addr = value_as_pointer (evaluate_expression (expr));
do_cleanups (old_chain);
@@ -78,7 +98,7 @@ parse_and_eval_address_1 (expptr)
struct expression *expr = parse_exp_1 (expptr, (struct block *)0, 0);
register CORE_ADDR addr;
register struct cleanup *old_chain =
- make_cleanup (free_current_contents, &expr);
+ make_cleanup ((make_cleanup_func) free_current_contents, &expr);
addr = value_as_pointer (evaluate_expression (expr));
do_cleanups (old_chain);
@@ -92,7 +112,7 @@ parse_and_eval (exp)
struct expression *expr = parse_expression (exp);
register value_ptr val;
register struct cleanup *old_chain
- = make_cleanup (free_current_contents, &expr);
+ = make_cleanup ((make_cleanup_func) free_current_contents, &expr);
val = evaluate_expression (expr);
do_cleanups (old_chain);
@@ -110,7 +130,7 @@ parse_to_comma_and_eval (expp)
struct expression *expr = parse_exp_1 (expp, (struct block *) 0, 1);
register value_ptr val;
register struct cleanup *old_chain
- = make_cleanup (free_current_contents, &expr);
+ = make_cleanup ((make_cleanup_func) free_current_contents, &expr);
val = evaluate_expression (expr);
do_cleanups (old_chain);
@@ -316,6 +336,7 @@ init_array_element (array, element, exp, pos, noside, low_bound, high_bound)
register struct expression *exp;
register int *pos;
enum noside noside;
+ LONGEST low_bound, high_bound;
{
LONGEST index;
int element_size = TYPE_LENGTH (VALUE_TYPE (element));
@@ -369,6 +390,11 @@ evaluate_subexp_standard (expect_type, exp, pos, noside)
value_ptr *argvec;
int upper, lower, retcode;
int code;
+ int ix;
+ long mem_offset;
+ struct symbol * sym;
+ struct type ** arg_types;
+ int save_pos1;
/* This expect_type crap should not be used for C. C expressions do
not have any notion of expected types, never has and (goddess
@@ -449,9 +475,16 @@ evaluate_subexp_standard (expect_type, exp, pos, noside)
access_value_history (longest_to_int (exp->elts[pc + 1].longconst));
case OP_REGISTER:
- (*pos) += 2;
- return value_of_register (longest_to_int (exp->elts[pc + 1].longconst));
-
+ {
+ int regno = longest_to_int (exp->elts[pc + 1].longconst);
+ value_ptr val = value_of_register (regno);
+
+ (*pos) += 2;
+ if (val == NULL)
+ error ("Value of register %s not available.", REGISTER_NAME (regno));
+ else
+ return val;
+ }
case OP_BOOL:
(*pos) += 2;
return value_from_longest (LA_BOOL_TYPE,
@@ -529,6 +562,9 @@ evaluate_subexp_standard (expect_type, exp, pos, noside)
}
else
{
+ if (index > high_bound)
+ /* to avoid memory corruption */
+ error ("Too many array elements");
memcpy (VALUE_CONTENTS_RAW (array)
+ (index - low_bound) * element_size,
VALUE_CONTENTS (element),
@@ -545,27 +581,54 @@ evaluate_subexp_standard (expect_type, exp, pos, noside)
value_ptr set = allocate_value (expect_type);
char *valaddr = VALUE_CONTENTS_RAW (set);
struct type *element_type = TYPE_INDEX_TYPE (type);
+ struct type *check_type = element_type;
LONGEST low_bound, high_bound;
+
+ /* get targettype of elementtype */
+ while (TYPE_CODE (check_type) == TYPE_CODE_RANGE ||
+ TYPE_CODE (check_type) == TYPE_CODE_TYPEDEF)
+ check_type = TYPE_TARGET_TYPE (check_type);
+
if (get_discrete_bounds (element_type, &low_bound, &high_bound) < 0)
error ("(power)set type with unknown size");
memset (valaddr, '\0', TYPE_LENGTH (type));
for (tem = 0; tem < nargs; tem++)
{
LONGEST range_low, range_high;
+ struct type *range_low_type, *range_high_type;
value_ptr elem_val;
if (exp->elts[*pos].opcode == BINOP_RANGE)
{
(*pos)++;
elem_val = evaluate_subexp (element_type, exp, pos, noside);
+ range_low_type = VALUE_TYPE (elem_val);
range_low = value_as_long (elem_val);
elem_val = evaluate_subexp (element_type, exp, pos, noside);
+ range_high_type = VALUE_TYPE (elem_val);
range_high = value_as_long (elem_val);
}
else
{
elem_val = evaluate_subexp (element_type, exp, pos, noside);
+ range_low_type = range_high_type = VALUE_TYPE (elem_val);
range_low = range_high = value_as_long (elem_val);
}
+ /* check types of elements to avoid mixture of elements from
+ different types. Also check if type of element is "compatible"
+ with element type of powerset */
+ if (TYPE_CODE (range_low_type) == TYPE_CODE_RANGE)
+ range_low_type = TYPE_TARGET_TYPE (range_low_type);
+ if (TYPE_CODE (range_high_type) == TYPE_CODE_RANGE)
+ range_high_type = TYPE_TARGET_TYPE (range_high_type);
+ if ((TYPE_CODE (range_low_type) != TYPE_CODE (range_high_type)) ||
+ (TYPE_CODE (range_low_type) == TYPE_CODE_ENUM &&
+ (range_low_type != range_high_type)))
+ /* different element modes */
+ error ("POWERSET tuple elements of different mode");
+ if ((TYPE_CODE (check_type) != TYPE_CODE (range_low_type)) ||
+ (TYPE_CODE (check_type) == TYPE_CODE_ENUM &&
+ range_low_type != check_type))
+ error ("incompatible POWERSET tuple elements");
if (range_low > range_high)
{
warning ("empty POWERSET tuple range");
@@ -645,6 +708,14 @@ evaluate_subexp_standard (expect_type, exp, pos, noside)
{
LONGEST fnptr;
+ /* 1997-08-01 Currently we do not support function invocation
+ via pointers-to-methods with HP aCC. Pointer does not point
+ to the function, but possibly to some thunk. */
+ if (hp_som_som_object_present)
+ {
+ error ("Not implemented: function invocation through pointer to method with HP aCC");
+ }
+
nargs++;
/* First, evaluate the structure into arg2 */
pc2 = (*pos)++;
@@ -748,6 +819,8 @@ evaluate_subexp_standard (expect_type, exp, pos, noside)
}
else
{
+ /* Non-method function call */
+ save_pos1 = *pos;
argvec[0] = evaluate_subexp_with_coercion (exp, pos, noside);
tem = 1;
type = VALUE_TYPE (argvec[0]);
@@ -757,16 +830,18 @@ evaluate_subexp_standard (expect_type, exp, pos, noside)
{
for (; tem <= nargs && tem <= TYPE_NFIELDS (type); tem++)
{
+ /* pai: FIXME This seems to be coercing arguments before
+ * overload resolution has been done! */
argvec[tem] = evaluate_subexp (TYPE_FIELD_TYPE (type, tem-1),
exp, pos, noside);
}
}
}
+ /* Evaluate arguments */
for (; tem <= nargs; tem++)
{
/* Ensure that array expressions are coerced into pointer objects. */
-
argvec[tem] = evaluate_subexp_with_coercion (exp, pos, noside);
}
@@ -777,23 +852,48 @@ evaluate_subexp_standard (expect_type, exp, pos, noside)
{
int static_memfuncp;
value_ptr temp = arg2;
- char tstr[64];
-
- argvec[1] = arg2;
- argvec[0] = 0;
- strcpy(tstr, &exp->elts[pc2+2].string);
- if (!argvec[0])
- {
- temp = arg2;
- argvec[0] =
- value_struct_elt (&temp, argvec+1, tstr,
- &static_memfuncp,
- op == STRUCTOP_STRUCT
- ? "structure" : "structure pointer");
- }
- arg2 = value_from_longest (lookup_pointer_type(VALUE_TYPE (temp)),
- VALUE_ADDRESS (temp)+VALUE_OFFSET (temp));
- argvec[1] = arg2;
+ char tstr[256];
+ struct fn_field * fns_ptr;
+ int num_fns;
+ struct type * basetype;
+ int boffset;
+
+ /* Method invocation : stuff "this" as first parameter */
+ /* pai: this used to have lookup_pointer_type for some reason,
+ * but temp is already a pointer to the object */
+ argvec[1] = value_from_longest (VALUE_TYPE (temp),
+ VALUE_ADDRESS (temp)+VALUE_OFFSET (temp));
+ /* Name of method from expression */
+ strcpy(tstr, &exp->elts[pc2+2].string);
+
+ if (overload_resolution && (exp->language_defn->la_language == language_cplus))
+ {
+ /* Language is C++, do some overload resolution before evaluation */
+ value_ptr valp = NULL;
+
+ /* Prepare list of argument types for overload resolution */
+ arg_types = (struct type **) xmalloc (nargs * (sizeof (struct type *)));
+ for (ix=1; ix <= nargs; ix++)
+ arg_types[ix-1] = VALUE_TYPE (argvec[ix]);
+
+ (void) find_overload_match (arg_types, nargs, tstr,
+ 1 /* method */, 0 /* strict match */,
+ arg2 /* the object */, NULL,
+ &valp, NULL, &static_memfuncp);
+
+
+ argvec[1] = arg2; /* the ``this'' pointer */
+ argvec[0] = valp; /* use the method found after overload resolution */
+ }
+ else /* Non-C++ case -- or no overload resolution */
+ {
+ temp = arg2;
+ argvec[0] = value_struct_elt (&temp, argvec+1, tstr,
+ &static_memfuncp,
+ op == STRUCTOP_STRUCT
+ ? "structure" : "structure pointer");
+ argvec[1] = arg2; /* the ``this'' pointer */
+ }
if (static_memfuncp)
{
@@ -807,6 +907,35 @@ evaluate_subexp_standard (expect_type, exp, pos, noside)
argvec[1] = arg2;
argvec[0] = arg1;
}
+ else
+ {
+ /* Non-member function being called */
+
+ if (overload_resolution && (exp->language_defn->la_language == language_cplus))
+ {
+ /* Language is C++, do some overload resolution before evaluation */
+ struct symbol * symp;
+
+ /* Prepare list of argument types for overload resolution */
+ arg_types = (struct type **) xmalloc (nargs * (sizeof (struct type *)));
+ for (ix=1; ix <= nargs; ix++)
+ arg_types[ix-1] = VALUE_TYPE (argvec[ix]);
+
+ (void) find_overload_match (arg_types, nargs, NULL /* no need for name */,
+ 0 /* not method */, 0 /* strict match */,
+ NULL, exp->elts[5].symbol /* the function */,
+ NULL, &symp, NULL);
+
+ /* Now fix the expression being evaluated */
+ exp->elts[5].symbol = symp;
+ argvec[0] = evaluate_subexp_with_coercion (exp, &save_pos1, noside);
+ }
+ else
+ {
+ /* Not C++, or no overload resolution allowed */
+ /* nothing to be done; argvec already correctly set up */
+ }
+ }
do_call_it:
@@ -829,7 +958,10 @@ evaluate_subexp_standard (expect_type, exp, pos, noside)
else
error ("Expression of type other than \"Function returning ...\" used as function");
}
+ if (argvec[0] == NULL)
+ error ("Cannot evaluate function -- may be inlined");
return call_function_by_hand (argvec[0], nargs, argvec + 1);
+ /* pai: FIXME save value from call_function_by_hand, then adjust pc by adjust_fn_pc if +ve */
case OP_F77_UNDETERMINED_ARGLIST:
@@ -938,14 +1070,40 @@ evaluate_subexp_standard (expect_type, exp, pos, noside)
NULL, "structure pointer");
}
-
case STRUCTOP_MEMBER:
arg1 = evaluate_subexp_for_address (exp, pos, noside);
+ arg2 = evaluate_subexp (NULL_TYPE, exp, pos, noside);
+
+ /* With HP aCC, pointers to methods do not point to the function code */
+ if (hp_som_som_object_present &&
+ (TYPE_CODE (VALUE_TYPE (arg2)) == TYPE_CODE_PTR) &&
+ (TYPE_CODE (TYPE_TARGET_TYPE (VALUE_TYPE (arg2))) == TYPE_CODE_METHOD))
+ error ("Pointers to methods not supported with HP aCC"); /* 1997-08-19 */
+
+ mem_offset = value_as_long (arg2);
goto handle_pointer_to_member;
+
case STRUCTOP_MPTR:
arg1 = evaluate_subexp (NULL_TYPE, exp, pos, noside);
- handle_pointer_to_member:
arg2 = evaluate_subexp (NULL_TYPE, exp, pos, noside);
+
+ /* With HP aCC, pointers to methods do not point to the function code */
+ if (hp_som_som_object_present &&
+ (TYPE_CODE (VALUE_TYPE (arg2)) == TYPE_CODE_PTR) &&
+ (TYPE_CODE (TYPE_TARGET_TYPE (VALUE_TYPE (arg2))) == TYPE_CODE_METHOD))
+ error ("Pointers to methods not supported with HP aCC"); /* 1997-08-19 */
+
+ mem_offset = value_as_long (arg2);
+
+handle_pointer_to_member:
+ /* HP aCC generates offsets that have bit #29 set; turn it off to get
+ a real offset to the member. */
+ if (hp_som_som_object_present)
+ {
+ if (!mem_offset) /* no bias -> really null */
+ error ("Attempted dereference of null pointer-to-member");
+ mem_offset &= ~0x20000000;
+ }
if (noside == EVAL_SKIP)
goto nosideret;
type = check_typedef (VALUE_TYPE (arg2));
@@ -960,9 +1118,9 @@ evaluate_subexp_standard (expect_type, exp, pos, noside)
arg1 = value_cast (lookup_pointer_type (TYPE_DOMAIN_TYPE (type)),
arg1);
arg3 = value_from_longest (lookup_pointer_type (TYPE_TARGET_TYPE (type)),
- value_as_long (arg1) + value_as_long (arg2));
+ value_as_long (arg1) + mem_offset);
return value_ind (arg3);
- bad_pointer_to_member:
+bad_pointer_to_member:
error("non-pointer-to-member value used in pointer-to-member construct");
case BINOP_CONCAT:
@@ -971,17 +1129,38 @@ evaluate_subexp_standard (expect_type, exp, pos, noside)
if (noside == EVAL_SKIP)
goto nosideret;
if (binop_user_defined_p (op, arg1, arg2))
- return value_x_binop (arg1, arg2, op, OP_NULL);
+ return value_x_binop (arg1, arg2, op, OP_NULL, noside);
else
return value_concat (arg1, arg2);
case BINOP_ASSIGN:
arg1 = evaluate_subexp (NULL_TYPE, exp, pos, noside);
arg2 = evaluate_subexp (VALUE_TYPE (arg1), exp, pos, noside);
+
+ /* Do special stuff for HP aCC pointers to members */
+ if (hp_som_som_object_present)
+ {
+ /* 1997-08-19 Can't assign HP aCC pointers to methods. No details of
+ the implementation yet; but the pointer appears to point to a code
+ sequence (thunk) in memory -- in any case it is *not* the address
+ of the function as it would be in a naive implementation. */
+ if ((TYPE_CODE (VALUE_TYPE (arg1)) == TYPE_CODE_PTR) &&
+ (TYPE_CODE (TYPE_TARGET_TYPE (VALUE_TYPE (arg1))) == TYPE_CODE_METHOD))
+ error ("Assignment to pointers to methods not implemented with HP aCC");
+
+ /* HP aCC pointers to data members require a constant bias */
+ if ((TYPE_CODE (VALUE_TYPE (arg1)) == TYPE_CODE_PTR) &&
+ (TYPE_CODE (TYPE_TARGET_TYPE (VALUE_TYPE (arg1))) == TYPE_CODE_MEMBER))
+ {
+ unsigned int * ptr = (unsigned int *) VALUE_CONTENTS (arg2); /* forces evaluation */
+ *ptr |= 0x20000000; /* set 29th bit */
+ }
+ }
+
if (noside == EVAL_SKIP || noside == EVAL_AVOID_SIDE_EFFECTS)
return arg1;
if (binop_user_defined_p (op, arg1, arg2))
- return value_x_binop (arg1, arg2, op, OP_NULL);
+ return value_x_binop (arg1, arg2, op, OP_NULL, noside);
else
return value_assign (arg1, arg2);
@@ -993,7 +1172,7 @@ evaluate_subexp_standard (expect_type, exp, pos, noside)
return arg1;
op = exp->elts[pc + 1].opcode;
if (binop_user_defined_p (op, arg1, arg2))
- return value_x_binop (arg1, arg2, BINOP_ASSIGN_MODIFY, op);
+ return value_x_binop (arg1, arg2, BINOP_ASSIGN_MODIFY, op, noside);
else if (op == BINOP_ADD)
arg2 = value_add (arg1, arg2);
else if (op == BINOP_SUB)
@@ -1008,7 +1187,7 @@ evaluate_subexp_standard (expect_type, exp, pos, noside)
if (noside == EVAL_SKIP)
goto nosideret;
if (binop_user_defined_p (op, arg1, arg2))
- return value_x_binop (arg1, arg2, op, OP_NULL);
+ return value_x_binop (arg1, arg2, op, OP_NULL, noside);
else
return value_add (arg1, arg2);
@@ -1018,7 +1197,7 @@ evaluate_subexp_standard (expect_type, exp, pos, noside)
if (noside == EVAL_SKIP)
goto nosideret;
if (binop_user_defined_p (op, arg1, arg2))
- return value_x_binop (arg1, arg2, op, OP_NULL);
+ return value_x_binop (arg1, arg2, op, OP_NULL, noside);
else
return value_sub (arg1, arg2);
@@ -1036,7 +1215,7 @@ evaluate_subexp_standard (expect_type, exp, pos, noside)
if (noside == EVAL_SKIP)
goto nosideret;
if (binop_user_defined_p (op, arg1, arg2))
- return value_x_binop (arg1, arg2, op, OP_NULL);
+ return value_x_binop (arg1, arg2, op, OP_NULL, noside);
else
if (noside == EVAL_AVOID_SIDE_EFFECTS
&& (op == BINOP_DIV || op == BINOP_REM || op == BINOP_MOD))
@@ -1056,24 +1235,31 @@ evaluate_subexp_standard (expect_type, exp, pos, noside)
arg2 = evaluate_subexp_with_coercion (exp, pos, noside);
if (noside == EVAL_SKIP)
goto nosideret;
- if (noside == EVAL_AVOID_SIDE_EFFECTS)
- {
- /* If the user attempts to subscript something that has no target
- type (like a plain int variable for example), then report this
- as an error. */
-
- type = TYPE_TARGET_TYPE (check_typedef (VALUE_TYPE (arg1)));
- if (type)
- return value_zero (type, VALUE_LVAL (arg1));
- else
- error ("cannot subscript something of type `%s'",
- TYPE_NAME (VALUE_TYPE (arg1)));
- }
-
if (binop_user_defined_p (op, arg1, arg2))
- return value_x_binop (arg1, arg2, op, OP_NULL);
+ return value_x_binop (arg1, arg2, op, OP_NULL, noside);
else
- return value_subscript (arg1, arg2);
+ {
+ /* If the user attempts to subscript something that is not an
+ array or pointer type (like a plain int variable for example),
+ then report this as an error. */
+
+ COERCE_REF (arg1);
+ type = check_typedef (VALUE_TYPE (arg1));
+ if (TYPE_CODE (type) != TYPE_CODE_ARRAY
+ && TYPE_CODE (type) != TYPE_CODE_PTR)
+ {
+ if (TYPE_NAME (type))
+ error ("cannot subscript something of type `%s'",
+ TYPE_NAME (type));
+ else
+ error ("cannot subscript requested type");
+ }
+
+ if (noside == EVAL_AVOID_SIDE_EFFECTS)
+ return value_zero (TYPE_TARGET_TYPE (type), VALUE_LVAL (arg1));
+ else
+ return value_subscript (arg1, arg2);
+ }
case BINOP_IN:
arg1 = evaluate_subexp_with_coercion (exp, pos, noside);
@@ -1124,7 +1310,7 @@ evaluate_subexp_standard (expect_type, exp, pos, noside)
if (binop_user_defined_p (op, arg1, arg2))
{
- arg1 = value_x_binop (arg1, arg2, op, OP_NULL);
+ arg1 = value_x_binop (arg1, arg2, op, OP_NULL, noside);
}
else
{
@@ -1228,7 +1414,7 @@ evaluate_subexp_standard (expect_type, exp, pos, noside)
if (binop_user_defined_p (op, arg1, arg2))
{
arg2 = evaluate_subexp (NULL_TYPE, exp, pos, noside);
- return value_x_binop (arg1, arg2, op, OP_NULL);
+ return value_x_binop (arg1, arg2, op, OP_NULL, noside);
}
else
{
@@ -1254,7 +1440,7 @@ evaluate_subexp_standard (expect_type, exp, pos, noside)
if (binop_user_defined_p (op, arg1, arg2))
{
arg2 = evaluate_subexp (NULL_TYPE, exp, pos, noside);
- return value_x_binop (arg1, arg2, op, OP_NULL);
+ return value_x_binop (arg1, arg2, op, OP_NULL, noside);
}
else
{
@@ -1272,7 +1458,7 @@ evaluate_subexp_standard (expect_type, exp, pos, noside)
goto nosideret;
if (binop_user_defined_p (op, arg1, arg2))
{
- return value_x_binop (arg1, arg2, op, OP_NULL);
+ return value_x_binop (arg1, arg2, op, OP_NULL, noside);
}
else
{
@@ -1287,7 +1473,7 @@ evaluate_subexp_standard (expect_type, exp, pos, noside)
goto nosideret;
if (binop_user_defined_p (op, arg1, arg2))
{
- return value_x_binop (arg1, arg2, op, OP_NULL);
+ return value_x_binop (arg1, arg2, op, OP_NULL, noside);
}
else
{
@@ -1302,7 +1488,7 @@ evaluate_subexp_standard (expect_type, exp, pos, noside)
goto nosideret;
if (binop_user_defined_p (op, arg1, arg2))
{
- return value_x_binop (arg1, arg2, op, OP_NULL);
+ return value_x_binop (arg1, arg2, op, OP_NULL, noside);
}
else
{
@@ -1317,7 +1503,7 @@ evaluate_subexp_standard (expect_type, exp, pos, noside)
goto nosideret;
if (binop_user_defined_p (op, arg1, arg2))
{
- return value_x_binop (arg1, arg2, op, OP_NULL);
+ return value_x_binop (arg1, arg2, op, OP_NULL, noside);
}
else
{
@@ -1332,7 +1518,7 @@ evaluate_subexp_standard (expect_type, exp, pos, noside)
goto nosideret;
if (binop_user_defined_p (op, arg1, arg2))
{
- return value_x_binop (arg1, arg2, op, OP_NULL);
+ return value_x_binop (arg1, arg2, op, OP_NULL, noside);
}
else
{
@@ -1347,7 +1533,7 @@ evaluate_subexp_standard (expect_type, exp, pos, noside)
goto nosideret;
if (binop_user_defined_p (op, arg1, arg2))
{
- return value_x_binop (arg1, arg2, op, OP_NULL);
+ return value_x_binop (arg1, arg2, op, OP_NULL, noside);
}
else
{
@@ -1360,7 +1546,8 @@ evaluate_subexp_standard (expect_type, exp, pos, noside)
arg2 = evaluate_subexp (NULL_TYPE, exp, pos, noside);
if (noside == EVAL_SKIP)
goto nosideret;
- if (TYPE_CODE (VALUE_TYPE (arg2)) != TYPE_CODE_INT)
+ type = check_typedef (VALUE_TYPE (arg2));
+ if (TYPE_CODE (type) != TYPE_CODE_INT)
error ("Non-integral right operand for \"@\" operator.");
if (noside == EVAL_AVOID_SIDE_EFFECTS)
{
@@ -1379,7 +1566,7 @@ evaluate_subexp_standard (expect_type, exp, pos, noside)
if (noside == EVAL_SKIP)
goto nosideret;
if (unop_user_defined_p (op, arg1))
- return value_x_unop (arg1, op);
+ return value_x_unop (arg1, op, noside);
else
return value_neg (arg1);
@@ -1391,7 +1578,7 @@ evaluate_subexp_standard (expect_type, exp, pos, noside)
if (noside == EVAL_SKIP)
goto nosideret;
if (unop_user_defined_p (UNOP_COMPLEMENT, arg1))
- return value_x_unop (arg1, UNOP_COMPLEMENT);
+ return value_x_unop (arg1, UNOP_COMPLEMENT, noside);
else
return value_complement (arg1);
@@ -1400,18 +1587,24 @@ evaluate_subexp_standard (expect_type, exp, pos, noside)
if (noside == EVAL_SKIP)
goto nosideret;
if (unop_user_defined_p (op, arg1))
- return value_x_unop (arg1, op);
+ return value_x_unop (arg1, op, noside);
else
- return value_from_longest (builtin_type_int,
+ return value_from_longest (LA_BOOL_TYPE,
(LONGEST) value_logical_not (arg1));
case UNOP_IND:
if (expect_type && TYPE_CODE (expect_type) == TYPE_CODE_PTR)
expect_type = TYPE_TARGET_TYPE (check_typedef (expect_type));
arg1 = evaluate_subexp (expect_type, exp, pos, noside);
+ if ((TYPE_TARGET_TYPE (VALUE_TYPE (arg1))) &&
+ ((TYPE_CODE (TYPE_TARGET_TYPE (VALUE_TYPE (arg1))) == TYPE_CODE_METHOD) ||
+ (TYPE_CODE (TYPE_TARGET_TYPE (VALUE_TYPE (arg1))) == TYPE_CODE_MEMBER)))
+ error ("Attempt to dereference pointer to member without an object");
if (noside == EVAL_SKIP)
goto nosideret;
- if (noside == EVAL_AVOID_SIDE_EFFECTS)
+ if (unop_user_defined_p (op, arg1))
+ return value_x_unop (arg1, op, noside);
+ else if (noside == EVAL_AVOID_SIDE_EFFECTS)
{
type = check_typedef (VALUE_TYPE (arg1));
if (TYPE_CODE (type) == TYPE_CODE_PTR
@@ -1445,9 +1638,20 @@ evaluate_subexp_standard (expect_type, exp, pos, noside)
evaluate_subexp (expect_type, exp, pos, EVAL_SKIP);
goto nosideret;
}
-
- return evaluate_subexp_for_address (exp, pos, noside);
-
+ else
+ {
+ value_ptr retvalp = evaluate_subexp_for_address (exp, pos, noside);
+ /* If HP aCC object, use bias for pointers to members */
+ if (hp_som_som_object_present &&
+ (TYPE_CODE (VALUE_TYPE (retvalp)) == TYPE_CODE_PTR) &&
+ (TYPE_CODE (TYPE_TARGET_TYPE (VALUE_TYPE (retvalp))) == TYPE_CODE_MEMBER))
+ {
+ unsigned int * ptr = (unsigned int *) VALUE_CONTENTS (retvalp); /* forces evaluation */
+ *ptr |= 0x20000000; /* set 29th bit */
+ }
+ return retvalp;
+ }
+
case UNOP_SIZEOF:
if (noside == EVAL_SKIP)
{
@@ -1475,7 +1679,8 @@ evaluate_subexp_standard (expect_type, exp, pos, noside)
return value_zero (exp->elts[pc + 1].type, lval_memory);
else
return value_at_lazy (exp->elts[pc + 1].type,
- value_as_pointer (arg1));
+ value_as_pointer (arg1),
+ NULL);
case UNOP_PREINCREMENT:
arg1 = evaluate_subexp (expect_type, exp, pos, noside);
@@ -1483,7 +1688,7 @@ evaluate_subexp_standard (expect_type, exp, pos, noside)
return arg1;
else if (unop_user_defined_p (op, arg1))
{
- return value_x_unop (arg1, op);
+ return value_x_unop (arg1, op, noside);
}
else
{
@@ -1498,7 +1703,7 @@ evaluate_subexp_standard (expect_type, exp, pos, noside)
return arg1;
else if (unop_user_defined_p (op, arg1))
{
- return value_x_unop (arg1, op);
+ return value_x_unop (arg1, op, noside);
}
else
{
@@ -1513,7 +1718,7 @@ evaluate_subexp_standard (expect_type, exp, pos, noside)
return arg1;
else if (unop_user_defined_p (op, arg1))
{
- return value_x_unop (arg1, op);
+ return value_x_unop (arg1, op, noside);
}
else
{
@@ -1529,7 +1734,7 @@ evaluate_subexp_standard (expect_type, exp, pos, noside)
return arg1;
else if (unop_user_defined_p (op, arg1))
{
- return value_x_unop (arg1, op);
+ return value_x_unop (arg1, op, noside);
}
else
{
@@ -1716,6 +1921,10 @@ evaluate_subexp_for_sizeof (exp, pos)
(*pos)++;
val = evaluate_subexp (NULL_TYPE, exp, pos, EVAL_AVOID_SIDE_EFFECTS);
type = check_typedef (VALUE_TYPE (val));
+ if (TYPE_CODE (type) != TYPE_CODE_PTR
+ && TYPE_CODE (type) != TYPE_CODE_REF
+ && TYPE_CODE (type) != TYPE_CODE_ARRAY)
+ error ("Attempt to take contents of a non-pointer value.");
type = check_typedef (TYPE_TARGET_TYPE (type));
return value_from_longest (builtin_type_int, (LONGEST)
TYPE_LENGTH (type));
OpenPOWER on IntegriCloud