What happens if two threads read and write the same piece of memory

I understand that if two threads are read from the same part of the memory, and no thread writes to this memory, the operation is safe. However, I'm not sure what will happen if one thread reads and the other writes. What would happen? The result is undefined? Or would you just read eclipse? If an obsolete read is not a concern, is it normal to have an unsynchronized write-write to a variable? Or is it possible that the data will be corrupted and neither reading nor writing will be correct, in which case should always be synchronized?

I want to say that I found out that this is a later case when the memory access race goes out of undefined state ... but I don’t remember where I might have found out about it, and I have a hard time finding the answer on google . My intuition is that a variable is managed in registers and that true (as in hardware) concurrency is impossible (or is), so the worst that can happen is outdated data, i.e. the following:

WriteThread: copy value from memory to register
WriteThread: update value in register
ReadThread:  copy value of memory to register
WriteThread: write new value to memory

At this point, the read stream has outdated data.

+6
source share
4 answers

undefined. . 64- , 32- . , , , 32- 0xffffffff. 0x00000000. , . , , - , , , , 0 - , .

+8

, ( 32- 64- , 32- 64- ).

, , .

32- /.

32 ​​ , , : . (, ), , . (, ), .

, (, 128- ), , ' t , . , , , .

, , .

, , , .

+9

, . :

!

- , - , .

#include <windows.h>
#include <stdio.h>

const int RUNFOR = 5000;
volatile bool terminating = false;
volatile int value;

static DWORD WINAPI CountErrors(LPVOID parm)
{
    int errors = 0;
    while(!terminating)
    {
        value = (int) parm;
        if(value != (int) parm)
            errors++;
    }
    printf("\tThread %08X: %d errors\n", parm, errors);
    return 0;
}

static void RunTest(int affinity1, int affinity2)
{
    terminating = false;
    DWORD dummy;
    HANDLE t1 = CreateThread(0, 0, CountErrors, (void*)0x1000, CREATE_SUSPENDED, &dummy);
    HANDLE t2 = CreateThread(0, 0, CountErrors, (void*)0x2000, CREATE_SUSPENDED, &dummy);

    SetThreadAffinityMask(t1, affinity1);
    SetThreadAffinityMask(t2, affinity2);
    ResumeThread(t1);
    ResumeThread(t2);

    printf("Running test for %d milliseconds with affinity %d and %d\n", RUNFOR, affinity1, affinity2);
    Sleep(RUNFOR);
    terminating = true;
    Sleep(100); // let threads have a chance of picking up the "terminating" flag.
}

int main()
{
    SetPriorityClass(GetCurrentProcess(), REALTIME_PRIORITY_CLASS);
    RunTest(1, 2);      // core 1 & 2
    RunTest(1, 4);      // core 1 & 3
    RunTest(4, 8);      // core 3 & 4
    RunTest(1, 8);      // core 1 & 4
}

Intel Q6600 ( iirc , L2), ;)), :

Running test for 5000 milliseconds with affinity 1 and 2
        Thread 00002000: 351883 errors
        Thread 00001000: 343523 errors
Running test for 5000 milliseconds with affinity 1 and 4
        Thread 00001000: 48073 errors
        Thread 00002000: 59813 errors
Running test for 5000 milliseconds with affinity 4 and 8
        Thread 00002000: 337199 errors
        Thread 00001000: 335467 errors
Running test for 5000 milliseconds with affinity 1 and 8
        Thread 00001000: 55736 errors
        Thread 00002000: 72441 errors
0

? , - , ? . ArrayList Java, ArrayList. , ( ) , . , , ArrayList , - ArrayList , - ArrayList 1.

0

All Articles