aboutsummaryrefslogtreecommitdiff
path: root/gcc/cp/semantics.c
diff options
context:
space:
mode:
Diffstat (limited to 'gcc/cp/semantics.c')
-rw-r--r--gcc/cp/semantics.c56
1 files changed, 43 insertions, 13 deletions
diff --git a/gcc/cp/semantics.c b/gcc/cp/semantics.c
index 1aa5a8b8b..717492709 100644
--- a/gcc/cp/semantics.c
+++ b/gcc/cp/semantics.c
@@ -3,8 +3,7 @@
building RTL. These routines are used both during actual parsing
and during the instantiation of template functions.
- Copyright (C) 1998, 1999, 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007,
- 2008, 2009, 2010, 2011, 2012 Free Software Foundation, Inc.
+ Copyright (C) 1998-2012 Free Software Foundation, Inc.
Written by Mark Mitchell (mmitchell@usa.net) based on code found
formerly in parse.y and pt.c.
@@ -2170,8 +2169,25 @@ finish_call_expr (tree fn, VEC(tree,gc) **args, bool disallow_virtual,
result = resolve_overloaded_builtin (input_location, fn, *args);
if (!result)
- /* A call to a namespace-scope function. */
- result = build_new_function_call (fn, args, koenig_p, complain);
+ {
+ if (warn_sizeof_pointer_memaccess
+ && !VEC_empty(tree, *args)
+ && TREE_CODE (VEC_last(tree, *args)) == SIZEOF_EXPR
+ && !processing_template_decl)
+ {
+ tree sizeof_arg = VEC_last(tree, *args);
+ if (SIZEOF_EXPR_TYPE_P (sizeof_arg))
+ sizeof_arg = TREE_TYPE (TREE_OPERAND (sizeof_arg, 0));
+ else
+ sizeof_arg = TREE_OPERAND (sizeof_arg, 0);
+ sizeof_pointer_memaccess_warning
+ (EXPR_LOCATION (VEC_last(tree, *args)), fn, *args,
+ sizeof_arg, same_type_ignoring_top_level_qualifiers_p);
+ }
+
+ /* A call to a namespace-scope function. */
+ result = build_new_function_call (fn, args, koenig_p, complain);
+ }
}
else if (TREE_CODE (fn) == PSEUDO_DTOR_EXPR)
{
@@ -7723,6 +7739,21 @@ cxx_eval_constant_expression (const constexpr_call *call, tree t,
non_constant_p);
break;
+ case SIZEOF_EXPR:
+ if (SIZEOF_EXPR_TYPE_P (t))
+ r = cxx_sizeof_or_alignof_type (TREE_TYPE (TREE_OPERAND (t, 0)),
+ SIZEOF_EXPR, false);
+ else if (TYPE_P (TREE_OPERAND (t, 0)))
+ r = cxx_sizeof_or_alignof_type (TREE_OPERAND (t, 0), SIZEOF_EXPR,
+ false);
+ else
+ r = cxx_sizeof_or_alignof_expr (TREE_OPERAND (t, 0), SIZEOF_EXPR,
+ false);
+ if (r == error_mark_node)
+ r = size_one_node;
+ VERIFY_CONSTANT (r);
+ break;
+
case COMPOUND_EXPR:
{
/* check_return_expr sometimes wraps a TARGET_EXPR in a
@@ -7740,6 +7771,7 @@ cxx_eval_constant_expression (const constexpr_call *call, tree t,
/* Check that the LHS is constant and then discard it. */
cxx_eval_constant_expression (call, op0, allow_non_constant,
false, non_constant_p);
+ op1 = TREE_OPERAND (t, 1);
r = cxx_eval_constant_expression (call, op1, allow_non_constant,
addr, non_constant_p);
}
@@ -8106,12 +8138,6 @@ potential_constant_expression_1 (tree t, bool want_rval, tsubst_flags_t flags)
int i;
tree tmp;
- /* C++98 has different rules for the form of a constant expression that
- are enforced in the parser, so we can assume that anything that gets
- this far is suitable. */
- if (cxx_dialect < cxx0x)
- return true;
-
if (t == error_mark_node)
return false;
if (t == NULL_TREE)
@@ -8632,6 +8658,9 @@ potential_constant_expression_1 (tree t, bool want_rval, tsubst_flags_t flags)
return false;
default:
+ if (objc_is_property_ref (t))
+ return false;
+
sorry ("unexpected AST of kind %s", tree_code_name[TREE_CODE (t)]);
gcc_unreachable();
return false;
@@ -8975,14 +9004,15 @@ is_capture_proxy (tree decl)
bool
is_normal_capture_proxy (tree decl)
{
- tree val;
-
if (!is_capture_proxy (decl))
/* It's not a capture proxy. */
return false;
/* It is a capture proxy, is it a normal capture? */
- val = DECL_VALUE_EXPR (decl);
+ tree val = DECL_VALUE_EXPR (decl);
+ if (val == error_mark_node)
+ return true;
+
gcc_assert (TREE_CODE (val) == COMPONENT_REF);
val = TREE_OPERAND (val, 1);
return DECL_NORMAL_CAPTURE_P (val);