1. 대화상자 기반의 새 프로젝트

 

2. 버튼 세개 추가

캡션 변경(Begin Thread1, Begin Thread2, Call GetString()

 

3. 이벤트 핸들러 추가. ThreadCrashDlg.cpp에 코드 작성

 

4. stdafx.cpp에 전역변수 선언

CCriticalSection g_CS;
TCHAR* g_pszBuffer = NULL; // 널종료 문자열, 문자 한자를 임시로 대기시키기 위한 공간

 

void SetString(TCHAR* pszData)
{
     // g_CS.Lock();
     int nLength = lstrlen(pszData)+1;  // 문자열의 길이값을 받아와서 기존의 값에 +1
     if(g_pszBuffer != NULL)
          free(g_pszBuffer);

 

     g_pszBuffer = (TCHAR*)malloc(sizeof(TCHAR)*nLength);
     swprintf_s(g_pszBuffer, nLength, TEXT("%s"), pszData);

 

     // g_CS.Unlock();

}

 

BOOL GetString(TCHAR* pszData)
{
     // g_CS.Lock();
 

     if(pszData != NULL && g_pszBuffer != NULL)
     {
          int nLength = lstrlen(g_pszBuffer);
          swprintf_s(pszData, nLength+1, TEXT("%s"), g_pszBuffer);
  

         // g_CS.Unlock();
  

         return FALSE;
     }
 

     // g_CS.Unlock();
     return TRUE;
}

 

g_CS.Lock() // 외부 스레드가 이 데이터에 접근하는 것을 막음

g_CS.Unlock() //

 

SetString->트랜젝션 하는 것

GetString->리트리브 하는 것(데이터를 얻는것)

트랜젝션: (프로그래밍)데이터를 쓰거나 지우거나 삭제하거나 수정하거나 생성하는 행위

 

5. stdafx.cpp에 스레드문 작성

UINT ThreadFunc1(LPVOID pParam)
{
     while(TRUE)
     {
          ::Sleep(1);
          SetString(TEXT("ThreadFun1"));
     }
 return 0;
}

 

UINT ThreadFunc2(LPVOID pParam)
{
     while(TRUE)
     {
          ::Sleep(1);
          SetString((TEXT("ThreadFun2")));
     }
     return 0;
}

6.stdafx.h파일에 원형 선언

extern TCHAR* g_pszBuffer;

 

void SetString(TCHAR* pszData);
BOOL GetString(TCHAR* pszData);
UINT ThreadFunc1(LPVOID pParam);
UINT ThreadFunc2(LPVOID pParam);

 

7. Button3이벤트 처리기 작성

void CThreadCrashDlg::OnBnClickedButton3()
{
     TCHAR szBuffer[64];
     ::ZeroMemory(szBuffer, sizeof(szBuffer));

     if(GetString(szBuffer))
          AfxMessageBox(szBuffer);

}

 

이 코드내에서 Lock/Unlock의 역할

Lock함수 내에서 실제로 Suspend Thread함수가 구현되어 있고,

반대로 Unlock은 Resume Thread로 구현되어 있다.

 

주석처리한 g_CS.Lock/g_CS.Unlock를 풀고 stdafx.h파일에 afxmt.h파일을 인클루드 하고 컴파일하여 실행

Posted by 마마필로 :