Skip to content

Commit 2588452

Browse files
Commandqueue uses source tracing. (#21084)
Add a caller to track the source of the command queue. Add a command queue source for printing tests. # Objective Fixes #21046 ## Solution Commandqueue uses source tracing ## Testing Only one MaybeLocation has been added for tracking sources, and it only works when track-location is enabled.
1 parent f726cb2 commit 2588452

File tree

1 file changed

+28
-4
lines changed

1 file changed

+28
-4
lines changed

crates/bevy_ecs/src/world/command_queue.rs

Lines changed: 28 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,10 @@
1+
#[cfg(feature = "track_location")]
2+
use crate::change_detection::MaybeLocation;
13
use crate::{
24
system::{Command, SystemBuffer, SystemMeta},
35
world::{DeferredWorld, World},
46
};
7+
58
use alloc::{boxed::Box, vec::Vec};
69
use bevy_ptr::{OwningPtr, Unaligned};
710
use core::{
@@ -29,7 +32,6 @@ struct CommandMeta {
2932
// entities/components/resources, and it's not currently possible to parallelize these
3033
// due to mutable [`World`] access, maximizing performance for [`CommandQueue`] is
3134
// preferred to simplicity of implementation.
32-
#[derive(Default)]
3335
pub struct CommandQueue {
3436
// This buffer densely stores all queued commands.
3537
//
@@ -39,6 +41,21 @@ pub struct CommandQueue {
3941
pub(crate) bytes: Vec<MaybeUninit<u8>>,
4042
pub(crate) cursor: usize,
4143
pub(crate) panic_recovery: Vec<MaybeUninit<u8>>,
44+
#[cfg(feature = "track_location")]
45+
pub(crate) caller: MaybeLocation,
46+
}
47+
48+
impl Default for CommandQueue {
49+
#[track_caller]
50+
fn default() -> Self {
51+
Self {
52+
bytes: Default::default(),
53+
cursor: Default::default(),
54+
panic_recovery: Default::default(),
55+
#[cfg(feature = "track_location")]
56+
caller: MaybeLocation::caller(),
57+
}
58+
}
4259
}
4360

4461
/// Wraps pointers to a [`CommandQueue`], used internally to avoid stacked borrow rules when
@@ -57,9 +74,13 @@ pub(crate) struct RawCommandQueue {
5774
// So instead, the manual impl just prints the length of vec.
5875
impl Debug for CommandQueue {
5976
fn fmt(&self, f: &mut core::fmt::Formatter<'_>) -> core::fmt::Result {
60-
f.debug_struct("CommandQueue")
61-
.field("len_bytes", &self.bytes.len())
62-
.finish_non_exhaustive()
77+
let mut binding = f.debug_struct("CommandQueue");
78+
binding.field("len_bytes", &self.bytes.len());
79+
80+
#[cfg(feature = "track_location")]
81+
binding.field("caller", &self.caller.into_option());
82+
83+
binding.finish_non_exhaustive()
6384
}
6485
}
6586

@@ -311,6 +332,9 @@ impl RawCommandQueue {
311332
impl Drop for CommandQueue {
312333
fn drop(&mut self) {
313334
if !self.bytes.is_empty() {
335+
#[cfg(feature = "track_location")]
336+
warn!("CommandQueue has un-applied commands being dropped. Did you forget to call SystemState::apply? caller:{:?}",self.caller.into_option());
337+
#[cfg(not(feature = "track_location"))]
314338
warn!("CommandQueue has un-applied commands being dropped. Did you forget to call SystemState::apply?");
315339
}
316340
// SAFETY: A reference is always a valid pointer

0 commit comments

Comments
 (0)