Emanuele
Emanuele

Reputation: 1456

Why does std::atomic<T>::compare_exchange_* should not suffer from ABA issue?

In some forums and books (i.e. C++ Concurrency in Action) there's a nice example of multi-producer/multi-consumer stack, and in pop implementations they usually do the following:


// head is an std::atomic<node*> variable
node *old_head = head.load();
while(old_head && !head.compare_exchange_weak(old_head, old_head->next));
...
Why would using a std::atomic<T>::compare_exchange_* prevent the ABA issue?
Let's say that:

ABA related issue would then happen.

I believe I'm missing something. What am I missing here?

Cheers

Upvotes: 3

Views: 695

Answers (1)

Stephan Dollberg
Stephan Dollberg

Reputation: 34608

Yes, you would suffer from an ABA problem here.

Though, I think that wouldn't matter because the implementation you are referring to(listing 7.3 in CiA) is anyway invalid, it is leaking nodes.

If we have a look at the most simple reference-counted implementation, the one using a lock-free std::shared_ptr(listing 7.9 in CiA) we see that the problem wouldn't happen. When using shared pointers, the old_head would not be deleted as our thread still holds a reference to it, as such a newly created head couldn't be created in the memory address of the old head.

There is also a thread on the official Concurrency in Action Manning forums about ABA problems in the stack implementation.

Upvotes: 3

Related Questions