| 일 | 월 | 화 | 수 | 목 | 금 | 토 |
|---|---|---|---|---|---|---|
| 1 | 2 | 3 | 4 | 5 | 6 | 7 |
| 8 | 9 | 10 | 11 | 12 | 13 | 14 |
| 15 | 16 | 17 | 18 | 19 | 20 | 21 |
| 22 | 23 | 24 | 25 | 26 | 27 | 28 |
- FRunnable
- unreal compute shader
- CSS
- FRunnableThread
- render target2d
- JavaScript
- HLSL
- unreal visual studio
- unreal niagara
- Compute Shader
- jquery
- IntersectionObserver
- Riot Games
- niagara.pdb 로드되지 않음
- Agile 게임 개발
- page dot
- unreal niagara with compute shader
- kanban
- unreal compute shader #unreal niagara #unreal #compute shader #unreal niagara with compute shader
- texture render target
- unreal c++ #unreal #unreal build #unreal
- scroll-snap
- render target
- League of Legend
- visual studio integration tool 상태
- hlsl with unreal
- Game Developement
- Unreal
- HTML
- carousel indicator
- Today
- Total
Nephrite21
Unreal 멀티스레딩 : FRunnable, FRunnableThread 본문
언리얼에서 비동기로 작업할 때 사용할 만한 것은 Async, TaskGraph등의 태스크 기반과 FRunnableThread 같은 스레딩 기반이 있다. 이중 Thread를 알아보겠다.
1. 클래스
Unreal에서 멀티스레딩을 할 때 중요한 클래스는 다음 두가지이다

FRunnable은 스레드 상에서 작동해야 하는 작업에 대한 정의를 갖는다.
FRunnableThread는 실제로 Game Thread에서 떨어져 나와 작동할 스레드 자체를 의미한다.
FRunnableThread* thread = new FRunnableThread(FRunnable* runnable, const TCHAR* ThreadName)
스레드의 생성은 위와 같이 실행되고, Thread가 생성되고 나면 FRunnable에 정의된 사용자의 작업이 실행되는 식이다.
2. FRunnable

FRunnable에서 중요한 내용은 Init, Run, Exit, Stop이고, 이곳에 정의된 대로 FRunnableThread에서 실행하게 된다.
- Init
스레드 시작 시 가장 먼저 해야할 작업에 대한 정의를 자유롭게 작성할 수 있다.
스레드를 네트워크 용도로 만들었다면 이곳에서 연결 설정이나 헤더 교환 등을 할 수 있을 것이고, 스레드를 패스파인딩용으로 만들었다면 이곳에서 노드들의 전처리를 진행할 수 있겠다.
반환값은 bool으로, true를 반환하였다면 Run을 실행하고, false였다면 실행하지 않는다. 이를 이용해서 Run을 실행할 수 있는지, 없는지에 대해서 판단하는 것도 가능하다.
- Run
스레드의 실제 작업 부분을 자유롭게 정의하는 공간이다.
스레드를 네트워크 용도로 만들었다면 이곳에서 While문을 이용해 지속적으로 패킷교환이 일어날 것이고, 패스파인딩 용이라면 복잡한 연산을 진행할 것이다.
- Exit
스레드가 종료되기 직전에 실행되는 함수이다.
기존에 정의한 변수들의 정리, 연결 종료 설정 등을 이곳에서 하면 되겠다.
- Stop
Init -> Run -> Exit으로 이어지는 과정에서 벗어나 임의로 이를 종료하고 싶을 때 종료하는 방법에 대해서 정의하는 공간이다.
Run을 다음과 같이 구성했다면
uint32 MyRunnable::Run(){
while(isOn){
//작업
}
return 0;
}
Stop을 다음과 같이 작성하여 종료 요청을 생성할 수 있다.
void MyRunnable::Stop(){
isOn = false;
}
Stop 실행 시 Run의 루프가 종료되고, 자동으로 Exit이 실행되며 스레드가 종료된다.
3. FRunnableThread

FRunnableThread 에서 중요한 것은 상단에 작성한 생성자와 WaitForCompletion이다.
WaitForCompletion은 동기함수로, 기존 스레드에서 실행하여 Thread가 종료되는 것을 보장한다.
위에서와 마찬가지로 Run이 다음과 같이 정의되어있을 때.
uint32 MyRunnable::Run(){ //FRunnableThread 에서 실행됨.
while(isOn){
//매우 무거운 작업
}
return 0;
}
Stop을 이용하여 isOn을 False로 바꾼다고 하더라도 이후에 존재하는 매우 무거운 작업에 의해 Exit이 호출되기까지는 시간이 걸린다.
이를 간과하고 즉시 Thread에 대한 포인터를 제거한다면 생명 주기 관리에 문제가 생길 수 있으므로, 확실히 종료가 될때까지 Gamethread를 멈추는 것이 WaitForCompletion이다.
//임의의 GameThread 상의 코드
Runnable->Stop();
thread->WaitForCompletion();
Stop이 실행되고, Exit이 끝날때 까지 GameThread는 blocking 되어 멈추게 된다.
4. 스레드 구분

위의 내용을 한장으로 정리하면 위와 같다.
GameThread 상에서 thread에 Frunnable을 할당하여 생성하게 되면 FrunnableThread 상에서 Init()을 호출한 후 Run을 실행하게 되고, 이를 GameThread에서 Stop을 통해서 멈추거나, Run이 종료되면 Exit이 실행된다.
WaitForCompletion은 Thread의 종료를 보장하는 동기함수이다.