aboutsummaryrefslogtreecommitdiff
path: root/gcc/cp/constexpr.c
diff options
context:
space:
mode:
Diffstat (limited to 'gcc/cp/constexpr.c')
-rw-r--r--gcc/cp/constexpr.c17
1 files changed, 16 insertions, 1 deletions
diff --git a/gcc/cp/constexpr.c b/gcc/cp/constexpr.c
index bb723f4..482f8af 100644
--- a/gcc/cp/constexpr.c
+++ b/gcc/cp/constexpr.c
@@ -1983,6 +1983,10 @@ cxx_eval_array_reference (const constexpr_ctx *ctx, tree t,
else if (lval)
return build4 (ARRAY_REF, TREE_TYPE (t), ary, index, NULL, NULL);
elem_type = TREE_TYPE (TREE_TYPE (ary));
+ if (TREE_CODE (ary) == VIEW_CONVERT_EXPR
+ && VECTOR_TYPE_P (TREE_TYPE (TREE_OPERAND (ary, 0)))
+ && TREE_TYPE (t) == TREE_TYPE (TREE_TYPE (TREE_OPERAND (ary, 0))))
+ ary = TREE_OPERAND (ary, 0);
if (TREE_CODE (ary) == CONSTRUCTOR)
len = CONSTRUCTOR_NELTS (ary);
else if (TREE_CODE (ary) == STRING_CST)
@@ -1991,6 +1995,8 @@ cxx_eval_array_reference (const constexpr_ctx *ctx, tree t,
/ TYPE_PRECISION (char_type_node));
len = (unsigned) TREE_STRING_LENGTH (ary) / elem_nchars;
}
+ else if (TREE_CODE (ary) == VECTOR_CST)
+ len = VECTOR_CST_NELTS (ary);
else
{
/* We can't do anything with other tree codes, so use
@@ -2007,7 +2013,14 @@ cxx_eval_array_reference (const constexpr_ctx *ctx, tree t,
return t;
}
- tree nelts = array_type_nelts_top (TREE_TYPE (ary));
+ tree nelts;
+ if (TREE_CODE (TREE_TYPE (ary)) == ARRAY_TYPE)
+ nelts = array_type_nelts_top (TREE_TYPE (ary));
+ else if (VECTOR_TYPE_P (TREE_TYPE (ary)))
+ nelts = size_int (TYPE_VECTOR_SUBPARTS (TREE_TYPE (ary)));
+ else
+ gcc_unreachable ();
+
/* For VLAs, the number of elements won't be an integer constant. */
nelts = cxx_eval_constant_expression (ctx, nelts, false, non_constant_p,
overflow_p);
@@ -2053,6 +2066,8 @@ cxx_eval_array_reference (const constexpr_ctx *ctx, tree t,
if (TREE_CODE (ary) == CONSTRUCTOR)
return (*CONSTRUCTOR_ELTS (ary))[i].value;
+ else if (TREE_CODE (ary) == VECTOR_CST)
+ return VECTOR_CST_ELT (ary, i);
else if (elem_nchars == 1)
return build_int_cst (cv_unqualified (TREE_TYPE (TREE_TYPE (ary))),
TREE_STRING_POINTER (ary)[i]);