iOS.OSAtomic
7734 단어 atomic
다중 루틴 코드를 작성하는 데 가장 중요한 것은 공유 데이터에 대한 접근을 잠그는 것이다.
Shared data is any data which more than one thread can access.
Atomic Operations(Atomic Operations)는 Shared 데이터에 액세스할 수 있는 스레드가 하나인 동시에 잠금을 해제할 필요가 없습니다.
원자 조작 중의'원자'는 분할할 수 없다는 뜻이다.
OSAtomic은 OS X의 원자 운용 라이브러리입니다.
2. OSAtomic
OSAtomic 함수는 OSAtomic에 있습니다.h 파일의 경로:/usr/include/libkern/OSAtomic.h
OSAtomic 함수는 사용자 도메인의 코드에서도 사용할 수 있습니다.
#import <libkern/OSAtomic.h>
이러한 방법은 5가지로 나뉜다.
정수 유형
"Due to the finnicky and low-level nature of atomic operations, there are significant limits on data types
and alignments. Atomic operations are only available for 32-bit and 64-bit data types, and on some
platforms (PowerPC being the only OS X one that I know of) they are only available for 32-bit. Always
use data types with a guaranteed size, such as
int32_t
, rather than built-in types ilke int
. " Ref[1] 주소 정렬
"The values must also be aligned to their size. This means that the address of the value has to be
a multiple of the value's size. "Ref[1]
"Alignment should only be a worry if you're messing around with addresses trying to set up your own
packing or using packed structs. And, well, don't use atomic operations with those."Ref[1]
2.1 Integer Operations(정수 작업)
x += 1;//이 조작은 원자가 아니다
x++;//원자도 아니에요.
OSAtomicAdd32()
OSAtomicIncrement()
OSAtomicDecrement()
OSAtomicOr() OSAtomicAnd() OSAtomicXor()
2.2 기본 작업
정수 조작의 개념은 기본적인 원자 조작인 compare and swap, 즉 CAS를 바탕으로 한다.
CAS 함수는 old value, new value, a pointer to a variable의 3개 매개변수를 수락합니다.
만약variable의 값이oldvalue와 일치한다면 newvalue를variable에 부여하고true로 되돌려줍니다.
CAS는 다음과 같습니다.
bool CompareAndSwap(int old, int new, int *value)
{
if(*value == old)
{
*value = new;
return true;
}
else
return false;
}
" If the new value is assigned and the function returns
true
then you can be absolutely certain that the value transitioned directly from
old
to new
without any other intermediate value."Ref[1] OSAtomic은 OSAtomicCompareAndSwap 함수족을 제공합니다.
CAS를 사용하여 OSAtomicAdd32 함수를 구현합니다.
"First, fetch the original value. Then add to obtain a new value. Finally, use compare and swap
with the original and new values. If it failed, go back and try everything again."Ref[1]
int32_t OSAtomicAdd32(int32_t howmuch, volatile int32_t *value)
{
bool success;
int32_t new;
do {
int32_t orig = *value;
new = orig + howmuch;
success = OSAtomicCompareAndSwap32(orig, new, value);
} while(!success);
return new;
}
TODO:키워드volatile
OSAtomicCompareAndSwapPtrBarrier() 함수 사용:
void AddNode(ListNode *node, ListNode * volatile *head)
{
bool success;
do {
ListNode *orig = *head;
node->next = orig;
success = OSAtomicCompareAndSwapPtrBarrier(orig, node, (void *)head);
} while(!success);
}
ListNode *StealList(ListNode * volatile *head)
{
bool success;
ListNode *orig;
do {
orig = *head;
success = OSAtomicCompareAndSwapPtrBarrier(orig, NULL, (void *)head);
} while(!success);
return orig;
}
"This kind of structure can be really useful in multithreaded programming. Many threads can safely
use
AddNode
to add new nodes to the structure. A worker thread can then use StealList
to grab the list and process it."Ref[1]
ABA Problem(ABA 질문)
ABA 관련 질문 참조: TODO
Ref[1] ABA Problem 이 섹션은 명료하게 설명되어 있습니다.
2.3 Spinlocks(자전거 잠금)
"A spinlock is a primitive type of lock that does not use any OS facilities."Ref[1]
일반 자물쇠의 개념:
"A lock in general is a facility which provides mutual exclusion between threads.
Two threads attempt to acquire a lock. One succeeds, the other waits. When the first one unlocks the lock,
the second one then acquires it.
Generally, when the second thread is waiting, we want it to be blocked so that it does not take any CPU
time while it's blocked. This requires intervention by the OS to stop the thread, and start it again when unlocking.
This OS intervention comes with a certain amount of overhead that is not always desirable. "Ref[1]
일반 잠금은 시스템 OS의 개입이 필요합니다.
Spinlock의 개념:
Spinlock은 가볍고 OS 개입이 필요 없는 사용자 공간에 있습니다.부작용은 라인이waiting에 있을 때 이 라인은blocked가 되지 않습니다.
unlocked까지 끊임없이 spinlock을 검사합니다.
"Spinlocks perform very well when a lock is not contended (only one thread at a time is accessing it)
but perform poorly when a lock is contended for an extended period."Ref[1]
TODO: 그럼 스핀록을 적용한 장면은 뭘까요?
You should generally use those higher-level (pthread_mutex, NSLock) abstractions, but spin locks are useful when performance
is absolutely critical and contention is rare.
2.4 Queues
"Unfortunately, after some additional investigation, I discovered that
OSQueue
is not entirely thread safe and thus should not be used. Since I have no idea if or
when this will be fixed, you should avoid the use of
OSQueue
." Ref[1] TODO: OSQueue의 조사 연구
2.5 메모리 장벽, 메모리 장벽
"Some architectures reorder memory reads and writes for extra speed.
These reorderings are hidden from the program by the CPU, but they are not hidden
from code executing on other CPUs at the same time. This can cause serious problems."Ref[1]
Memory Barries의 역할:
"A memory barrier forces all all reads before the barrier to complete before any
reads after the barrier complete. The same goes for writes. Technically, there can be
separate barriers for reads and writes, but OSAtomic rolls them both into a single concept."
TODO: OSMemoryBarrier의 예를 사용합니다.
Reference
1. Friday Q&A 2011-03-04: A Tour of OSAtomic (AAAAA)
https://www.mikeash.com/pyblog/friday-qa-2011-03-04-a-tour-of-osatomic.html
2.
http://cocoadev.com/OSAtomic
3. 자전거 자물쇠spinlock 분석 및 개선 (읽지 않음)
http://kb.cnblogs.com/page/105657/
이 내용에 흥미가 있습니까?
현재 기사가 여러분의 문제를 해결하지 못하는 경우 AI 엔진은 머신러닝 분석(스마트 모델이 방금 만들어져 부정확한 경우가 있을 수 있음)을 통해 가장 유사한 기사를 추천합니다:
[Atomic C++] 시작하기저는 ubuntu 리눅스 환경을 사용하고 있습니다. cli 환경에서 g++을 이용해서 컴파일을 하지 않고 VScode, CLion과 같은 IDE를 사용하여 프로그래밍을 하고 있습니다. 다음 명령어로 thread를 사...
텍스트를 자유롭게 공유하거나 복사할 수 있습니다.하지만 이 문서의 URL은 참조 URL로 남겨 두십시오.
CC BY-SA 2.5, CC BY-SA 3.0 및 CC BY-SA 4.0에 따라 라이센스가 부여됩니다.