On Wed, Oct 24, 2018 at 02:55:14PM -0400, Jason Merrill wrote:
> On 10/12/18 12:32 PM, Marek Polacek wrote:
> > + EXPLICIT_SPECIFIER is used in case the explicit-specifier, if any, has
> > + value-dependent expression. */
> > static void
> > cp_parser_decl_specifier_seq (cp_parser* parser,
> > cp_parser_flags flags,
> > cp_decl_specifier_seq *decl_specs,
> > - int* declares_class_or_enum)
> > + int* declares_class_or_enum,
> > + tree* explicit_specifier)
>
> Why not add the explicit-specifier to cp_decl_specifier_seq? They don't
> live very long, so making them bigger isn't a concern. Then other of the
> handling could move into grokdeclarator along with the other explicit
> handling.
Great -- that simplifies things.
> > @@ -12822,6 +12844,17 @@ tsubst_function_decl (tree t, tree args,
> > tsubst_flags_t complain,
> >if (!uses_template_parms (DECL_TI_ARGS (t)))
> > return t;
> > + /* Handle explicit(dependent-expr). */
> > + if (DECL_HAS_DEPENDENT_EXPLICIT_SPEC_P (t))
> > + {
> > + tree spec = lookup_explicit_specifier (t);
> > + spec = tsubst_copy_and_build (spec, args, complain, in_decl,
> > + /*function_p=*/false,
> > + /*i_c_e_p=*/true);
> > + spec = build_explicit_specifier (spec, complain);
> > + DECL_NONCONVERTING_P (t) = (spec == boolean_true_node);
> > + }
>
> This is setting DECL_NONCONVERTING_P on the template, rather than the
> instantiation r, which hasn't been created yet at this point; this handling
> needs to move further down in the function.
Hmm, interesting that that worked, too. Anyway, fixed. Thanks!
Bootstrapped/regtested on x86_64-linux, ok for trunk?
2018-10-29 Marek Polacek
Implement P0892R2, explicit(bool).
* c-cppbuiltin.c (c_cpp_builtins): Define __cpp_explicit_bool.
* call.c (add_template_candidate_real): Return if the declaration is
explicit and we're only looking for non-converting constructor.
* cp-tree.h (lang_decl_fn): Add has_dependent_explicit_spec_p bit.
(DECL_HAS_DEPENDENT_EXPLICIT_SPEC_P): New macro.
(cp_decl_specifier_seq): Add explicit_specifier field.
(build_explicit_specifier, store_explicit_specifier): Declare.
* decl.c (grokdeclarator): Call store_explicit_specifier.
(build_explicit_specifier): New function.
* parser.c (cp_parser_function_specifier_opt) :
Parse C++20 explicit(bool).
* pt.c (store_explicit_specifier, lookup_explicit_specifier): New.
(tsubst_function_decl): Handle explicit(dependent-expr).
* g++.dg/cpp2a/explicit1.C: New test.
* g++.dg/cpp2a/explicit10.C: New test.
* g++.dg/cpp2a/explicit11.C: New test.
* g++.dg/cpp2a/explicit12.C: New test.
* g++.dg/cpp2a/explicit13.C: New test.
* g++.dg/cpp2a/explicit2.C: New test.
* g++.dg/cpp2a/explicit3.C: New test.
* g++.dg/cpp2a/explicit4.C: New test.
* g++.dg/cpp2a/explicit5.C: New test.
* g++.dg/cpp2a/explicit6.C: New test.
* g++.dg/cpp2a/explicit7.C: New test.
* g++.dg/cpp2a/explicit8.C: New test.
* g++.dg/cpp2a/explicit9.C: New test.
* testsuite/20_util/any/cons/explicit.cc: Adjust dg-error.
* testsuite/20_util/pair/cons/explicit_construct.cc: Likewise.
* testsuite/20_util/tuple/cons/explicit_construct.cc: Likewise.
diff --git gcc/gcc/c-family/c-cppbuiltin.c gcc/gcc/c-family/c-cppbuiltin.c
index 96a6b4dfd2b..b085cf9201f 100644
--- gcc/gcc/c-family/c-cppbuiltin.c
+++ gcc/gcc/c-family/c-cppbuiltin.c
@@ -955,7 +955,7 @@ c_cpp_builtins (cpp_reader *pfile)
}
if (cxx_dialect > cxx14)
{
- /* Set feature test macros for C++1z. */
+ /* Set feature test macros for C++17. */
cpp_define (pfile, "__cpp_unicode_characters=201411");
cpp_define (pfile, "__cpp_static_assert=201411");
cpp_define (pfile, "__cpp_namespace_attributes=201411");
@@ -975,6 +975,11 @@ c_cpp_builtins (cpp_reader *pfile)
cpp_define (pfile, "__cpp_structured_bindings=201606");
cpp_define (pfile, "__cpp_variadic_using=201611");
}
+ if (cxx_dialect > cxx17)
+ {
+ /* Set feature test macros for C++2a. */
+ cpp_define (pfile, "__cpp_explicit_bool=201806");
+ }
if (flag_concepts)
cpp_define (pfile, "__cpp_concepts=201507");
if (flag_tm)
diff --git gcc/gcc/cp/call.c gcc/gcc/cp/call.c
index cd0c0f60ced..e3453aca96e 100644
--- gcc/gcc/cp/call.c
+++ gcc/gcc/cp/call.c
@@ -3251,6 +3251,12 @@ add_template_candidate_real (struct z_candidate
**candidates, tree tmpl,
goto fail;
}
+ /* Now the explicit specifier might have been deduced; check if this
+ declaration is explicit. If it is and we're