Ping.

On Wed, Feb 11, 2026 at 10:29:24AM -0500, Marek Polacek wrote:
> On Wed, Feb 11, 2026 at 05:02:40PM +0900, Jason Merrill wrote:
> > On 2/11/26 1:05 AM, Marek Polacek wrote:
> > > Bootstrapped/regtested on x86_64-pc-linux-gnu, ok for trunk?
> > > 
> > > -- >8 --
> > > In <https://gcc.gnu.org/pipermail/gcc-patches/2026-January/705175.html>
> > > (bottom of the message) we discussed not passing ctx to 
> > > finish_id_expression
> > > so that we can get rid of the _deferring_access_checks calls.  So the
> > > cp_parser_splice_expression changes are what we want.  In order to be
> > > able to do that, I had to adjust finish_id_expression_1 so that things
> > > like &[: ^^S::fn :] and &[: ^^S::mem :] keep working.
> > 
> > Would it make sense to call build_offset_ref in cp_parser_splice_expression?
> 
> I could do that, but then I'd also have to duplicate the calls to
> push/pop_deferring_access_checks, and add checks around build_offset_ref
> just like in the r16-7445 patch.  But then I think I wouldn't have
> to add the new splice_p parameter.  Thought maybe we want to signal to
> finish_class_member_access_expr that we're coming from a splice anyway.
> So I think the patch wouldn't be much simpler if I called b_o_r in _parser_.
> 
> > > gcc/cp/ChangeLog:
> > > 
> > >   * cp-tree.h (finish_id_expression): Adjust declaration.
> > >   * parser.cc (cp_parser_splice_expression): Don't defer access checking.
> > >   Don't pass context to finish_id_expression.  Call finish_id_expression
> > >   with splice_p = true.
> > >   (cp_parser_primary_expression): Adjust the call to finish_id_expression.
> > >   (cp_parser_lambda_introducer): Likewise.
> > >   (cp_parser_decltype_expr): Likewise.
> > >   (cp_finish_omp_declare_variant): Likewise.
> > >   * pt.cc (tsubst_expr): Likewise.
> > >   * semantics.cc (finish_id_expression_1): New splice_p parameter.
> > >   For FIELD_DECLs and functions, call build_offset_ref when taking
> > >   the address when the entity was designated by a splice-expression.
> > >   Use nullptr.  Allow a VAR_DECL in an assert.
> > >   (finish_id_expression): New splice_p parameter.  Use it.
> > >   (omp_reduction_lookup): Adjust the call to finish_id_expression.
> > > ---
> > >   gcc/cp/cp-tree.h    |  2 +-
> > >   gcc/cp/parser.cc    | 21 +++++++--------------
> > >   gcc/cp/pt.cc        |  1 +
> > >   gcc/cp/semantics.cc | 41 +++++++++++++++++++++++++++++------------
> > >   4 files changed, 38 insertions(+), 27 deletions(-)
> > > 
> > > diff --git a/gcc/cp/cp-tree.h b/gcc/cp/cp-tree.h
> > > index fcad67a662c..99f4c2fc2e4 100644
> > > --- a/gcc/cp/cp-tree.h
> > > +++ b/gcc/cp/cp-tree.h
> > > @@ -8443,7 +8443,7 @@ extern tree process_outer_var_ref           (tree, 
> > > tsubst_flags_t, bool force_use = false
> > >   extern cp_expr finish_id_expression             (tree, tree, tree,
> > >                                                    cp_id_kind *,
> > >                                                    bool, bool, bool *,
> > > -                                          bool, bool, bool, bool,
> > > +                                          bool, bool, bool, bool, bool,
> > >                                                    const char **,
> > >                                                    location_t);
> > >   extern tree finish_typeof                       (tree);
> > > diff --git a/gcc/cp/parser.cc b/gcc/cp/parser.cc
> > > index 8c46b260fff..a7ad4876ac3 100644
> > > --- a/gcc/cp/parser.cc
> > > +++ b/gcc/cp/parser.cc
> > > @@ -6395,18 +6395,8 @@ cp_parser_splice_expression (cp_parser *parser, 
> > > bool template_p,
> > >            a variable template.  For &[: ^^S::x :], we have to create an
> > >            OFFSET_REF.  For a VAR_DECL, we need the 
> > > convert_from_reference.  */
> > >         cp_unevaluated u;
> > > -      /* CWG 3109 adjusted [class.protected] to say that checking access 
> > > to
> > > -  protected non-static members is disabled for members designated by a
> > > -  splice-expression.  */
> > > -      push_deferring_access_checks (dk_no_check);
> > >         const char *error_msg;
> > > -      /* We don't have the parser scope here, so figure out the context. 
> > >  In
> > > -    struct S { static constexpr int i = 42; };
> > > -    constexpr auto r = ^^S::i;
> > > -    int i = [: r :];
> > > -  we need to pass down 'S'.  */
> > > -      tree ctx = DECL_P (t) ? DECL_CONTEXT (t) : NULL_TREE;
> > > -      t = finish_id_expression (t, t, ctx, idk,
> > > +      t = finish_id_expression (t, t, NULL_TREE, idk,
> > >                                   
> > > /*integral_constant_expression_p=*/false,
> > >                                   
> > > /*allow_non_integral_constant_expr_p=*/true,
> > >                                   
> > > &parser->non_integral_constant_expression_p,
> > > @@ -6414,11 +6404,11 @@ cp_parser_splice_expression (cp_parser *parser, 
> > > bool template_p,
> > >                                   /*done=*/true,
> > >                                   address_p,
> > >                                   template_arg_p,
> > > +                         /*splice_p=*/true,
> > >                                   &error_msg,
> > >                                   loc);
> > >         if (error_msg)
> > >           cp_parser_error (parser, error_msg);
> > > -      pop_deferring_access_checks ();
> > >       }
> > >     return t;
> > > @@ -7174,6 +7164,7 @@ cp_parser_primary_expression (cp_parser *parser,
> > >                    &parser->non_integral_constant_expression_p,
> > >                    template_p, done, address_p,
> > >                    template_arg_p,
> > > +          /*splice_p=*/false,
> > >                    &error_msg,
> > >                    id_expression.get_location ()));
> > >           if (error_msg)
> > > @@ -13177,6 +13168,7 @@ cp_parser_lambda_introducer (cp_parser* parser, 
> > > tree lambda_expr)
> > >                    /*done=*/true,
> > >                    /*address_p=*/false,
> > >                    /*template_arg_p=*/false,
> > > +          /*splice_p=*/false,
> > >                    &error_msg,
> > >                    capture_token->location);
> > > @@ -19299,6 +19291,7 @@ cp_parser_decltype_expr (cp_parser *parser,
> > >                      /*done=*/true,
> > >                      /*address_p=*/false,
> > >                      /*template_arg_p=*/false,
> > > +            /*splice_p=*/false,
> > >                      &error_msg,
> > >                      id_expr_start_token->location));
> > > @@ -53549,8 +53542,8 @@ cp_finish_omp_declare_variant (cp_parser *parser, 
> > > cp_token *pragma_tok,
> > >           = finish_id_expression (varid, variant, parser->scope,
> > >                                   &idk, false, true,
> > >                                   
> > > &parser->non_integral_constant_expression_p,
> > > -                         template_p, true, false, false, &error_msg,
> > > -                         varid.get_location ());
> > > +                         template_p, true, false, false, false,
> > > +                         &error_msg, varid.get_location ());
> > >         if (error_msg)
> > >           cp_parser_error (parser, error_msg);
> > >       }
> > > diff --git a/gcc/cp/pt.cc b/gcc/cp/pt.cc
> > > index 7c6577b48ef..c510733d41b 100644
> > > --- a/gcc/cp/pt.cc
> > > +++ b/gcc/cp/pt.cc
> > > @@ -21185,6 +21185,7 @@ tsubst_expr (tree t, tree args, tsubst_flags_t 
> > > complain, tree in_decl)
> > >                                        /*done=*/true,
> > >                                        /*address_p=*/false,
> > >                                        /*template_arg_p=*/false,
> > > +                              /*splice_p=*/false,
> > >                                        &error_msg,
> > >                                        input_location);
> > >           if (error_msg)
> > > diff --git a/gcc/cp/semantics.cc b/gcc/cp/semantics.cc
> > > index 236bc625c25..76b0ddb1b12 100644
> > > --- a/gcc/cp/semantics.cc
> > > +++ b/gcc/cp/semantics.cc
> > > @@ -4735,6 +4735,7 @@ process_outer_var_ref (tree decl, tsubst_flags_t 
> > > complain, bool odr_use)
> > >      TEMPLATE_P is true iff the qualified-id was of the form
> > >      "A::template B".  TEMPLATE_ARG_P is true iff this qualified name
> > >      appears as a template argument.
> > > +   SPLICE_P is true if ID_EXPRESSION was designated by a 
> > > splice-expression.
> > >      If an error occurs, and it is the kind of error that might cause
> > >      the parser to abort a tentative parse, *ERROR_MSG is filled in.  It
> > > @@ -4760,6 +4761,7 @@ finish_id_expression_1 (tree id_expression,
> > >                           bool done,
> > >                           bool address_p,
> > >                           bool template_arg_p,
> > > +                 bool splice_p,
> > >                           const char **error_msg,
> > >                           location_t location)
> > >   {
> > > @@ -5022,16 +5024,23 @@ finish_id_expression_1 (tree id_expression,
> > >                 && contract_class_ptr == current_class_ptr)
> > >               {
> > >                 error ("%qD 'this' required when accessing a member 
> > > within a "
> > > -           "constructor precondition or destructor postcondition "
> > > -           "contract check", decl);
> > > -               return error_mark_node;
> > > +              "constructor precondition or destructor postcondition "
> > > +              "contract check", decl);
> > > +       return error_mark_node;
> > >               }
> > >             /* Since SCOPE is NULL here, this is an unqualified name.
> > >                Access checking has been performed during name lookup
> > >                already.  Turn off checking to avoid duplicate errors.  */
> > >             push_deferring_access_checks (dk_no_check);
> > > -   decl = finish_non_static_data_member (decl, NULL_TREE,
> > > -                                         /*qualifying_scope=*/NULL_TREE);
> > > +
> > > +   if (splice_p && address_p)
> > > +     decl = build_offset_ref (DECL_CONTEXT (decl), decl,
> > > +                              /*address_p=*/true,
> > > +                              tf_warning_or_error);
> > > +   else
> > > +     decl
> > > +       = finish_non_static_data_member (decl, NULL_TREE,
> > > +                                        /*qualifying_scope=*/NULL_TREE);
> > >             pop_deferring_access_checks ();
> > >           }
> > >         else if (is_overloaded_fn (decl))
> > > @@ -5041,6 +5050,11 @@ finish_id_expression_1 (tree id_expression,
> > >                concerned with (all member fns or all non-members).  */
> > >             tree first_fn = get_first_fn (decl);
> > >             first_fn = STRIP_TEMPLATE (first_fn);
> > > +   tree ctx = DECL_CONTEXT (first_fn);
> > > +
> > > +   if (splice_p && address_p)
> > > +     return build_offset_ref (ctx, first_fn, /*address_p=*/true,
> > > +                              tf_warning_or_error);
> > >             if (!template_arg_p
> > >                 && (TREE_CODE (first_fn) == USING_DECL
> > > @@ -5053,14 +5067,15 @@ finish_id_expression_1 (tree id_expression,
> > >                     && contract_class_ptr == current_class_ptr)
> > >                   {
> > >                     error ("%qD 'this' required when accessing a member 
> > > within a "
> > > -               "constructor precondition or destructor postcondition "
> > > -               "contract check", decl);
> > > +                  "constructor precondition or destructor postcondition "
> > > +                  "contract check", decl);
> > >                     return error_mark_node;
> > >                   }
> > > -       decl = maybe_dummy_object (DECL_CONTEXT (first_fn), 0);
> > > +       decl = maybe_dummy_object (ctx, nullptr);
> > >                 return finish_class_member_access_expr (decl, 
> > > id_expression,
> > >                                                         
> > > /*template_p=*/false,
> > > -                                               tf_warning_or_error);
> > > +                                               tf_warning_or_error,
> > > +                                               splice_p);
> > >               }
> > >             decl = baselink_for_fns (decl);
> > > @@ -5080,7 +5095,8 @@ finish_id_expression_1 (tree id_expression,
> > >                          ??? Should this case make a clone instead, like
> > >                          handle_using_decl?  */
> > > -             gcc_assert (TREE_CODE (decl) == CONST_DECL);
> > > +             gcc_assert (TREE_CODE (decl) == CONST_DECL
> > > +                         || (splice_p && VAR_P (decl)));
> > >                     else
> > >                       perform_or_defer_access_check (TYPE_BINFO (path),
> > >                                                      decl, decl,
> > > @@ -5114,6 +5130,7 @@ finish_id_expression (tree id_expression,
> > >                         bool done,
> > >                         bool address_p,
> > >                         bool template_arg_p,
> > > +               bool splice_p,
> > >                         const char **error_msg,
> > >                         location_t location)
> > >   {
> > > @@ -5123,7 +5140,7 @@ finish_id_expression (tree id_expression,
> > >                                 allow_non_integral_constant_expression_p,
> > >                                 non_integral_constant_expression_p,
> > >                                 template_p, done, address_p, 
> > > template_arg_p,
> > > -                       error_msg, location);
> > > +                       splice_p, error_msg, location);
> > >     return result.maybe_add_location_wrapper ();
> > >   }
> > > @@ -6744,7 +6761,7 @@ omp_reduction_lookup (location_t loc, tree id, tree 
> > > type, tree *baselinkp,
> > >           decl = error_mark_node;
> > >         id = finish_id_expression (id, decl, NULL_TREE, &idk, false, true,
> > >                                    &nonint_cst_expression_p, false, true, 
> > > false,
> > > -                          false, &error_msg, loc);
> > > +                          false, false, &error_msg, loc);
> > >         if (idk == CP_ID_KIND_UNQUALIFIED
> > >             && identifier_p (id))
> > >           {
> > > 
> > > base-commit: 065a6ab3747fe9116643ac6754582bc195847bfc
> > 
> 
> Marek

Marek

Reply via email to