blob: 93398da6763a0f0f91911fd05b305b4906b494f7 (
plain) (
blame)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
|
# TSAN suppression / options file for zenserver
#
# Usage:
# TSAN_OPTIONS="detect_deadlocks=0 suppressions=$(pwd)/tsan.supp" ./zenserver
#
# NOTE: detect_deadlocks=0 is required because the GC's LockState() acquires shared
# lock scopes on every named cache bucket (m_IndexLock) and every oplog
# (GcReferenceLocker) simultaneously. With enough buckets/projects/oplogs this
# easily exceeds TSAN's hard per-thread limit of 128 simultaneously-held locks
# (all_locks_with_contexts_[128] in sanitizer_deadlock_detector.h:67), causing a
# CHECK abort. This is a known TSAN limitation, not a real deadlock risk.
# The long-term fix is to replace the N per-bucket shared-lock pattern in
# ZenCacheStore::LockState / ProjectStore::LockState with a single coarser
# "GC epoch" RwLock at the disk-layer / project-store level.
# EASTL's hashtable uses a global gpEmptyBucketArray[2] sentinel shared by all
# empty hash tables (mnBucketCount == 1). DoFreeNodes unconditionally writes NULL
# to each bucket slot, including this shared global. Multiple threads concurrently
# destroying empty EASTL hash_maps all write NULL to gpEmptyBucketArray[0], which
# TSAN reports as a race. This is benign: the slot is always NULL and writing NULL
# to it has no observable effect.
race:eastl::hashtable*DoFreeNodes*
# UE::Trace's GetUid() uses a racy static uint32 cache (Uid = Uid ? Uid : Initialize())
# as a fast path to avoid re-entering Initialize(). The actual initialization is done via
# a thread-safe static (Uid_ThreadSafeInit) inside Initialize(), so the worst case is
# redundant calls to Initialize() which always returns the same value.
race:*Fields::GetUid*
# TRACE_CPU_SCOPE generates a function-local `static int32 scope_id` that is lazily
# initialized without synchronization (if (0 == scope_id) scope_id = ScopeNew(...)).
# Same benign pattern as GetUid: the worst case is redundant calls to ScopeNew() which
# always returns the same value for a given scope name.
race:*$trace_scope_id*
|