-
-
Notifications
You must be signed in to change notification settings - Fork 3.9k
Separate component and resource access #14561
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
Separate component and resource access #14561
Conversation
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This is my preferred approach. This is a straightforward and more correct model.
Code is good, tests are nice. There's a couple of docs that you missed updating but this is fundamentally an approval.
/// The exclusively-accessed components. | ||
component_writes: FixedBitSet, | ||
/// All accessed resources. | ||
resource_read_and_writes: FixedBitSet, |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Why introduce extra FixedBitSets for resources here? IMO, we only need to split 'reads/writes_all' into 'read/write_all_component/resource' because Components and Resources share ID space
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
It's to check the has_any_resource
that is needed to check compatibility
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
There's also a correctness hazard in sharing the bit sets for resources and components. There's a risk that the component Foo clashes with the resource Foo, for types which are both components and resources. This isn't the right memory model, and care must be taken far elsewhere in the stack (when assigning component ids) to avoid it if we don't separate it here.
A test to validate that behavior would be nice actually.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Not for this PR, but we should discuss whether to split the ID space. With this PR each bitset is going to be oversized and do extra work for the id's of the other type.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
what I am most worried about is that Access
is used in many places (such as EntityFilterRef), Perhaps we can move it to a new struct CombinedAccess
and used it for' FilteredAccessSet::combined_access, with hhis way, we can limit the influence of this pr.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Not for this PR, but we should discuss whether to split the ID space. With this PR each bitset is going to be oversized and do extra work for the id's of the other type.
Note that this probably won't be a problem anymore if we go ahead with this
#14385
which removes the bitsets.
(which will probably be necessary since with relations the ComponentIds will become very high, so the memory used by FixedBitSet will become prohibitive)
what I am most worried about is that Access is used in many places (such as EntityFilterRef), Perhaps we can move it to a new struct CombinedAccess and used it for' FilteredAccessSet::combined_access, with hhis way, we can limit the influence of this pr.
Your concern is the increased memory usage because of 2 FixedBitSets?
Yes i think the solution would probably be #14385
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Your concern is the increased memory usage because of 2 FixedBitSets?
yeah ,Two FixedBitSets (even not used) occupy extra 48 bytes, we only use it for combined access,
With #14385, this number is even Larger
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
A test to validate that behavior would be nice actually.
@alice-i-cecile added a test that checks that a resource/component that share the same componentId (same struct) do not conflict with each other
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
yeah ,Two FixedBitSets (even not used) occupy extra 48 bytes, we only use it for combined access,
With #14385, this number is even Larger
On the contrary with #14385 we don't have a problem anymore, no?
14385 uses a Vec<usize>
for the access; so if there are no resource accessed we would just have an empty vec.
Or do you mean stack usage and not heap usage?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
with #14385 It will make the problem more serious.
Access
is just a struct, whether it occupies stack or heap depends on how you use it- Update Access and FilteredAccess to use sorted vecs instead of FixedBitSet #14385 uses SmallVec<[usize;N> (N default to 64),so it occupies 24+8 * 64 =536 bytes (* 2 = 1072 bytes ) even without any usage.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Good changes, and always good to add some test cases!
I want to merge #14579 first, to ensure that we have more test cases in place. |
@re0312 while I share your nervousness about performance, the existing model is both wrong and confusing IMO. The test added in daf6981 won't pass using the access model on |
yeah. totally agree with you , I don't intend to block this , I'm merely expressing my concern about it. |
# Objective Re-enable some tests in `entity_ref.rs` that are marked as `#[ignore]`, but that pass after #14561. ## Solution Remove `#[ignore]` from those tests.
# Objective Re-enable some tests in `entity_ref.rs` that are marked as `#[ignore]`, but that pass after bevyengine#14561. ## Solution Remove `#[ignore]` from those tests.
# Objective Re-enable some tests in `entity_ref.rs` that are marked as `#[ignore]`, but that pass after bevyengine#14561. ## Solution Remove `#[ignore]` from those tests.
Objective
Solution
component
fields andresource
fieldsTesting