-
Notifications
You must be signed in to change notification settings - Fork 13k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Existential type can have inconsistent concrete type #52632
Comments
O_o I don't think I considered closures at all. Should closures be defining uses? Or just uses (and thus only be able to return that type by calling a function that defines the existential)? |
As a motivating use case, existential types defined by a closure are required if we want to extend #![feature(existential_type, untagged_unions)]
#[macro_use]
extern crate lazy_static;
use std::ops::Deref;
#[derive(Debug)]
struct ExpensiveResult;
// TODO: move this inside of `lazy_local!`.
existential type Init: FnOnce() -> ExpensiveResult;
macro_rules! lazy_local {
(ref $name:ident : $ty:ty = $init:expr;) => {
#[allow(unions_with_drop_fields)]
union BrieflyUninit {
uninit: (),
// If $name is never deref'd, this initializer is never dropped.
value: Init,
}
static mut INIT: BrieflyUninit = BrieflyUninit { uninit: () };
let init = move || -> Init { move || $init };
unsafe {
std::ptr::write(&mut INIT.value, init());
}
lazy_static! {
static ref $name: $ty = unsafe { std::ptr::read(&INIT.value)() };
}
};
}
fn lazy_deref_with_args(arg: i32) -> &'static impl Deref<Target = ExpensiveResult> {
lazy_local! {
ref STATE: ExpensiveResult = { println!("arg={}", arg); ExpensiveResult };
}
&STATE
}
fn main() {
let state = lazy_deref_with_args(1);
println!("{:?}", **state);
} |
This comment has been minimized.
This comment has been minimized.
This comment has been minimized.
This comment has been minimized.
This comment has been minimized.
This comment has been minimized.
I chose a simpler logic: any in scope use must be a defining use. |
We've moved from segmentation faults to an ICE:
|
Fixes rust-lang#52632 Existential types (soon to be 'impl trait' aliases) can either be delcared at a top-level crate/module scope, or within another item such as an fn. Previously, we were handling the second case incorrectly when recursively searching for defining usages - we would check children of the item, but not the item itself. This lead to us missing closures that consituted a defining use of the existential type, as their opaque type instantiations are stored in the TypeckTables of their parent function. This commit ensures that we explicitly visit the defining item itself, not just its children.
…r=cramertj Properly check the defining scope of existential types Fixes rust-lang#52632 Existential types (soon to be 'impl trait' aliases) can either be delcared at a top-level crate/module scope, or within another item such as an fn. Previously, we were handling the second case incorrectly when recursively searching for defining usages - we would check children of the item, but not the item itself. This lead to us missing closures that consituted a defining use of the existential type, as their opaque type instantiations are stored in the TypeckTables of their parent function. This commit ensures that we explicitly visit the defining item itself, not just its children.
…r=cramertj Properly check the defining scope of existential types Fixes rust-lang#52632 Existential types (soon to be 'impl trait' aliases) can either be delcared at a top-level crate/module scope, or within another item such as an fn. Previously, we were handling the second case incorrectly when recursively searching for defining usages - we would check children of the item, but not the item itself. This lead to us missing closures that consituted a defining use of the existential type, as their opaque type instantiations are stored in the TypeckTables of their parent function. This commit ensures that we explicitly visit the defining item itself, not just its children.
…r=cramertj Properly check the defining scope of existential types Fixes rust-lang#52632 Existential types (soon to be 'impl trait' aliases) can either be delcared at a top-level crate/module scope, or within another item such as an fn. Previously, we were handling the second case incorrectly when recursively searching for defining usages - we would check children of the item, but not the item itself. This lead to us missing closures that consituted a defining use of the existential type, as their opaque type instantiations are stored in the TypeckTables of their parent function. This commit ensures that we explicitly visit the defining item itself, not just its children.
…r=cramertj Properly check the defining scope of existential types Fixes rust-lang#52632 Existential types (soon to be 'impl trait' aliases) can either be delcared at a top-level crate/module scope, or within another item such as an fn. Previously, we were handling the second case incorrectly when recursively searching for defining usages - we would check children of the item, but not the item itself. This lead to us missing closures that consituted a defining use of the existential type, as their opaque type instantiations are stored in the TypeckTables of their parent function. This commit ensures that we explicitly visit the defining item itself, not just its children.
Mentioning the existential types tracking issue #34511
Mentioning @oli-obk and @cramertj
The text was updated successfully, but these errors were encountered: