Why is this not thread safe?

time to read 2 min | 238 words

Originally posted at 4/15/2011

Take a look at the following piece of code:

if(items.ContainsKey(key) == false)
{
    lock(items)
    {
        if(items.ContainsKey(key) == false)
        {
            items.Add(key, val);
        }
    }
}

The answer is quite simple, and it is located directly in the docs:

image

Yes, on the face of it, this is safe code, in the sense that we will never get DuplicateKeyException. But the implementation of ContainsKey() isn’t safe to run when Add() is also executing.

The actual behavior depends on the implementation, but it is easy enough to imagine a scenario where invariants that ContainsKey() relies on are broken for the duration of the Add() call.