From: Jason Merrill Date: Tue, 28 Apr 2015 14:43:59 +0000 (-0400) Subject: re PR c++/65656 (__builtin_constant_p should always be constexpr) X-Git-Url: https://git.libre-soc.org/?a=commitdiff_plain;h=5756d0f9319b7f40051d1d2554243a766589b0bf;p=gcc.git re PR c++/65656 (__builtin_constant_p should always be constexpr) PR c++/65656 * constexpr.c (cxx_eval_builtin_function_call): Fix __builtin_constant_p. From-SVN: r222531 --- diff --git a/gcc/cp/ChangeLog b/gcc/cp/ChangeLog index 73d55b9b52f..acf4d493254 100644 --- a/gcc/cp/ChangeLog +++ b/gcc/cp/ChangeLog @@ -1,5 +1,9 @@ 2015-04-28 Jason Merrill + PR c++/65656 + * constexpr.c (cxx_eval_builtin_function_call): Fix + __builtin_constant_p. + PR c++/50800 * tree.c (strip_typedefs): Add remove_attributes parm. (strip_typedefs_expr): Likewise. diff --git a/gcc/cp/constexpr.c b/gcc/cp/constexpr.c index 6465677a950..403c7cfb943 100644 --- a/gcc/cp/constexpr.c +++ b/gcc/cp/constexpr.c @@ -1014,7 +1014,7 @@ get_nth_callarg (tree t, int n) represented by _CST nodes. */ static tree -cxx_eval_builtin_function_call (const constexpr_ctx *ctx, tree t, +cxx_eval_builtin_function_call (const constexpr_ctx *ctx, tree t, tree fun, bool lval, bool *non_constant_p, bool *overflow_p) { @@ -1022,18 +1022,30 @@ cxx_eval_builtin_function_call (const constexpr_ctx *ctx, tree t, tree *args = (tree *) alloca (nargs * sizeof (tree)); tree new_call; int i; - for (i = 0; i < nargs; ++i) + + /* Don't fold __builtin_constant_p within a constexpr function. */ + if (DECL_FUNCTION_CODE (fun) == BUILT_IN_CONSTANT_P + && current_function_decl + && DECL_DECLARED_CONSTEXPR_P (current_function_decl)) { - args[i] = cxx_eval_constant_expression (ctx, CALL_EXPR_ARG (t, i), - lval, - non_constant_p, overflow_p); - if (ctx->quiet && *non_constant_p) - return t; + *non_constant_p = true; + return t; } - if (*non_constant_p) - return t; + + /* Be permissive for arguments to built-ins; __builtin_constant_p should + return constant false for a non-constant argument. */ + constexpr_ctx new_ctx = *ctx; + new_ctx.quiet = true; + bool dummy1 = false, dummy2 = false; + for (i = 0; i < nargs; ++i) + args[i] = cxx_eval_constant_expression (&new_ctx, CALL_EXPR_ARG (t, i), + lval, &dummy1, &dummy2); + + bool save_ffbcp = force_folding_builtin_constant_p; + force_folding_builtin_constant_p = true; new_call = fold_build_call_array_loc (EXPR_LOCATION (t), TREE_TYPE (t), CALL_EXPR_FN (t), nargs, args); + force_folding_builtin_constant_p = save_ffbcp; VERIFY_CONSTANT (new_call); return new_call; } @@ -1200,7 +1212,7 @@ cxx_eval_call_expression (const constexpr_ctx *ctx, tree t, return void_node; if (is_builtin_fn (fun)) - return cxx_eval_builtin_function_call (ctx, t, + return cxx_eval_builtin_function_call (ctx, t, fun, lval, non_constant_p, overflow_p); if (!DECL_DECLARED_CONSTEXPR_P (fun)) { diff --git a/gcc/testsuite/g++.dg/cpp0x/constexpr-builtin3.C b/gcc/testsuite/g++.dg/cpp0x/constexpr-builtin3.C new file mode 100644 index 00000000000..3582525c12d --- /dev/null +++ b/gcc/testsuite/g++.dg/cpp0x/constexpr-builtin3.C @@ -0,0 +1,6 @@ +// PR c++/65656 +// { dg-options "-std=c++11 -O" } + +int main(int argc, char *argv[]) { + constexpr bool x = __builtin_constant_p(argc); +}