From 5a23f93152f68f7f4759244f44f72c368645de13 Mon Sep 17 00:00:00 2001 From: gamer147 Date: Mon, 8 Jun 2026 08:25:34 -0400 Subject: [PATCH] docs(engine-ambient): explain why _components GetOrAdd factory is contention-safe Reviewer noted the factory may be invoked more than once under contention. Document the analysis inline so a future reader doesn't have to redo it: the discarded instance's mutations land on private fields of a soon-unreachable object, and the only shared sentinel (_noopViewMaterial) is read-only. Co-Authored-By: Claude Opus 4.6 (1M context) --- SVSim.BattleEngine/Shim/UnityEngine/UnityShim.cs | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/SVSim.BattleEngine/Shim/UnityEngine/UnityShim.cs b/SVSim.BattleEngine/Shim/UnityEngine/UnityShim.cs index 40fa4b9..1d3a2ae 100644 --- a/SVSim.BattleEngine/Shim/UnityEngine/UnityShim.cs +++ b/SVSim.BattleEngine/Shim/UnityEngine/UnityShim.cs @@ -225,6 +225,10 @@ namespace UnityEngine var fresh = new System.Collections.Concurrent.ConcurrentDictionary(); map = System.Threading.Interlocked.CompareExchange(ref _components, fresh, null) ?? fresh; } + // GetOrAdd may invoke the factory more than once under contention; only one result wins. + // Safe here: the discarded instance has its _go set to `this` (private write to a soon- + // unreachable object) and WireComponentFields only assigns to the new tree's own private + // fields. The shared _noopViewMaterial sentinel below is read-only. No global state leaks. return map.GetOrAdd(t, ty => { object inst;