I’m working on a concurrent dictionary implementation for C#, and I’m wondering if this GetEnumerator() implementation is actually (thread) safe.
It’s not doing a actual snapshot, so I’m wondering if it’ll mess up later read/writes to the internal dictionary, or if it’ll expose potential deadlocks because the enumeration of the exposed IEnumerator will actually run inside the lock.
private readonly Dictionary<TKey, TValue> internalDictionary;
private SpinLock spinLock = new SpinLock();
IEnumerator IEnumerable.GetEnumerator()
{
IEnumerator enumerator;
bool lockTaken = false;
try
{
spinLock.TryEnter(ref lockTaken);
enumerator = (this.internalDictionary as IEnumerable).GetEnumerator();
}
finally
{
if (lockTaken)
{
spinLock.Exit(false);
}
}
return enumerator;
}
Your method is not thread-safe with respect to concurrent writers because
ToListon it or something to actually snapshot.Here is a fixed version with all the cleverness removed:
Concurrent writers have to take the lock, too.