[c++-concepts] code review

Andrew Sutton andrew.n.sutton@gmail.com
Tue Jun 18 16:28:00 GMT 2013


I've finished revising based on comments. All of the changes seemed
pretty smooth, except for the use of fold_non_dependent_expr.

There was a bug in instantiation_dependent_expr_r that would cause
trait expressions like __is_class(int) to be marked as type dependent.
It was always testing the 2nd operand, even for unary traits
(NULL_TREE turns out to be type dependent). I added is_unary_trait,
is_binary_trait to help test around those conditions.

I ended up removing <cstdlib>.

Updated Changelog.

2013-06-18  Andrew Sutton  <andrew.n.sutton@gmail.com>
        * gcc/cp/class.c (are_constrained_member_overloads): New.
        (add_method): Allow overloading of constrained member functions.
        * gcc/cp/call.c (rejection_reason_code): New rr_constraint_failure.
        (template_constraint_failure): New.
        (add_function_candidate): Check for viability as a precondition to use.
        (add_template_candidate_real): Integrate constraint diagnostics.
        Provide constraint info for new template instantiations.
        (print_z_candidate): Emit diagnostics for constraint failures.
        (template_decl_for_candidate): New.
        (joust): Allow non-member templates of class templates to be evaluated
        in more_specialized_fn if they are constrained.
        * gcc/cp/ptree.c (cxx_print_xnode): Dump constraint info.
        * gcc/cp/semantics.c (finish_template_template_parm): Build template
        info for template template parameters.
        (is_unary_trait): New.
        (is_binary_trait): New.
        (finish_trait_expr): Check for binary traits using new function.
        * gcc/cp/constraint.cc (join_requirements): New
        (conjoin_requirements): Join expressions correctly. Fixed docs.
        (disjoin_requirements): Removed.
        (is_constriant): Removed.
        (resolve_constraint_check): New. Replaces previous get_constraint
        check and related functions.
        (get_constraints): New, along with helper functions.
        (suppress_template_processing): New.
        (check_template_constraints): New, along with helper functions.
        (equivalent_constraints): New.
        (equivalently_constrained): New.
        (more_constraints): New.
        (more_constrianed): New.
        (diagnose_constraint_failure): New.
        * gcc/cp/decl.c (decls_match): Check for constraint equivalence if
        the types are the same.
        (check_concept_refinement): New.
        (are_constrained_overloads): New.
        (duplicate_decls): Handle constraints for ambigous declarations. Check
        and diagnose concept refinement.
        (check_concept_fn): Don't fail completely just because the concept
        isn't defined correctly. Allow analysis to continue as if declared
        constexpr. Concepts must return bool.
        * gcc/cp/tree.c (bind_template_template_parm): Provide empty
        constraints for bound template template parameters.
        * gcc/cp/logic.cc: Rewrite of proof state and related structures and
        decomposition logic. Removed right-decomposition logic, but retained
        right-logical rules.
        (match_terms): Renamed from entails.
        (subsumes_prop): Cleanup, added specific handlers for and/or cases.
        (subsumes_constraints): Update from interface change.
        * gcc/cp/cp-tree.h (check_constraint_info): Renamed and applied
        interface change.
        (check_template_info): Renamed and applied interface change.
        (cp_unevaluated): New
        (local_specialization_stack): New.
        (coerce_template_parms): New.
        (is_unary_trait): New.
        (is_binary_trait): New.
        (get_constraints): New.
        (check_constraints): New.
        (check_template_constraints): New.
        (subst_template_constraints): New.
        (equivalent_constraints): New.
        (equivalently_constrained): New.
        (more_constraints): New.
        (more_constrained): New.
        (diagnose_constraints_failure): New.
        * gcc/cp/cxx-pretty-print.c (pp_cxx_template_declaration): Print the
        template requirements.
        * gcc/cp/pt.c (local_specialization_stack): New.
        (build_template_info): Refactor into 3-argument version and
        incorporate template requirements.
        (check_explicit_specialization): Instantiate requirements for
        template info.
        (push_template_decl_real): Include constraints in template info.
        (redeclare_class_template): Diagnose redeclaration with different
        constraints.
        (is_compatible_template_arg): New.
        (convert_template_argument): Check constraints on template template
        arguments and diagnose errors.
        (lookup_template_class_1): Check constraints on alias templates.
        Keep constraints with instantiated types.
        (instantiate_class_template_1): Check constraints on class templates.
        (tsubst_decl): Instantiate and keep constraints with template info.
        Also, allow dependent pack arguments to produce neww parameter
        packs when instantiated.
        (coerce_template_parms): New overload.
        (tsubst_copy): Handle REAL_TYPE and BOOLEAN_TYPE.
        (tsubst_copy_and_build): PARM_DECLs can be instantiated as pack
        expansions (used with requires expression).
        (fn_type_unification): Check constraints for function templates.
        (more_specialized_fn): Determine which candidate is more constrained.
        (substitute_template_parameters): Removed.
        (tsubst_constraint): New.
        (substitute_requirements): New.
        * gcc/cp/parser.c: (cp_parser_optional) Removed along with helper
        functions, etc.
        (cp_unevaluated): New.
        (cp_parser_type_parameter): Check for requires kw explicitly, and
        save/clear template requirements before parsing the requires clause.
        (cp_parser_requires_clause): Removed.
        (cp_parser_template_declaration_after_exp): Check for requires kw
        explicitly.
        * gcc/system.h (cstdlib): Removed include.
        * gcc/c-family/c-common.h (D_CXX_CONCEPTS): New flag for disabling
        concept keywords.
        * gcc/c-family/c.opt (flag_concepts): Remove redundant declaration.
        * gcc/c-family/c-common.c (c_common_r): Concept-specific keywords
        are only enabled when concepts are enabled.

On Mon, Jun 17, 2013 at 2:20 PM, Jason Merrill <jason@redhat.com> wrote:
> On 06/17/2013 02:10 PM, Andrew Sutton wrote:
>>>
>>> You mean you don't need <algorithm> anymore in logic.cc?  I think we want
>>> the <cstdlib> include in general if we're going to support people using
>>> the
>>> C++ standard library.
>>
>>
>> I don't. Those decisions are above my pay grade, so I'm doing my best
>> not to make them.
>
>
> If you don't need the change for concepts any more, feel free to drop it.
>
>
>>> Can friend temploids be constrained?
>>
>>
>> I have not thought deeply about constrained friend declarations. What
>> would a friend temploid look like?
>
>
> I was thinking something like
>
> template <class T> struct A {
>   T t;
>  requires Addable<T>()
>   friend A operator+(const A& a1, const A& a2)
>   { return A(a1.t + a2.t); }
>
> };
>
>>> I'm not clear on the issue.  Perhaps leaving processing_template_decl
>>> alone
>>> and using fold_non_dependent_expr would accomplish what you want?
>>
>>
>> I don't think that will work. The problem comes from the instantiation
>> of traits (and some other expressions) during constraint checking.
>> When processing_template_decl is non-zero, finish_trait_expr will
>> create TRAIT_EXPR nodes, which aren't handled by the constexpr
>> evaluation engine.
>
>
> Sure, but fold_non_dependent_expr should turn the TRAIT_EXPR into a more
> useful form.
>
>
>>> Can explicit specializations have constraints, to indicate which template
>>> they are specializing?
>>
>>
>> Good question. I don't think so. I believe that it would be a
>> specialization of the most specialized function template whose
>> constraints were satisfied. So:
>
>
> Makes sense.
>
>
>>> Passing 'true' for require_all_args means no deduction will be done;
>>> rather,
>>> all arguments must either be specified or have default arguments.
>>
>>
>> I see. It seems like I should be passing false here, since I want to
>> ensure that the resulting argument list can be used to instantiate the
>> template.
>
>
> I think true is what you want, since there are no function arguments to do
> argument deduction from.  Passing true for require_all_args guarantees that
> the result can be used to instantiate the template; passing false can return
> an incomplete set of arguments that will be filled in later by
> fn_type_unification.
>
> Jason
>



-- 
Andrew Sutton
andrew.n.sutton@gmail.com
-------------- next part --------------
A non-text attachment was scrubbed...
Name: reqs-3.patch
Type: application/octet-stream
Size: 77099 bytes
Desc: not available
URL: <http://gcc.gnu.org/pipermail/gcc-patches/attachments/20130618/06340319/attachment.obj>


More information about the Gcc-patches mailing list