Commit d259b234 by Jakub Jelinek Committed by Jakub Jelinek

re PR sanitizer/70135 (-fsanitize=undefined causes static_assert to fail)

	PR c++/70135
	* constexpr.c (cxx_eval_loop_expr): Forget saved values of SAVE_EXPRs
	even after the last iteration of the loop.

	* g++.dg/cpp1y/constexpr-loop4.C: New test.
	* g++.dg/ubsan/pr70135.C: New test.

From-SVN: r234064
parent 56aae4b7
2016-03-08 Jakub Jelinek <jakub@redhat.com> 2016-03-08 Jakub Jelinek <jakub@redhat.com>
PR c++/70135
* constexpr.c (cxx_eval_loop_expr): Forget saved values of SAVE_EXPRs
even after the last iteration of the loop.
* decl.c (duplicate_decls): Fix spelling - becuase -> because. * decl.c (duplicate_decls): Fix spelling - becuase -> because.
2016-03-07 Patrick Palka <ppalka@gcc.gnu.org> 2016-03-07 Patrick Palka <ppalka@gcc.gnu.org>
......
...@@ -3165,21 +3165,21 @@ cxx_eval_loop_expr (const constexpr_ctx *ctx, tree t, ...@@ -3165,21 +3165,21 @@ cxx_eval_loop_expr (const constexpr_ctx *ctx, tree t,
constexpr_ctx new_ctx = *ctx; constexpr_ctx new_ctx = *ctx;
tree body = TREE_OPERAND (t, 0); tree body = TREE_OPERAND (t, 0);
while (true) do
{ {
hash_set<tree> save_exprs; hash_set<tree> save_exprs;
new_ctx.save_exprs = &save_exprs; new_ctx.save_exprs = &save_exprs;
cxx_eval_statement_list (&new_ctx, body, cxx_eval_statement_list (&new_ctx, body,
non_constant_p, overflow_p, jump_target); non_constant_p, overflow_p, jump_target);
if (returns (jump_target) || breaks (jump_target) || *non_constant_p)
break;
/* Forget saved values of SAVE_EXPRs. */ /* Forget saved values of SAVE_EXPRs. */
for (hash_set<tree>::iterator iter = save_exprs.begin(); for (hash_set<tree>::iterator iter = save_exprs.begin();
iter != save_exprs.end(); ++iter) iter != save_exprs.end(); ++iter)
new_ctx.values->remove (*iter); new_ctx.values->remove (*iter);
} }
while (!returns (jump_target) && !breaks (jump_target) && !*non_constant_p);
if (breaks (jump_target)) if (breaks (jump_target))
*jump_target = NULL_TREE; *jump_target = NULL_TREE;
......
2016-03-08 Jakub Jelinek <jakub@redhat.com> 2016-03-08 Jakub Jelinek <jakub@redhat.com>
PR c++/70135
* g++.dg/cpp1y/constexpr-loop4.C: New test.
* g++.dg/ubsan/pr70135.C: New test.
PR target/70110 PR target/70110
* gcc.dg/pr70110.c: New test. * gcc.dg/pr70110.c: New test.
......
// { dg-do compile { target c++14 } }
struct A
{
int i;
};
constexpr bool f()
{
A ar[5] = { 6, 7, 8, 9, 10 };
A *ap = ar;
int i = 0, j = 0;
for (j = 0; j < 2; j++)
{
do
*ap++ = A{i};
while (++i < j * 2 + 2);
}
return (ar[0].i == 0
&& ar[1].i == 1
&& ar[2].i == 2
&& ar[3].i == 3
&& ar[4].i == 10);
}
#define SA(X) static_assert((X),#X)
SA(f());
// PR c++/70135
// { dg-do run }
// { dg-options "-fsanitize=bounds -std=c++14" }
template <bool... b>
struct S {
static constexpr bool c[] {b...};
static constexpr auto foo ()
{
unsigned long n = 0;
for (unsigned long i = 0; i < sizeof (c); i++)
if (!c[i])
++n;
return n;
}
static constexpr auto n = foo () + 1;
static constexpr auto bar ()
{
int h = 0;
for (int g = 0, i = 0; g < n; ++g)
{
while (i < sizeof...(b) && c[i++])
++h;
h += 64;
}
return h;
}
};
int
main ()
{
S <true, false, false, true, true, true, false, true> s;
constexpr auto c = s.bar ();
static_assert (s.bar () == 4 * 64 + 5);
}
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment