Search Issue Tracker

Won't Fix

Won't Fix in 6000.0.X, 6000.3.X, 6000.4.X, 6000.5.X, 6000.6.X

Votes

19

Found in

6000.0.69f1

6000.3.11f1

6000.4.0b9

6000.5.0a8

6000.6.0a1

Issue ID

UUM-139722

Regression

No

Crash on "core::base_hash_set" when using nested [SerializeReference] fields in List<T> structures

Serialization

-

How to reproduce:
1. Open the attached “IN-136474.zip” project
2. Open the “__Test” scene
3. In the Hierarchy tab, select the “Character” GameObject
4. In the Inspector tab, click and open the “Character.cs“ script
5. Make any change to the script
6. Save the script
7. Observe the Unity Editor

Actual result: Editor freezes on “Reloading Domain” and crashes after a minute
Expected result: Editor compiles all scripts successfully

Reproducible with: 2023.1.0a5, 6000.0.72f1, 6000.3.12f1, 6000.4.2f1, 6000.5.0b3, 6000.6.0a2

Reproducible on: macOS 15.3.2 (24D81) (M1 Max)
Not reproducible on: No other environment tested

Notes: Commenting out the [SerializeReference] module list in “ControllerCore.cs” fixes the crash

First few lines of stack trace:
#0 0x00000100bb20ac in core::base_hash_set<core::pair<core::pair<EntityId, bool, false> const, ShaderChannelMask, false>, core::hash_pair<core::hash<core::pair<EntityId, bool, false>>, core::pair<EntityId, bool, false>>, core::equal_pair<std::__1::equal_to<core::pair<EntityId, bool, false>>, core::pair<EntityId, bool, false>>>::resize(int)
#1 0x000001038deb50 in core::pair<core::base_hash_set<core::pair<long long const, ScriptingGCHandle, false>, core::hash_pair<core::hash<long long>, long long>, core::equal_pair<std::__1::equal_to<long long>, long long>>::node_iterator<core::pair<long long const, ScriptingGCHandle, false>>, bool, false> core::base_hash_set<core::pair<long long const, ScriptingGCHandle, false>, core::hash_pair<core::hash<long long>, long long>, core::equal_pair<std::__1::equal_to<long long>, long long>>::insert<core::pair<long long, ScriptingGCHandle, false>>(core::pair<long long, ScriptingGCHandle, false>&&)
#2 0x000001038da14c in WeakRefInstanceTracker::Add(long long, ScriptingObjectPtr)
#3 0x000001038d9f2c in ManagedReferencesRegistry::TrackInstance(long long, ScriptingObjectPtr, ManagedReferencesRegistry::TrackInstanceConflictBehavior)
#4 0x000001038d9e40 in ManagedReferencesRegistry::TrackInstanceWithNewId(ScriptingObjectPtr)
#5 0x000001038e3a64 in ManagedReferencesTransferState::RegisterReference(ScriptingObjectPtr)

  1. Resolution Note:

    Thank you for reporting a bug to Unity.

    We have reviewed the issue carefully, and in this case, the team is unable to prioritize fixing this bug. There are a number of reasons we make this decision, including the impact and severity of the issue across our user and customer base, and the possibility that future plans may solve the problem in a different way, or that a workaround for the bug may be available.

    Today we will be closing this case. Thank you again for taking the time to report this issue, and please let us know if there is anything else that changes the impact or severity of this issue.

    The crash is caused by an infinite loop caused by an unfortunate interaction between Unity serialization semantics and the user code using field initialization to instantiate new objects.

    There is a workaround:

    The two files involved are:

    Runtime/Modules/Core/Input/ModuleInput.cs — this is where the [SerializeReference] fields are initialized in the field initializer:
    - m_Input = new InputProcessorDirectional()
    - m_Submodules = { new SubmoduleInputJump(), new SubmoduleInputDash() }

    Runtime/Modules/Core/Input/Submodules/Base/SubmoduleInput.cs — this is where the protected ModuleInput Input { get; private set; } auto-property closes the cycle
    back to ModuleInput.

    The simplest fix the user can apply is in ModuleInput.cs: remove the field initializers from both [SerializeReference] fields and initialize them in Reset()
    instead:

    [SerializeReference] private InputProcessorBase m_Input;
    [SerializeReference] private SubmoduleInput[] m_Submodules;

    private void Reset()
    {
    m_Input = new InputProcessorDirectional();
    m_Submodules = new SubmoduleInput[] { new SubmoduleInputJump(), new SubmoduleInputDash() };
    }

    That breaks the cycle at the source without touching SubmoduleInput.cs at all — ModuleInput no longer seeds SerializeReference children in its constructor, so the walker never has new submodule instances to chase.

  2. Resolution Note (6000.6.X):

    Thank you for reporting a bug to Unity.

    We have reviewed the issue carefully, and in this case, the team is unable to prioritize fixing this bug. There are a number of reasons we make this decision, including the impact and severity of the issue across our user and customer base, and the possibility that future plans may solve the problem in a different way, or that a workaround for the bug may be available.

    Today we will be closing this case. Thank you again for taking the time to report this issue, and please let us know if there is anything else that changes the impact or severity of this issue.

  3. Resolution Note (6000.6.X):

    Thank you for reporting a bug to Unity.

    We have reviewed the issue carefully, and in this case, the team is unable to prioritize fixing this bug. There are a number of reasons we make this decision, including the impact and severity of the issue across our user and customer base, and the possibility that future plans may solve the problem in a different way, or that a workaround for the bug may be available.

    Today we will be closing this case. Thank you again for taking the time to report this issue, and please let us know if there is anything else that changes the impact or severity of this issue.

    The crash is caused by an infinite loop caused by an unfortunate interaction between Unity serialization semantics and the user code using field initialization to instantiate new objects.

    There is a workaround:

    The two files involved are:

    Runtime/Modules/Core/Input/ModuleInput.cs — this is where the [SerializeReference] fields are initialized in the field initializer:
    - m_Input = new InputProcessorDirectional()
    - m_Submodules = { new SubmoduleInputJump(), new SubmoduleInputDash() }

    Runtime/Modules/Core/Input/Submodules/Base/SubmoduleInput.cs — this is where the protected ModuleInput Input { get; private set; } auto-property closes the cycle
    back to ModuleInput.

    The simplest fix the user can apply is in ModuleInput.cs: remove the field initializers from both [SerializeReference] fields and initialize them in Reset()
    instead:

    [SerializeReference] private InputProcessorBase m_Input;
    [SerializeReference] private SubmoduleInput[] m_Submodules;

    private void Reset()
    {
    m_Input = new InputProcessorDirectional();
    m_Submodules = new SubmoduleInput[] { new SubmoduleInputJump(), new SubmoduleInputDash() };
    }

    That breaks the cycle at the source without touching SubmoduleInput.cs at all — ModuleInput no longer seeds SerializeReference children in its constructor, so the walker never has new submodule instances to chase.

  4. Resolution Note (6000.5.X):

    Thank you for reporting a bug to Unity.

    We have reviewed the issue carefully, and in this case, the team is unable to prioritize fixing this bug. There are a number of reasons we make this decision, including the impact and severity of the issue across our user and customer base, and the possibility that future plans may solve the problem in a different way, or that a workaround for the bug may be available.

    Today we will be closing this case. Thank you again for taking the time to report this issue, and please let us know if there is anything else that changes the impact or severity of this issue.

  5. Resolution Note (6000.4.X):

    Thank you for reporting a bug to Unity.

    We have reviewed the issue carefully, and in this case, the team is unable to prioritize fixing this bug. There are a number of reasons we make this decision, including the impact and severity of the issue across our user and customer base, and the possibility that future plans may solve the problem in a different way, or that a workaround for the bug may be available.

    Today we will be closing this case. Thank you again for taking the time to report this issue, and please let us know if there is anything else that changes the impact or severity of this issue.

  6. Resolution Note (6000.3.X):

    Thank you for reporting a bug to Unity.

    We have reviewed the issue carefully, and in this case, the team is unable to prioritize fixing this bug. There are a number of reasons we make this decision, including the impact and severity of the issue across our user and customer base, and the possibility that future plans may solve the problem in a different way, or that a workaround for the bug may be available.

    Today we will be closing this case. Thank you again for taking the time to report this issue, and please let us know if there is anything else that changes the impact or severity of this issue.

  7. Resolution Note (6000.0.X):

    Thank you for reporting a bug to Unity.

    We have reviewed the issue carefully, and in this case, the team is unable to prioritize fixing this bug. There are a number of reasons we make this decision, including the impact and severity of the issue across our user and customer base, and the possibility that future plans may solve the problem in a different way, or that a workaround for the bug may be available.

    Today we will be closing this case. Thank you again for taking the time to report this issue, and please let us know if there is anything else that changes the impact or severity of this issue.

Add comment

Log in to post comment

All about bugs

View bugs we have successfully reproduced, and vote for the bugs you want to see fixed most urgently.