본문 바로가기
프로그래밍/MFC

MFC에서 Thread 사용하기

by 머니테크리더 2023. 10. 4.
반응형

MFC에서 Thread 사용하기
MFC에서 Thread 사용하기

 

🔖 INDEX

     

     

    MFC (Microsoft Foundation Class Library)에서의 스레드 처리는 주로 CWinThread 클래스를 기반으로 합니다. MFC를 사용하여 멀티 스레딩 애플리케이션을 개발할 때 알아야 할 주요 개념과 방법에 대해 설명하겠습니다.

    CWinThread 클래스

    CWinThread는 MFC (Microsoft Foundation Class) 라이브러리에서 제공하는 스레드 관리 클래스입니다. 이 클래스는 Windows 스레드와 관련된 다양한 기능을 제공하여 Windows 프로그래밍에서 멀티스레딩 작업을 더 쉽게 만들어줍니다.

     

    주요 멤버 변수

    CWinThread 클래스의 멤버 변수들은 해당 스레드와 관련된 다양한 정보와 자원을 나타냅니다. 아래는 CWinThread에서 사용되는 주요 멤버 변수들에 대한 설명입니다.

     

    m_hThread

    • 타입: HANDLE
    • 설명: 현재 CWinThread 객체에 연결된 Windows 스레드의 핸들을 나타냅니다. 이 핸들을 사용하면 Windows API 함수들을 직접 호출하여 스레드에 대한 작업을 수행할 수 있습니다.

     

    m_nThreadID

    • 타입: DWORD
    • 설명: 현재 스레드의 ID를 나타냅니다. 스레드 ID는 시스템 내에서 스레드를 유일하게 식별하는 데 사용됩니다.

     

    m_pMainWnd

    • 타입: CWnd*
    • 설명: 스레드의 주 창을 가리키는 포인터입니다. UI 스레드에서만 유효하며, 작업 스레드에서는 nullptr 값을 가집니다. 이 변수를 사용하면 스레드의 주 창에 메시지를 보내거나 그와 관련된 작업을 수행할 수 있습니다.

     

    m_bAutoDelete

    • 타입: BOOL
    • 설명: 스레드 객체가 자동으로 삭제되어야 하는지의 여부를 지정합니다. TRUE로 설정된 경우, 스레드가 종료되면 객체가 자동으로 삭제됩니다.

    이 외에도 CWinThread는 다양한 내부 멤버 변수를 포함하고 있습니다. 그러나 위에 나열된 변수들은 CWinThread를 사용하는 개발자가 일반적으로 사용하게 될 주요 변수들입니다.

     

    주요 멤버 함수

    CWinThread 클래스의 주요 멤버 함수들은 스레드의 생성, 제어 및 관리에 관련된 다양한 기능을 제공합니다. 아래에 이들 함수에 대한 더 자세한 설명을 제공하겠습니다.

     

    CreateThread()

    • 기능: 스레드를 생성하고 실행시킵니다.
    • 인자:
      • dwCreateFlags: 스레드의 생성 플래그입니다. 일반적으로 0을 사용하며, CREATE_SUSPENDED를 사용하여 스레드를 일시 중지 상태로 생성할 수도 있습니다.
      • nStackSize: 스레드 스택의 크기를 지정합니다. 일반적으로 0을 사용하여 기본 크기를 사용합니다.
    • 반환 값: 성공 시 TRUE, 실패 시 FALSE.

     

    ExitInstance()

    • 기능: 스레드의 인스턴스를 종료하고 리소스를 정리합니다. 주로 오버라이드하여 추가적인 정리 작업을 수행합니다.
    • 반환 값: 종료 코드. 일반적으로 0을 반환합니다.

     

    PostThreadMessage()

    • 기능: 스레드의 메시지 큐에 메시지를 게시합니다. 이 메서드는 UI 스레드에 메시지를 보낼 때 주로 사용됩니다.
    • 인자:
      • message: 메시지 ID.
      • wParam: 메시지와 함께 전달할 첫 번째 매개변수.
      • lParam: 메시지와 함께 전달할 두 번째 매개변수.
    • 반환 값: 메시지 게시 성공 시 TRUE, 실패 시 FALSE.

     

     

    SuspendThread()

    • 기능: 스레드를 일시 중지합니다.
    • 반환 값: 성공 시 스레드의 이전 중지 개수, 실패 시 -1.

     

    ResumeThread()

    • 기능: 일시 중지된 스레드를 재개합니다.
    • 반환 값: 성공 시 스레드의 이전 중지 개수, 실패 시 -1.

     

    InitInstance()

    • 기능: 스레드의 인스턴스를 초기화합니다. 대부분의 CWinThread 파생 클래스에서 이 함수를 오버라이드하여 초기화 코드를 제공합니다.
    • 반환 값: 초기화가 성공적으로 수행되면 TRUE, 실패하면 FALSE를 반환합니다.

     

    이러한 함수들은 CWinThread 객체의 생명 주기 동안 스레드의 생성, 제어 및 종료에 필요한 주요 동작을 수행하는 데 사용됩니다. 이 외에도 CWinThread는 스레드와 관련된 여러 다른 메서드를 제공하지만, 위의 목록은 가장 일반적으로 사용되는 핵심 함수들을 나열한 것입니다.

     

    CWinThread의 상태 변화

    CWinThread의 상태 변화는 스레드의 생명 주기 동안 발생하는 다양한 상태와 그 상태 사이의 전환을 나타냅니다. 이 상태들은 스레드의 현재 동작 및 상태를 반영하며, 이러한 상태 변화는 주로 CWinThread 클래스의 멤버 함수를 사용하여 제어됩니다.

     

    Not Started (시작되지 않음)

    • 스레드 객체는 생성되었지만 아직 시작되지 않았습니다.
    • 이 상태는 CWinThread 객체가 인스턴스화되었지만 CreateThread() 함수가 아직 호출되지 않았을 때 발생합니다.

     

    Running (실행 중)

    • 스레드가 실행 중이며 할당된 작업을 처리하고 있습니다.
    • CreateThread() 함수가 호출되면 이 상태로 전환됩니다.
    • SuspendThread() 함수를 호출하여 이 상태에서 "Suspended" 상태로 전환할 수 있습니다.

     

    Suspended (일시 중지)

    • 스레드는 일시적으로 작업을 중단하였습니다.
    • SuspendThread() 함수를 호출하여 스레드를 이 상태로 만들 수 있습니다.
    • ResumeThread() 함수를 호출하여 "Running" 상태로 다시 전환할 수 있습니다.

     

    Terminated (종료됨)

    • 스레드의 작업이 완료되었거나 스레드가 강제로 종료되었습니다.
    • 스레드 함수가 종료될 때, PostQuitMessage()나 스레드에 WM_QUIT 메시지가 전송되면 이 상태로 전환됩니다.
    • 스레드가 이 상태로 전환되면 더 이상 재시작할 수 없습니다. 새로운 작업을 시작하려면 새 스레드를 생성해야 합니다.

     

    이러한 상태는 CWinThread의 생명 주기와 밀접하게 연관되어 있습니다. 스레드의 상태 변화는 특히 멀티스레딩 환경에서 여러 스레드를 동시에 관리하고 제어할 필요가 있을 때 중요한 역할을 합니다. 이를 통해 스레드의 동시 실행, 일시 중지, 재개 및 종료와 같은 주요 작업을 효과적으로 수행할 수 있습니다.

     

     

    스레드 생성 방법

    MFC에서 스레드를 생성하는 주요 방법은 두 가지입니다.

     

    Worker Thread

    AfxBeginThread 함수를 사용하여 작업 스레드를 생성합니다.

    UINT MyThreadProc(LPVOID pParam) {
        // 스레드 코드
        return 0;
    }
    
    void SomeFunction() {
        AfxBeginThread(MyThreadProc, NULL);
    }

     

    User Interface (UI) Thread

    CWinThread 파생 클래스를 사용하여 UI 스레드를 생성합니다. UI 스레드는 메시지 루프를 가지며, GUI와 상호작용이 가능합니다.

    class MyThread : public CWinThread {
    public:
        MyThread() {}
        virtual BOOL InitInstance() {
            // 초기화 코드
            return TRUE;
        }
    };
    
    void SomeFunction() {
        MyThread* pThread = new MyThread();
        pThread->CreateThread();
    }

     

    스레드 동기화

    멀티 스레딩 환경에서는 여러 스레드가 동시에 자원에 액세스할 때 문제가 발생할 수 있으므로 동기화가 중요합니다. MFC는 여러 동기화 메커니즘을 제공합니다.

    • CCriticalSection: 임계 영역을 표현하며, 한 번에 하나의 스레드만 이 영역의 코드를 실행할 수 있습니다.
    • CMutex: 여러 프로세스 간에도 사용할 수 있는 뮤텍스를 제공합니다.
    • CSemaphore: 세마포어를 사용하여 리소스에 대한 동시 액세스 수를 제한합니다.
    • CEvent: 이벤트를 사용하여 스레드 간의 통신을 할 수 있습니다.

     

    스레드 종료 및 자원 정리

    스레드가 더 이상 필요하지 않을 때는 적절하게 종료하고 관련 리소스를 해제해야 합니다.

    • Worker Thread: AfxEndThread 함수를 사용하여 스레드를 종료합니다.
    • UI Thread: PostThreadMessage(WM_QUIT, 0, 0)를 사용하여 메시지 루프를 종료하고 스레드를 종료합니다.

     

     

    댓글