Skip to content

Commit e8fd750

Browse files
authored
Fix unbatchable meshes. (#18761)
# Objective Fixes #18550. Because bin state for unbatchable meshes wasn't being cleared each frame, the buffer indices for unbatchable meshes would demote from sparse to dense storage and aggressively leak memory, with all kinds of weird consequences downstream, namely supplying invalid instance ranges for render. ## Solution Clear out the unbatchable mesh bin state when we start a new frame.
1 parent dc7c8f2 commit e8fd750

File tree

1 file changed

+20
-0
lines changed
  • crates/bevy_render/src/render_phase

1 file changed

+20
-0
lines changed

crates/bevy_render/src/render_phase/mod.rs

Lines changed: 20 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -67,6 +67,7 @@ use bevy_ecs::{
6767
};
6868
use core::{fmt::Debug, hash::Hash, iter, marker::PhantomData, ops::Range, slice::SliceIndex};
6969
use smallvec::SmallVec;
70+
use tracing::warn;
7071

7172
/// Stores the rendering instructions for a single phase that uses bins in all
7273
/// views.
@@ -853,6 +854,10 @@ where
853854
.set_range(self.cached_entity_bin_keys.len().., true);
854855

855856
self.entities_that_changed_bins.clear();
857+
858+
for unbatchable_bin in self.unbatchable_meshes.values_mut() {
859+
unbatchable_bin.buffer_indices.clear();
860+
}
856861
}
857862

858863
/// Checks to see whether the entity is in a bin and returns true if it's
@@ -1325,6 +1330,10 @@ impl UnbatchableBinnedEntityIndexSet {
13251330
// but let's go ahead and do the sensible thing anyhow: demote
13261331
// the compressed `NoDynamicOffsets` field to the full
13271332
// `DynamicOffsets` array.
1333+
warn!(
1334+
"Unbatchable binned entity index set was demoted from sparse to dense. \
1335+
This is a bug in the renderer. Please report it.",
1336+
);
13281337
let new_dynamic_offsets = (0..instance_range.len() as u32)
13291338
.flat_map(|entity_index| self.indices_for_entity_index(entity_index))
13301339
.chain(iter::once(indices))
@@ -1337,6 +1346,17 @@ impl UnbatchableBinnedEntityIndexSet {
13371346
}
13381347
}
13391348
}
1349+
1350+
/// Clears the unbatchable binned entity index set.
1351+
fn clear(&mut self) {
1352+
match self {
1353+
UnbatchableBinnedEntityIndexSet::Dense(dense_indices) => dense_indices.clear(),
1354+
UnbatchableBinnedEntityIndexSet::Sparse { .. } => {
1355+
*self = UnbatchableBinnedEntityIndexSet::NoEntities;
1356+
}
1357+
_ => {}
1358+
}
1359+
}
13401360
}
13411361

13421362
/// A collection of all items to be rendered that will be encoded to GPU

0 commit comments

Comments
 (0)