On 11/29/25 2:31 AM, Egas Ribeiro wrote:
On 2025-11-28 15:32, Patrick Palka wrote:
Hey Egas, thanks for the patch!

On Fri, 28 Nov 2025, Egas Ribeiro wrote:

Lambdas used as non-type template arguments to concepts are wrapped
in TARGET_EXPR nodes. After r16-5115 changed convert_template_argument
to call instantiate_non_dependent_expr_internal on non-dependent
expressions, these TARGET_EXPRs began hitting the default case in
tsubst_expr, causing an ICE. Add proper TARGET_EXPR handling.

TARGET_EXPR is deliberately not handled by the tsubst routines because
it is considered a non-templated tree (and the tsubst routines naturally
expect to see only templated trees).  TARGET_EXPR represents temporary
objects, but we want the templated representation of expressions to
mirror their syntactic, written form, not their underlying semantic
representation in terms of temporary objects etc.

The problem here seems to be that when parsing A<[]{}>, we haven't yet
seen the 'auto' that indicates an abbreviated function template, so we
haven't switched to being in a template context yet, and we therefore
represent the []{} template argument as a non-templated tree.  Once
we see the auto we switch to a template context but we still build up
the type-constraint using the non-templated []{} tree.  Later when
checking the type-constraint via tsubst, it sees this non-template []{}
tree, which contains a TARGET_EXPR, and we ICE.

We somehow need to switch to being in a template context _before_
parsing the A<[]{}> type-constraint so that it's represented as
a templated tree.  In order to do that I guess we need to do some
sort of lookahead of to detect an abbreviated funciton template (
indicated by an 'auto' function parameter), which admittedly seems
quite tricky :/

Once we enter cp_parser_placeholder_type_specifier with parser->auto_is_implicit_function_template_parm_p we know we're dealing with an abbreviated function template, no need to wait until we actually see the 'auto'.

In the meantime I think it'd be good to document in tsubst_expr that
TARGET_EXPR is deliberately not handled since it's not a valid templated
tree.

Indeed.  Perhaps with a separate gcc_unreachable case.

Wonder what Jason thinks
Thanks for the detailed explanation Patrick! That makes a lot of sense -
I hadn't considered that the parser hasn't switched to template context
yet when parsing A<[]{}>, though i did suspect TARGET_EXPR could be
wrong for this lambda case.

Implementing some form of lookahead sounds like the right approach, but
it does seem tricky to do correctly.
Happy to wait for Jason's input on whether to go with a temporary
workaround (with a comment explaining the underlying issue) or if there's
a better solution to apply here.

Thanks!
Egas


Reply via email to