Associated type constraints on super traits allowing for unsound transmutation to trait objects · Issue #114389 · rust-lang/rust (original) (raw)
Navigation Menu
- Explore
- Pricing
Provide feedback
Saved searches
Use saved searches to filter your results more quickly
Appearance settings
Description
This code allows for unsound transmutation to trait objects of trait with impossible constraints.
trait TypeEq { type This: ?Sized; }
impl<T: ?Sized> TypeEq for T { type This = T; }
fn identity<T: ?Sized>(t: &::This) -> &T { t // T::This is deduced to be T }
trait Cat { fn meow(&self) { println!("meow"); } }
struct SomeType; impl Cat for SomeType {}
// dyn Dog
isn't a valid type, but we are still allowed to create a trait object of this
trait Dog: TypeEq<This = dyn Cat> {
fn bark(&self) {
println!("bark");
}
}
pub fn main() { let normal_coercion: &dyn Cat = &SomeType;
// `T` is inferred to be `dyn Dog`, `T::This` is inferred as `dyn Cat`, which is different from how the compiler
// inferred these types in the function definition.
let oh_no_my_vtable: &dyn Dog = identity(normal_coercion);
oh_no_my_vtable.bark(); // meow :3
}
I'm not sure if this is a special case of one of the numerous similar known bugs, so I thought I should share it just in case. Simpler cases where the types' memory layouts do not match cause the compiler to panic or llvm to segfault during optimization.