메모리 배리어
멀티스레드 환경에서 메모리순서가 강제로 변경되는데, 이때 메모리 순서 변경을 막기위한 방법
코드 재배치 억제
1) Full Memory Barrier(어셈블리 MFENCE, C# Thread.MemoryBarrier) - Store/Load 둘다 막는다.
2) Store Memory Barrier(어셈블리 SFENCE - Store 막는다)
3) Load Memory Barrier(어셈블리 LFENCE - Load 막는다)
* 일단은 Full Memory Barrier만 알아 둘 것!
static int x = 0;
static int y = 0;
static int r1 = 0;
static int r2 = 0;
static void Thread_1()
{
y = 1;
//Thread.MemoryBarrier(); 메모리베리어 사용시 메모리의 순서가 변하지 않는다.
r1 = x;
}
static void Thread_2()
{
x = 1;
//Thread.MemoryBarrier(); 메모리베리어 사용시 메모리의 순서가 변하지 않는다.
r2 = y;
}
static void Main(string[] args)
{
int count = 0;
while (true)
{
count++;
x = y = r1 = r2 = 0;
Task t1 = new Task(Thread_1);
Task t2 = new Task(Thread_2);
t1.Start();
t2.Start();
Task.WaitAll(t1, t2);
if(r1==0 && r2 == 0)
{
break;
}
}
Console.WriteLine(count);
}
메모리 배리어를 사용하지 않으면, 위 코드는 평균 10~30 count로 프로그램이 종료된다. 하지만 메모리 배리어를 사용하면무한 루프를 빠져나오지 못하고, 프로그램이 종료되지 않는다. 컴파일러나 CPU는 실행 속도를 높히기 위해 코드의 실행 순서를 바꿀 수 있다.
가시성
멀티쓰레드 환경에서 한 쓰레드의 연산상황을 중앙 메모리에 업로드해서 다른 쓰레드도 지금 다른 그 쓰레드의 변경된 값들을 반영할 수 있다.
ex) 식당에 가시성을 비유를 하면, 주문현황판에 새로 받은 주문을 업데이트를 해서 다른 직원도 주문 현황, 수정된 주문 등을 알 수 있는 것
메모리 배리어를 사용하면, 이러한 수정된 정보를 중앙 메모리에 저장, 불러오기를 할 수 있다.
'서버 > 서버 이론' 카테고리의 다른 글
Lock (0) | 2025.03.27 |
---|---|
InterLocked (0) | 2025.03.24 |
캐시 이론 (0) | 2025.03.18 |
쓰레드 (Thread) (0) | 2025.03.03 |
프로세스와 쓰레드 (0) | 2025.03.02 |