On Thursday, April 28, 2016 at 10:41:21 AM UTC+10, Ehsan Akhgari wrote:
> On 2016-04-28 8:00 AM, Gerald Squelart wrote:
> > On Thursday, April 28, 2016 at 9:35:56 AM UTC+10, Kyle Huey wrote:
> >> Can we catch this pattern with a compiler somehow?
> >>
> >> Foo foo;
> >> foo.x = thing;
> >> DoBar(mozilla::Move(foo));
> >> if (foo.x) { /* do stuff */ }
> 
> I think so.  We already have an analysis which would detect whether the
> return value of a function is used somewhere or not.  We should be able
> to reuse that to find the call to DoBar(), and then look for future
> occurrences of foo used as an rvalue in the rest of the function.  Once
> we detect a use of "foo" as an lvalue, further usages of it as an rvalue
> in the same function should be OK and not trigger the error.  File a bug?
> 
> > Definitely something that would be nice.
> > 
> > But if we have/implement such a catcher, I'd like to have an annotation to 
> > say "yep I really want to reuse this moved-from object".
> > Because sometimes the function will choose not to actually move from an 
> > rvalue-ref, or the object knows to revert to a fully-reusable state, etc.
> 
> What you're describing sounds like a violation of move semantics, right?
>  The first case should only happen if DoBar doesn't accept an rvalue
> reference, in which case the code above is definitely doing something
> that the author did not expect, given that they have used Move().  The
> latter case sounds completely broken, and if there is an actual good use
> case for it, the C++ move semantics sound like the wrong tool to achieve
> that goal to me.
> 
> If you feel like I'm missing something or you can make a strong argument
> on why breaking move semantics is OK in some cases, please let me know.  :-)
> 
> Cheers,
> Ehsan

std::move and mozilla:Move are just casts that make an l-value object *look* 
like an r-value, so that when the compiler considers which 'DoBar' to use, one 
that takes an r-value reference will be picked first.

"Move" is probably not the best name because it gives this impression that an 
actual move happens, but that's what we're stuck with in the standard.

I don't see a "violation of move semantics" in there, could you please 
elaborate on what exact move semantics are violated?
I'd say it's probably more a "perversion of the move spirit". :-)

In any case, a moved-from object *must* stay valid after that call, because at 
the minimum it will be destroyed at the end of its enclosing scope, by invoking 
its normal destructor, no magic or special path there.

Now what to do with a moved-from object, is I think more a philosophical 
question! Some argue that we should do nothing (except the inevitable implied 
destruction). Others think it should be fine to also allow re-assignment (i.e. 
reuse the variable for something completely different). And yet others would 
allow total reuse.

My position is that 'Move(x)' *usually* means we give the value away and don't 
want to use it again, and therefore a compiler warning/error would help catch 
unexpected reuses; but also that some situations call for reuse (e.g. the 
function doesn't always steal the object's contents, based on other factors) 
and a programmer in the know should be allowed to annotate this special case.
_______________________________________________
dev-platform mailing list
dev-platform@lists.mozilla.org
https://lists.mozilla.org/listinfo/dev-platform

Reply via email to