-
Notifications
You must be signed in to change notification settings - Fork 11
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
Fix: Reference Counting Cache refactoring #2182
base: main
Are you sure you want to change the base?
Conversation
- Textures referencing, Sprites handling, all systems are changed accordingly - UIBackground - NFT - Avatar Attachment Thumbnails - Materials - Map Pins - Common Ref Counting Data - Asset Bundle Cache, Audio Cache, Profiles Cache are unified
- Unify Video Texture with Texture2DData - Fix tests
# Conflicts: # Explorer/Assets/DCL/PluginSystem/Global/MultiplayerMovementPlugin.cs
Windows and Mac build successfull in Unity Cloud! You can find a link to the downloadable artifact below.
|
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.
🟢 QA Approved. The assets no longer disappear after pressing the FULL button in memory settings.
This fix was verified on Windows and Mac. A smoke test was performed, covering:
- Backpack
- Emotes
- Nav bar (all shortcuts)
- Badges/Profile Customization
- Map navigation
- Scenes/worlds (Doll House/Seed/Casa Roustan/Metadynelabs).
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.
Really nice PR! Cache is looking so much better <3
Left some cleaning suggestions, and a possible leak detection. let me know your thoughts!
using Object = UnityEngine.Object; | ||
|
||
namespace ECS.StreamableLoading.AssetBundles | ||
{ | ||
/// <summary> | ||
/// A wrapper over <see cref="AssetBundle" /> to provide additional data | ||
/// </summary> | ||
public class AssetBundleData : IAssetData | ||
public class AssetBundleData : StreamableRefCountData<AssetBundle>, IStreamableRefCountData |
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.
IStreamableRefCountData
is redudant here
namespace ECS.StreamableLoading.Cache | ||
{ | ||
public abstract class RefCountStreamableCacheBase<TAssetData, TAsset, TLoadingIntention> : IEqualityComparer<TLoadingIntention> | ||
where TAssetData: StreamableRefCountData<TAsset> where TAsset: class |
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.
public bool TryGet(in TLoadingIntention key, out TAssetData asset) => | ||
cache.TryGetValue(key, out asset); | ||
|
||
public void AddReference(in TLoadingIntention _, TAssetData asset) |
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.
Maybe we can make this one internal
since its only used for testing?
/// Needed for non-ECS code to properly handle reference counting | ||
/// </summary> | ||
/// <returns></returns> | ||
public RefAcquisition AcquireRef() => |
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.
Isnt it a little bit YAGNI? Some examples come to mind? As far as I see, this is not beieng used.
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.
We have a mess with profiles where it will be needed, I wanted to address it straight-away but the scope was too big
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.
I would like to leave it here even for the existing assets so e.g. if the texture is requested from UI it can be owned and later unowned
{ | ||
private int referencesCount; | ||
public AudioClip AudioClip => Asset; |
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 not used anywhere. Should we remove it for clarity? Seems like Asset
is the way to access the Audio
} | ||
|
||
public void Dispose() | ||
{ | ||
// On Dispose video textures are dereferenced by material that acquired it |
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.
I think we have a leak here.
This texture was never added to the texture cache, since its not created through LoadSystemBase
, but rather on the fly by VideoTextureUtils
, gotten through the videoTexturesPool
.I understand that by this point it should not hold any reference since it was dereferenced by the material that it was using it and now destroyed.
But shouldnt it be returned to the pool here, rather than nullifying it?
Whatsmore, cleaning of this pool cache for this pool is not clear.
I see that its injected in MediaPlayerPluginWrapper
and then registered to the cache cleanear, as part of the avatarPools
. The name is super misleading, but Im ignoring that. When this type of pool cache is cleared in ExtendedObjectPool.ClearThrottled
, only objects in the pool are cleared. But I couldnt find the place where we returned the video texture to the pool.
It may be out of scopre of this PR, but as I see it, I think we have a leak here.
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 the only place where we return the video texture to the pool and call Dispose
:
private void CleanUpVideoTexture(ref VideoTextureConsumer videoTextureConsumer)
{
videoTexturesPool.Release(videoTextureConsumer.Texture);
videoTextureConsumer.Dispose();
}
in CleanUpMediaPlayerSystem
and VideoTextureConsumer
itself is not bound to the pool itself (by design), that's why it does not handle returning to the pool.
I preserved the original design
# Conflicts: # Explorer/Assets/DCL/AvatarRendering/Emotes/Components/IEmote.cs # Explorer/Assets/DCL/SDKComponents/SceneUI/Systems/UIBackground/UIBackgroundInstantiationSystem.cs
Fixes #2126
RefCountStreamableCacheBase
for:Profiles
Asset Bundles
Audio Clips
Nft Shape
Textures
StreamableRefCountData<TAsset>
, it is the base class for all cached assets with ref countingMaterials
already were releasing properly: they required minimum adjustmentsHow to QA
Following this pattern:
Memory.FULL
inDebug Menu
Memory.NORMAL
All the affected assets should be verified:
For Avatar Attachments check that thumbnails do not disappear (backpack, passport) after setting
Memory.FULL