문제

내 시절에 Beos 프로그래머로 돌아와서 읽었어요 이 기사 Benoit Schillings에 의해 "Benaphore"를 만드는 방법을 설명합니다. Atomic 변수를 사용하여 공통 (No-Contention) 사례에서 뮤트를 획득/해제하는 중요한 섹션을 시행하는 방법.

나는 그것이 다소 영리하다고 생각했고, 원자 증가/감소를 지원하는 모든 플랫폼에서 동일한 트릭을 수행 할 수있는 것처럼 보입니다.

반면에 이것은 표준 Mutex 구현 자체에 쉽게 포함될 수있는 것처럼 보입니다.이 경우 내 프로그램 에서이 논리를 구현하는 것은 중복되어 어떤 이점도 제공하지 않습니다.

현대식 잠금 API (예 : pthread_mutex_lock ()/pthread_mutex_unlock ()) 이이 트릭을 내부적으로 사용하는지 아는 사람이 있습니까? 그리고 그렇지 않다면 왜 그렇지 않습니까?

도움이 되었습니까?

해결책

기사가 설명하는 것은 오늘날 일반적으로 사용됩니다. 가장 자주 그것은 "이라고 불립니다"중요한 섹션"그리고 그것은 인터 로크 변수, 많은 플래그 및 내부 동기화 객체 (MUTEX, 정확하게 기억한다면)로 구성됩니다. 일반적으로 경합이 거의없는 시나리오에서 중요한 섹션은 커널을 포함하지 않고 사용자 모드에서 완전히 실행됩니다. 동기화 객체. 이것은 빠른 실행을 보장합니다. 경합이 높으면 커널 객체가 대기에 사용되며, 이는 더 빠른 전환을 위해 시간 슬라이스 전도성을 방출합니다.

일반적 으로이 시대와 시대에 동기화 프리미티브를 구현하는 데는 의미가 거의 없습니다. 운영 체제에는 이러한 객체가 다양한 객체가 제공되며 단일 프로그래머가 상상할 수있는 것보다 훨씬 더 넓은 범위의 시나리오에서 최적화되고 테스트됩니다. 문자 그대로 좋은 동기화 메커니즘을 발명, 구현 및 테스트하는 데 몇 년이 걸립니다. 그것은 시도하는 데 가치가 없다고 말하는 것은 아닙니다. :)

다른 팁

Java 's AbstractQueuedSynchronizer (그리고 그 형제 AbstractQueuedLongSynchronizer)도 비슷하게 작동하거나 적어도 작동합니다 ~할 수 있었다 비슷하게 구현됩니다. 이러한 유형은 Java 라이브러리의 여러 동시성 프리미티브의 기초를 형성합니다. ReentrantLock 그리고 FutureTask.

상태를 나타내는 원자 정수를 사용하여 작동합니다. 잠금은 값 0을 잠금 해제 된 것으로 정의하고 1은 잠긴 것으로 정의 할 수 있습니다. 잠금을 획득하려는 모든 스레드는 원자력을 통해 잠금 상태를 0에서 1으로 변경하려고 시도합니다. 비교-세트 작업; 시도가 실패하면 현재 상태는 0이 아니므로 잠금이 다른 스레드가 소유하고 있음을 의미합니다.

AbstractQueuedSynchronizer 또한 자물쇠를 기다리고 알림을 기다립니다 정황 유지함으로써 CLH 대기열, 잠금 장치를 통해 잠금을 획득하거나 조건을 통해 알림을 받기 위해 대기하는 스레드 라인을 나타내는 잠금이없는 링크 목록입니다. 이러한 알림은 조건에서 대기하는 스레드 중 하나 또는 전부를 관련 잠금을 획득하기를 기다리는 사람들의 대기열의 헤드로 이동합니다.

대부분 이 기계는 상태를 나타내는 원자 정수와 각 대기 대기열에 대한 몇 가지 원자 포인터로 구현 될 수 있습니다. 스레드의 실제 스케줄링은 상태 변수를 검사하고 변경하기 위해 경쟁합니다 (예 : AbstractQueuedSynchronizer#tryAcquire(int))는 그러한 라이브러리의 범위를 벗어나 호스트 시스템의 스케줄러로 떨어집니다.

라이센스 : CC-BY-SA ~와 함께 속성
제휴하지 않습니다 StackOverflow
scroll top