Join GitHub today
GitHub is home to over 31 million developers working together to host and review code, manage projects, and build software together.
Sign upImplement by-value object safety #54183
Conversation
rust-highfive
assigned
eddyb
Sep 13, 2018
rust-highfive
added
the
S-waiting-on-review
label
Sep 13, 2018
qnighy
force-pushed the
qnighy:by-value-object-safety
branch
2 times, most recently
from
7a494a3
to
74e4171
Sep 17, 2018
This comment has been minimized.
This comment has been minimized.
|
Ping from triage @eddyb: This PR requires your review. |
eddyb
reviewed
Sep 26, 2018
| assert!(arg_ty.is_self()); | ||
| local_decls[rcvr_arg].ty = tcx.mk_mut_ptr(arg_ty); | ||
|
|
||
| Operand::Copy(rcvr_l.deref()) |
This comment has been minimized.
This comment has been minimized.
eddyb
Sep 26, 2018
•
Member
This doesn't seem right, should probably be Operand::Move. cc @nikomatsakis
This comment has been minimized.
This comment has been minimized.
eddyb
reviewed
Sep 26, 2018
|
|
||
| if instance.is_vtable_shim() { | ||
| buf.push("{{vtable-shim}}"); | ||
| } |
This comment has been minimized.
This comment has been minimized.
This comment has been minimized.
This comment has been minimized.
qnighy
Sep 26, 2018
Author
Contributor
It's unnecessary for symbol distinction. It's useful when reading the generated LLVM IR or assembly.
eddyb
reviewed
Sep 26, 2018
| @@ -219,6 +219,9 @@ fn get_symbol_hash<'a, 'tcx>( | |||
| .hash_stable(&mut hcx, &mut hasher); | |||
| (&tcx.crate_disambiguator(instantiating_crate)).hash_stable(&mut hcx, &mut hasher); | |||
| } | |||
|
|
|||
| let is_vtable_shim = instance.is_vtable_shim(); | |||
| is_vtable_shim.hash_stable(&mut hcx, &mut hasher); | |||
This comment has been minimized.
This comment has been minimized.
eddyb
Sep 26, 2018
•
Member
Shouldn't we be hashing something from the Instance anyway? I thought we already had overlaps in (DefId, Substs) between possible Instances, did I imagine that?
This comment has been minimized.
This comment has been minimized.
qnighy
Sep 26, 2018
Author
Contributor
My understanding is that, aside from VtableShim that I've just introduced, there are no overlaps in (DefId, Substs). Intrinsics just differs from Item in its ABI. FnPtrShim, Virtual, ClosureOnceShim, and CloneShim all refers to trait methods, and these instances do not have manual implementations. DropGlue refers to core::ptr::drop_in_palce, but for that function DropGlue is specifically generated, so it won't collide with Item.
With that said, hashing InstanceDef's discriminator seems good to me.
eddyb
reviewed
Sep 26, 2018
| @@ -98,7 +98,7 @@ pub fn get_vtable( | |||
| let methods = tcx.vtable_methods(trait_ref); | |||
| let methods = methods.iter().cloned().map(|opt_mth| { | |||
| opt_mth.map_or(nullptr, |(def_id, substs)| { | |||
| callee::resolve_and_get_fn(cx, def_id, substs) | |||
| callee::resolve_and_get_fn_for_vtable(cx, def_id, substs) | |||
This comment has been minimized.
This comment has been minimized.
eddyb
Sep 26, 2018
Member
You probably need to do something similar in miri, but it might be harder.
eddyb
reviewed
Sep 26, 2018
| @@ -456,3 +456,22 @@ pub fn ty_fn_sig<'a, 'tcx>(cx: &CodegenCx<'a, 'tcx>, | |||
| _ => bug!("unexpected type {:?} to ty_fn_sig", ty) | |||
| } | |||
| } | |||
|
|
|||
| pub fn ty_fn_sig_vtable<'a, 'tcx>( | |||
This comment has been minimized.
This comment has been minimized.
eddyb
Sep 26, 2018
Member
I would expect this to be on Instance itself. Same for ty_fn_sig above, I guess. Feel free to leave FIXME comments here instead.
This comment has been minimized.
This comment has been minimized.
qnighy
Sep 26, 2018
Author
Contributor
Should I introduce InstanceExt in codegen_llvm, or just move them into librustc?
This comment has been minimized.
This comment has been minimized.
arielb1
Oct 1, 2018
•
Contributor
This feels like it would fit in librustc as a function of instance. It would also allow us to get rid of the ugly is_vtable_shim boolean passed around.
This comment has been minimized.
This comment has been minimized.
qnighy
Oct 6, 2018
Author
Contributor
Moved ty_fn_sig(_vtable) under Instance as Instance::fn_sig. Now is_vtable_shim is seen in only a few places.
qnighy
force-pushed the
qnighy:by-value-object-safety
branch
from
74e4171
to
0d5e048
Sep 26, 2018
This comment has been minimized.
This comment has been minimized.
|
r? @michaelwoerister or @arielb1 on the instance/symbol changes. |
rust-highfive
assigned
michaelwoerister
and unassigned
eddyb
Sep 28, 2018
This comment has been minimized.
This comment has been minimized.
|
@eddyb The changes to the symbol names and hashes look good to me. |
arielb1
reviewed
Oct 1, 2018
| let sig = common::ty_fn_sig(cx, fn_type); | ||
| debug!("declare_rust_fn(name={:?}, fn_type={:?}, is_vtable_shim={:?})", | ||
| name, fn_type, is_vtable_shim); | ||
| let sig = common::ty_fn_sig_vtable(cx, fn_type, is_vtable_shim); |
This comment has been minimized.
This comment has been minimized.
This comment has been minimized.
This comment has been minimized.
qnighy
Oct 6, 2018
Author
Contributor
As a result of the ty_fn_sig refactoring, we now have only a reasonable amount of occurrences of is_vtable_shim.
arielb1
requested changes
Oct 1, 2018
| @@ -456,3 +456,22 @@ pub fn ty_fn_sig<'a, 'tcx>(cx: &CodegenCx<'a, 'tcx>, | |||
| _ => bug!("unexpected type {:?} to ty_fn_sig", ty) | |||
| } | |||
| } | |||
|
|
|||
| pub fn ty_fn_sig_vtable<'a, 'tcx>( | |||
This comment has been minimized.
This comment has been minimized.
arielb1
Oct 1, 2018
•
Contributor
This feels like it would fit in librustc as a function of instance. It would also allow us to get rid of the ugly is_vtable_shim boolean passed around.
This comment has been minimized.
This comment has been minimized.
|
r? @arielb1 |
rust-highfive
assigned
arielb1
and unassigned
michaelwoerister
Oct 4, 2018
This comment has been minimized.
This comment has been minimized.
|
|
qnighy
force-pushed the
qnighy:by-value-object-safety
branch
from
0d5e048
to
326e3c0
Oct 6, 2018
This comment has been minimized.
This comment has been minimized.
|
|
qnighy
force-pushed the
qnighy:by-value-object-safety
branch
from
326e3c0
to
cd844f5
Oct 12, 2018
This comment has been minimized.
This comment has been minimized.
|
|
qnighy
force-pushed the
qnighy:by-value-object-safety
branch
from
cd844f5
to
8e27255
Oct 15, 2018
This comment has been minimized.
This comment has been minimized.
|
Ping from triage @arielb1 / @rust-lang/compiler: This PR requires your review. |
oli-obk
requested changes
Oct 23, 2018
| @@ -0,0 +1,30 @@ | |||
| // Copyright 2018 The Rust Project Developers. See the COPYRIGHT | |||
This comment has been minimized.
This comment has been minimized.
This comment has been minimized.
This comment has been minimized.
| @@ -0,0 +1,65 @@ | |||
| // Copyright 2018 The Rust Project Developers. See the COPYRIGHT | |||
This comment has been minimized.
This comment has been minimized.
This comment has been minimized.
This comment has been minimized.
qnighy
Oct 24, 2018
Author
Contributor
Sure, removed these headers for all unsized-locals tests including those from #51131.
|
|
||
|
|
||
| fn main() { | ||
| let x = *(Box::new(A) as Box<dyn Foo>); |
This comment has been minimized.
This comment has been minimized.
oli-obk
Oct 23, 2018
Contributor
Are there preexisting tests for calling such a method directly on a Box<dyn Foo> without first dereferencing the box? If not, please add a ui test for that.
This comment has been minimized.
This comment has been minimized.
qnighy
Oct 24, 2018
Author
Contributor
I've not tested that, and it turned out to compile! I added this as a run-pass test (just below here).
This comment has been minimized.
This comment has been minimized.
oli-obk
Oct 24, 2018
Contributor
awesome!
The RFC isn't very clear on this. But I would see that as a natural consequence.
Can you add more tests (also failure tests ensuring that we can't use the box anymore after having called a method on it?)
This comment has been minimized.
This comment has been minimized.
This comment has been minimized.
This comment has been minimized.
qnighy
added some commits
Sep 11, 2018
qnighy
force-pushed the
qnighy:by-value-object-safety
branch
from
8e27255
to
1c48647
Oct 24, 2018
oli-obk
approved these changes
Oct 27, 2018
This comment has been minimized.
This comment has been minimized.
|
@bors r+ |
This comment has been minimized.
This comment has been minimized.
|
|
bors
added
S-waiting-on-bors
and removed
S-waiting-on-review
labels
Oct 27, 2018
This comment has been minimized.
This comment has been minimized.
bors
added a commit
that referenced
this pull request
Oct 27, 2018
This comment has been minimized.
This comment has been minimized.
|
|
qnighy commentedSep 13, 2018
This PR implements by-value object safety, which is part of unsized rvalues #48055. That means, with
#![feature(unsized_locals)], you can call a methodfn foo(self, ...)on trait objects. One aim of this is to enableBox<FnOnce>in the near future.The difficulty here is this: when constructing a vtable for a trait
Foo, we can't just put the function<T as Foo>::foointo the table. IfTis no larger thanusize,selfis usually passed directly. However, as the caller of the vtable doesn't know the concreteSelftype, we want a variant of<T as Foo>::foowhereselfis always passed by reference.Therefore, when the compiler encounters such a method to be generated as a vtable entry, it produces a newly introduced instance called
InstanceDef::VtableShim(def_id)(that wraps the original instance). the shim just derefs the receiver and calls the original method. We give different symbol names for the shims by appending::{{vtable-shim}}to the symbol path (and also adding vtable-shimness as an ingredient to the symbol hash).r? @eddyb