mirror of
https://github.com/OPCFoundation/UA-.NETStandard.git
synced 2026-10-24 11:01:55 +08:00
# Description `ConditionState.m_branches` (a plain `Dictionary`) was read and written from multiple threads without synchronization. A state change on a background thread could mutate the dictionary while readers (`GetRetainState`/`UpdateRetainState`, `ConditionRefresh`, `GetBranch`) enumerated it, yielding torn entries and native access violations (observed as `IsBranch` on a null `this`). This ports the master378 fix to `master`, where the type lives at `Stack/Opc.Ua.Core.Types/State/ConditionState.cs` and uses `ByteString`/nullable refs. - **Lock all branch access**: added a private `m_branchesLock` guarding every read/write of `m_branches` (`CreateBranch`, `GetBranch`, `ReplaceBranchEvent`, `RemoveBranchEvent`, `ClearBranches`, `GetBranchCount`). - **Snapshot enumeration**: `GetBranches()` now returns a copy taken under the lock, so internal readers and `AlarmHolder.GetBranchesForConditionRefresh` iterate a stable collection while other threads mutate the live one. Public signature is unchanged. - **Test**: added `ConcurrentBranchAccessIsThreadSafe`, stressing concurrent create/clear writers against enumerate/count readers. `lock` is used rather than `SemaphoreSlim` because all affected methods are synchronous. Each `ConditionState` holds its own lock, so the recursive `UpdateRetainState` traversal across branches neither contends nor deadlocks. `ConcurrentDictionary` was rejected: it would change the public return type and still leave compound read-modify-write sequences (e.g. `ReplaceBranchEvent`) unprotected. ## Related Issues ## Checklist _Put an `x` in the boxes that apply. You can complete these step by step after opening the PR._ - [ ] I have signed the [CLA](https://opcfoundation.org/license/cla/ContributorLicenseAgreementv1.0.pdf) and read the [CONTRIBUTING](https://github.com/OPCFoundation/UA-.NETStandard/blob/master/CONTRIBUTING.md) doc. - [x] I have added tests that prove my fix is effective or that my feature works and increased code coverage. - [ ] I have added all necessary documentation. - [x] I have verified that my changes do not introduce (new) build or analyzer warnings. - [ ] I ran **all** tests locally using the **UA.slnx** solution against at least .net **framework** and .net **10**, and all passed. - [ ] I fixed **all** failing and flaky tests in the CI pipelines and **all** CodeQL warnings. - [ ] I have addressed **all** PR feedback received. --------- Co-authored-by: copilot-swe-agent[bot] <198982749+Copilot@users.noreply.github.com> Co-authored-by: Marc Schier <marcschier@users.noreply.github.com> Co-authored-by: Copilot Autofix powered by AI <175728472+Copilot@users.noreply.github.com> Co-authored-by: Suciu Mircea Adrian <Mircea-Adrian.Suciu@softing.com>