bevyengine/bevy · critical
No supported formats for surface
Error message
No supported formats for surface
What it means
After creating a window surface, Bevy reads surface.get_capabilities(&render_adapter).formats and does formats.first().expect("No supported formats for surface"). An empty capability format list means the adapter and surface are incompatible at the format level — a driver/platform problem, not application logic: nothing exists to pick even a fallback format from.
Source
Thrown at crates/bevy_render/src/view/window/mod.rs:401
for (entity, mut window, handle, mut maybe_surface_data) in &mut windows {
let Some(data) = maybe_surface_data.as_mut() else {
let surface_target = SurfaceTargetUnsafe::RawHandle {
raw_display_handle: Some(handle.get_display_handle()),
raw_window_handle: handle.get_window_handle(),
};
// SAFETY: The window handles in ExtractedWindows will always be valid objects to create surfaces on
let surface = unsafe {
// NOTE: On some OSes this MUST be called from the main thread.
// As of wgpu 0.15, only fallible if the given window is a HTML canvas and obtaining a WebGPU or WebGL2 context fails.
render_instance
.create_surface_unsafe(surface_target)
.expect("Failed to create wgpu surface")
};
let caps = surface.get_capabilities(&render_adapter);
let present_mode = present_mode(&window, &caps);
let formats = caps.formats;
// For future HDR output support, we'll need to request a format that supports HDR,
// but as of wgpu 0.15 that is not yet supported.
// Prefer sRGB formats for surfaces, but fall back to first available format if no sRGB formats are available.
let mut format = *formats.first().expect("No supported formats for surface");
for available_format in formats {
// Rgba8UnormSrgb and Bgra8UnormSrgb and the only sRGB formats wgpu exposes that we can use for surfaces.
if available_format == TextureFormat::Rgba8UnormSrgb
|| available_format == TextureFormat::Bgra8UnormSrgb
{
format = available_format;
break;
}
}
let texture_view_format = if !format.is_srgb() {
Some(format.add_srgb_suffix())
} else {
None
};
let configuration = SurfaceConfiguration {View on GitHub (pinned to 8d743eb7dc)
Solutions
- Unset WGPU_FORCE_FALLBACK_ADAPTER and WGPU_ADAPTER_NAME so wgpu picks a presenting-capable adapter
- If you need a specific GPU, verify it can output to the window (driver hybrid-graphics settings, e.g. forcing the discrete GPU system-wide)
- Update GPU drivers / VM guest tools; on Linux check the compositor and backend (Wayland vs X11) match
- As a workaround try a different backend with WGPU_BACKEND
Defensive patterns
Strategy: validation
Validate before calling
// Before app start, sanitize the environment that steers adapter choice:
fn clean_adapter_env() {
for key in ["WGPU_FORCE_FALLBACK_ADAPTER", "WGPU_ADAPTER_NAME"] {
std::env::remove_var(key); // only if you did not set them intentionally
}
} Prevention
- Don't leave WGPU_FORCE_FALLBACK_ADAPTER=1 or a wrong WGPU_ADAPTER_NAME in dev/CI environments
- On hybrid-graphics laptops, prefer driver-level GPU selection over wgpu env overrides
- Keep GPU drivers and VM guest additions up to date when running in VMs/remote sessions
When it happens
Trigger: The selected adapter reports zero supported formats for the created surface — e.g. a software/fallback adapter (WGPU_FORCE_FALLBACK_ADAPTER=1 or forced via WGPU_ADAPTER_NAME) that cannot present to the window, or a buggy/limited driver stack (vGPU, remote desktop).
Common situations: Forcing WGPU_ADAPTER_NAME to an incompatible GPU (optimus laptops picking the wrong chip); WGPU_FORCE_FALLBACK_ADAPTER=1 left set in the environment; virtual machines/remote-desktop sessions with constrained GPU paravirtualization; outdated drivers reporting empty caps.
Related errors
- Failed to create wgpu surface
- Please use a more specific shader stage: https://github.com/
- Failed to poll device for map async
- Failed to build bind group: {0}
- Failed to map buffer
AI-assisted analysis of bevyengine/bevy@8d743eb7dc (2026-08-20).
Data as JSON: /api/errors/30a41a387f149e3c.
Report an issue: GitHub.