Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Operations from atomic.h seem to be non-atomic

The following code produces random values for both n and v. It's not surprising that n is random without being properly protected. But it is supposed that v should finally be 0. Is there anything wrong in my code? Or could anyone explain this for me? Thanks.

I'm working on a 4-core server of x86 architecture. The uname is as follows.

Linux 2.6.9-22.ELsmp #1 SMP Mon Sep 19 18:00:54 EDT 2005 x86_64 x86_64 x86_64 GNU/Linux

#include <stdio.h>
#include <pthread.h>
#include <asm-x86_64/atomic.h>

int n = 0;
atomic_t v;
pthread_mutex_t mutex = PTHREAD_MUTEX_INITIALIZER;

#define LOOP 10000

void* foo(void *p)
{
    int i = 0;
    for(i = 0; i < LOOP; i++) {
//        pthread_mutex_lock(&mutex);
        ++n;
        --n;
        atomic_inc(&v);
        atomic_dec(&v);
//        pthread_mutex_unlock(&mutex);
    }

    return NULL;
}

#define COUNT 50

int main(int argc, char **argv)
{
    int i;
    pthread_t pids[COUNT];
    pthread_attr_t attr;
    pthread_attr_init(&attr);
    atomic_set(&v, 0);

    for(i = 0; i < COUNT; i++) {
        pthread_create(&pids[i], &attr, foo, NULL);
    }

    for(i = 0; i < COUNT; i++) {
        pthread_join(pids[i], NULL);
    }

    printf("%d\n", n);
    printf("%d\n", v);
    return 0;
}
like image 376
Hank Avatar asked May 04 '09 08:05

Hank


People also ask

What is non atomic operation?

Non-Atomic CPU InstructionsA memory operation can be non-atomic even when performed by a single CPU instruction. For example, the ARMv7 instruction set includes the strd instruction, which stores the contents of two 32-bit source registers to a single 64-bit value in memory.

What is atomic and non atomic operations in Java?

Atomic means only one thread accesses the variable (static type). Atomic is thread-safe, but it is slow. Nonatomic means multiple threads access the variable (dynamic type). Nonatomic is thread-unsafe, but it is fast.

What operations are atomic?

Atomic operations are sequences of instructions that guarantee atomic accesses and updates of shared single word variables. This means that atomic operations cannot protect accesses to complex data structures in the way that locks can, but they provide a very efficient way of serializing access to a single word.

What is a non atomic attribute?

Non atomic properties has no guarantee regarding the returned value. It can be the correct value, a partially written value or even some garbage value. As most things that are not safe — this comes with enhanced speed of accessing this properties.


2 Answers

You should use gcc built-ins instead (see. this) This works fine, and also works with icc.

int a; 
__sync_fetch_and_add(&a, 1); // atomic a++

Note that you should be aware of the cache consistency issues when you modify variables without locking.

like image 166
Ben Avatar answered Oct 10 '22 18:10

Ben


This old post implies that

  • It's not obvious that you're supposed to include this kernel header in userspace programs
  • It's been known to fail to provide atomicity for userspace programs.

So ... Perhaps that's the reason for the problems you're seeing?

like image 34
unwind Avatar answered Oct 10 '22 18:10

unwind