This is the mail archive of the gcc-patches@gcc.gnu.org mailing list for the GCC project.


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]
Other format: [Raw text]

Re: [PR c++/83160] local ref to capture


On Fri, Jan 12, 2018 at 2:11 PM, Nathan Sidwell <nathan@acm.org> wrote:
> Jason,
> this fixes 83160, where we complain about not having an lvalue in things
> like:
>
> void foo () {
>   const int a = 0;
>   [&a] () {
>     const int &b = a;  // here
>   };
> }
>
> The problem is that we in convert_like_real we have ref_bind->identity
> conversions, and the identity conversion calls 'mark_rvalue_use'.  For a
> regular rvalue use of a 'const int' VAR_DECL, we return the VAR_DECL -- not
> collapse it to the initialized value.  However, for captures, there is code
> to look through the capture when rvalue_p is true.  We end up looking
> through the lambda capture, through the captured 'a' and to its initializer.
> oops.
>
> Calling mark_lvalue_use instead is also wrong, because the identity conv may
> of course be being applied to an rvalue, and we end up giving an equally
> wrong error in the opposite case.  Dealing with ck_identity this way sees
> wrong -- context determines whether this is an rvalue or lvalue use.
>
> I think the solution is for the identity conv to know whether it's going to
> be the subject of a direct reference binding and call mark_lvalue_use in tha
> case.  There's 2 issues with that:
>
> 1) mark_lvalue_use isn't quite right because we want to specify
> reject_builtin to the inner mark_use call.  (I didn't try changing
> mark_lvalue_use to pass true, I suspected it'd break actual calls of
> builtins).  Fixed by making mark_use externally reachable, and passing in an
> appropriate 'rvalue_p' parm directly.  I think your recent patch to select
> between the two marking fns may be neater using this entry point?
>
> 2) I modify direct_reference_binding to look at the incoming conv, and if it
> is ck_identity set that conv's rvaluedness_matches_p flag.  Then deply that
> flag to determine the arg in #1.  'rvaluedness_matches_p' seemed the least
> worst existing flag to press into service here.

This makes sense to me.  But I think we'd want also that flag set on
the ck_identity inside the ck_base that direct_reference_binding
creates, so setting it first rather than in an else.

Jason


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]