thread programming

posix thread 와 관련하여 signal handling을 해야하는 일이 있어서... 

(뭐.. 정확히는 data handling하는 부분에 있어서 thread로 동작시 강제 종료할 경우 data가 틀어지는 문제가 있어서... 흑..ㅠㅠ)


기존의 sigprocmask대신에 pthread_sigmask를 사용하는데.. 새로 알게 된 사실들....


1. thread 생성 이전에 signal 을 설정해줘야 한다...


아래의 sample code에서와 같이 SIG_BLOCK을 thread 생성전에 해줘야 thread에서 해당 signal 이 block된다...

심지어.. thread 생성전에 signal을 설정해줘도.. SIG_UNBLOCK을 해두면.. 무효.. -_-


2. pthread_sigmask라고 해도.. thread별로 signal을 받는게 아니므로.. 큰 의미는 모르겠음.. -_-;;


아래 샘플코드는 테스트한 내용을 전부 해둔거라 지저분하지만.. 뭐.. 언젠가 또 볼일이 있을지도...ㅋ


결론: thread로 바꿀시에는 심각하게 signal이라던가.. variable등을 심각하게 고려해 concurrency control에 문제가 없는지 다시 한번 고민해볼지어다..ㅠㅠ


<1>


#include <stdio.h>
#include <signal.h>
#include <pthread.h>

#include <time.h>

sigset_t mdgBset, mdgOset;

void *sub(void)
{
char tmp[1024];

sigset_t newmask;
struct timespec st;

sigemptyset(&newmask);
sigaddset(&newmask, SIGINT);
#if 1
pthread_sigmask(SIG_UNBLOCK, &newmask, 0);
#if 0
if(pthread_sigmask(SIG_BLOCK, &mdgBset, 0) != 0)
fprintf(stderr, "[%s: %d]\n", __FILE__, __LINE__);
#endif
printf("yo man~!\n");
fgets(tmp, sizeof(tmp), stdin);

pthread_sigmask(SIG_BLOCK, &newmask, 0);

st.tv_sec = 3;
st.tv_nsec = 0;
printf("end man~!\n");
fgets(tmp, sizeof(tmp), stdin);
//nanosleep(&st, NULL);
#if 0
if(pthread_sigmask(SIG_SETMASK, &mdgOset, 0) != 0)
fprintf(stderr, "[%s: %d]\n", __FILE__, __LINE__);
#endif
printf("done man~!\n");
fgets(tmp, sizeof(tmp), stdin);
pthread_sigmask(SIG_UNBLOCK, &newmask, 0);
printf("restart man~!\n");
fgets(tmp, sizeof(tmp), stdin);
#else
sigprocmask(SIG_UNBLOCK, &newmask, 0);
#if 0
if(pthread_sigmask(SIG_BLOCK, &mdgBset, 0) != 0)
fprintf(stderr, "[%s: %d]\n", __FILE__, __LINE__);
#endif
printf("yo man~!\n");
fgets(tmp, sizeof(tmp), stdin);

sigprocmask(SIG_BLOCK, &newmask, 0);
printf("end man~!\n");
fgets(tmp, sizeof(tmp), stdin);
#if 0
if(pthread_sigmask(SIG_SETMASK, &mdgOset, 0) != 0)
fprintf(stderr, "[%s: %d]\n", __FILE__, __LINE__);
#endif
printf("done man~!\n");
fgets(tmp, sizeof(tmp), stdin);
sigprocmask(SIG_UNBLOCK, &newmask, 0);
printf("restart man~!\n");
fgets(tmp, sizeof(tmp), stdin);

#endif
}

void sub_set()
{
sigemptyset(&mdgBset);
sigaddset(&mdgBset, SIGINT);
#if 1
if(pthread_sigmask(SIG_SETMASK, &mdgBset, &mdgOset) != 0)
{
fprintf(stderr, "[%s: %d]\n", __FILE__, __LINE__);
}
if(pthread_sigmask(SIG_SETMASK, &mdgOset, 0) != 0)
{
fprintf(stderr, "[%s: %d]\n", __FILE__, __LINE__);
}
#if 1
if(pthread_sigmask(SIG_BLOCK, &mdgBset, 0) != 0)
fprintf(stderr, "[%s: %d]\n", __FILE__, __LINE__);
// pthread_sigmask(SIG_UNBLOCK, &mdgBset, 0);
#endif
#else
sigprocmask(SIG_SETMASK, &mdgBset, &mdgOset);
sigprocmask(SIG_SETMASK, &mdgOset, NULL);
sigprocmask(SIG_BLOCK, &mdgBset, NULL);
// sigprocmask(SIG_SETMASK, &mdgOset, NULL);
#endif
}

int main(int argc, char* argv[])
{
pthread_t tid[4];
int iIdx;

sub_set();
// pthread_sigmask(SIG_UNBLOCK, &mdgBset, 0);
#if 1
for(iIdx = 0; iIdx < 1; iIdx++)
pthread_create(&tid[iIdx], NULL, sub, NULL);

for(iIdx = 0; iIdx < 1; iIdx++)
pthread_join(tid[iIdx], NULL);
#else
sub();
#endif
}



이 글과 관련있는 글을 자동검색한 결과입니다 [?]

by 아비숑 | 2009/10/22 18:00 | IT Life | 트랙백 | 덧글(1)

트랙백 주소 : http://mirr187.egloos.com/tb/2461493
☞ 내 이글루에 이 글과 관련된 글 쓰기 (트랙백 보내기) [도움말]
Commented at 2009/10/23 16:18
비공개 덧글입니다.

:         :

:

비공개 덧글

◀ 이전 페이지          다음 페이지 ▶



'="text/javascript" src="http://allblet2.allblog.net/allblet2.js">
이글루링크 취소