-
Notifications
You must be signed in to change notification settings - Fork 12.7k
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
Next-gen solver: Compiler "hang" & eventual OOM when facing complex mutually recursive structs & many projections #126196
Comments
cc @lcnr |
Ofc, I will try to minimize this in the coming hours or days. |
Slightly smaller: Reproducer (78 LOC)use std::sync::{Mutex, Arc, Weak};
use std::collections::HashMap;
pub trait Api: Clone {
type Surface: Surface<A = Self>;
type Buffer: WasmNotSendSync + 'static;
type Texture: WasmNotSendSync + 'static;
type SurfaceTexture: WasmNotSendSync + std::borrow::Borrow<Self::Texture>;
type TextureView: WasmNotSendSync;
type Sampler: WasmNotSendSync;
type QuerySet: WasmNotSendSync;
}
pub trait Surface: WasmNotSendSync {
type A: Api;
}
pub trait WasmNotSendSync: WasmNotSend + WasmNotSync {}
impl<T: WasmNotSend + WasmNotSync> WasmNotSendSync for T {}
pub trait WasmNotSend: Send {}
impl<T: Send> WasmNotSend for T {}
pub trait WasmNotSync: Sync {}
impl<T: Sync> WasmNotSync for T {}
trait HalApi: Api + 'static {}
struct BindGroup<A: HalApi>(Box<Device<A>>);
struct Device<A: HalApi>(LifetimeTracker<A>);
struct LifetimeTracker<A: HalApi>(
Vec<Arc<Texture<A>>>,
ResourceMaps<A>,
Vec<ActiveSubmission<A>>,
);
struct Buffer<A: HalApi>(
A::Buffer,
Arc<Device<A>>,
std::marker::PhantomData<Buffer<A>>,
Mutex<Vec<Weak<BindGroup<A>>>>,
);
struct StagingBuffer<A: HalApi>(
Mutex<Option<A::Buffer>>,
Arc<Device<A>>,
std::marker::PhantomData<StagingBuffer<A>>,
);
struct Texture<A: HalApi>(
Arc<Device<A>>,
std::marker::PhantomData<Texture<A>>,
Mutex<Vec<Weak<TextureView<A>>>>,
Mutex<Vec<Weak<BindGroup<A>>>>,
);
struct TextureView<A: HalApi>(
A::TextureView,
Arc<Texture<A>>,
Arc<Device<A>>,
std::marker::PhantomData<TextureView<A>>,
);
struct Sampler<A: HalApi>(
Option<A::Sampler>,
Arc<Device<A>>,
std::marker::PhantomData<Self>,
);
struct ResourceMaps<A: HalApi>(
HashMap<i32, Arc<Buffer<A>>>,
HashMap<i32, Arc<StagingBuffer<A>>>,
HashMap<i32, Arc<Texture<A>>>,
HashMap<i32, Arc<TextureView<A>>>,
HashMap<i32, Arc<Sampler<A>>>,
HashMap<i32, Arc<BindGroup<A>>>,
HashMap<i32, Arc<A>>,
HashMap<i32, Arc<A>>,
HashMap<i32, Arc<A>>,
HashMap<i32, Arc<A>>,
HashMap<i32, Arc<A>>,
);
struct ActiveSubmission<A: HalApi>(
ResourceMaps<A>,
Vec<Arc<Buffer<A>>>,
Vec<std::marker::PhantomData<A>>,
);
fn main() {
check::<BindGroup<_>>();
fn check<T: WasmNotSync>() {}
} Even smaller: Reproducer (61 LOC)use std::sync::{Mutex, Arc, Weak};
pub trait Api {
type Surface: Surface<A = Self>;
type Buffer: WasmNotSendSync + 'static;
type Texture: WasmNotSendSync + 'static;
type SurfaceTexture: WasmNotSendSync + std::borrow::Borrow<Self::Texture>;
type TextureView: WasmNotSendSync;
type Sampler: WasmNotSendSync;
type QuerySet: WasmNotSendSync;
}
pub trait Surface: WasmNotSendSync {
type A: Api;
}
pub trait WasmNotSendSync: WasmNotSend + WasmNotSync {}
impl<T: WasmNotSend + WasmNotSync> WasmNotSendSync for T {}
pub trait WasmNotSend: Send {}
impl<T: Send> WasmNotSend for T {}
pub trait WasmNotSync: Sync {}
impl<T: Sync> WasmNotSync for T {}
trait HalApi: Api {}
struct BindGroup<A: HalApi>(Box<Device<A>>);
struct Device<A: HalApi>(ResourceMaps<A>);
struct Buffer<A: HalApi>(
A::Buffer,
Arc<Device<A>>,
std::marker::PhantomData<Buffer<A>>,
Mutex<Vec<Weak<BindGroup<A>>>>,
);
struct StagingBuffer<A: HalApi>(
Mutex<Option<A::Buffer>>,
Arc<Device<A>>,
std::marker::PhantomData<StagingBuffer<A>>,
);
struct Texture<A: HalApi>(
Arc<Device<A>>,
std::marker::PhantomData<Texture<A>>,
Mutex<Vec<Weak<TextureView<A>>>>,
Mutex<Vec<Weak<BindGroup<A>>>>,
);
struct TextureView<A: HalApi>(
A::TextureView,
Arc<Texture<A>>,
Arc<Device<A>>,
std::marker::PhantomData<TextureView<A>>,
);
struct Sampler<A: HalApi>(
Option<A::Sampler>,
Arc<Device<A>>,
std::marker::PhantomData<Self>,
);
struct ResourceMaps<A: HalApi>(
Arc<Buffer<A>>,
Arc<StagingBuffer<A>>,
Arc<TextureView<A>>,
Arc<Sampler<A>>,
Arc<BindGroup<A>>,
);
fn main() {
check::<BindGroup<_>>();
fn check<T: WasmNotSync>() {}
} |
"Even smaller" (no longer I-hang but still I-compiletime (32.31s on my machine) + I-compilemem (9GB+)): "Reproducer" (53 LOC)use std::sync::{Mutex, Arc, Weak};
pub trait HalApi {
type Surface: Surface<A = Self>;
type Buffer: WasmNotSendSync;
type Texture: WasmNotSendSync ;
type SurfaceTexture: WasmNotSendSync;
type TextureView: WasmNotSendSync;
type Sampler: WasmNotSendSync;
}
pub trait Surface: WasmNotSendSync {
type A: HalApi;
}
pub trait WasmNotSendSync: WasmNotSend + WasmNotSync {}
impl<T: WasmNotSend + WasmNotSync> WasmNotSendSync for T {}
pub trait WasmNotSend: Send {}
impl<T: Send> WasmNotSend for T {}
pub trait WasmNotSync: Sync {}
impl<T: Sync> WasmNotSync for T {}
struct BindGroup<A: HalApi>(Box<Device<A>>);
struct Device<A: HalApi>(ResourceMaps<A>);
struct Buffer<A: HalApi>(
A::Buffer,
Arc<Device<A>>,
std::marker::PhantomData<Buffer<A>>,
Mutex<Vec<Weak<BindGroup<A>>>>,
);
struct Texture<A: HalApi>(
Arc<Device<A>>,
std::marker::PhantomData<Texture<A>>,
Mutex<Vec<Weak<TextureView<A>>>>,
Mutex<Vec<Weak<BindGroup<A>>>>,
);
struct TextureView<A: HalApi>(
A::TextureView,
Arc<Texture<A>>,
Arc<Device<A>>,
std::marker::PhantomData<TextureView<A>>,
);
struct Sampler<A: HalApi>(
Option<A::Sampler>,
Arc<Device<A>>,
std::marker::PhantomData<Self>,
);
struct ResourceMaps<A: HalApi>(
Arc<Buffer<A>>,
Arc<TextureView<A>>,
Arc<Sampler<A>>,
Arc<BindGroup<A>>,
);
fn main() {
check::<BindGroup<_>>();
fn check<T: WasmNotSync>() {}
} Minimization is prone to distortion (at least with the way I was just pursuing). Stopping right now, will pick it up some other time and will try different approaches that are less aggressive. |
(Replacing
I-hang
|
should be fixed by #125981 |
Fixed by #128828. |
Context / History
The original issue is a rustdoc[old solver] compiletime issue: #114891.
I was able to reduce that issue to 211 LOC: #114891 (comment).
I then looked into switching rustdoc's blanket impl synthesizer to use the next solver: #125907.
Ignoring the fact that that's blocked on perf, it would actually make #114891 (comment) hang and alloc until the OS's OOM killer swoops in.
Finally, the reproducer below (to be minimized) is the rustdoc[next solver] "MCVE" turned into a rustc[next solver] issue by "reifying" the obligations registered by
blanket_impl
as Rust code.Fixing this issue would partially unblock #125907 / #114891.
Reproducer
Old solver: Error type annotations needed // cannot infer type of the type parameter
T
declared on the functioncheck
.Next solver: Compiler hang & eventual OOM.
Reproducer (215 LOC)
The text was updated successfully, but these errors were encountered: