강좌 & 팁
글 수 2,412
2010.11.26 21:42:45 (*.82.68.231)
58007
프로그램을 작성하다보면
sleep(), usleep() 함수에서 지연을 갖거나 또는 poll() 함수를 통해 timeout을 구현할때가 있다.
만일 프로세스가 이들함수에 의해 자고 있을때 시스템 시간이 현재보다 앞으로 가거나 또는 뒤로 가게되면
이들 함수에서 깨어날수 있을까?
테스트를 해보았다.
프로그램은 sleep()함수를 위한 쓰레드와 usleep() 함수를 위한 쓰레드
그리고 메인함수에서 poll() 함수를 10초간격으로 깨어나게 하였다.
프로그램을 수행한 후 쉘에서 date 유틸리티를 사용하여 시간을 변경하였다.
결론 : 정상적으로 timeout 이 발생하였다. (원했던 결과이다. ㅡ.ㅡ)
시간이 변경되었을때 정확히 10초 이후에 깨어났는지는 확인하지 못했지만 비숫한 시간이 소모된 듯 하다.
아래는 테스트 소스이다.
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
#include <fcntl.h>
#include <unistd.h>
#include <errno.h>
#include <signal.h>
#include <sys/ioctl.h>
#include <sys/time.h>
#include <sys/socket.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <sys/poll.h>
#include <time.h>
#include <pthread.h>
long long get_cur_msec( void )
{
struct timeval mytime;
// 현재 시간을 얻어온다.
gettimeofday(&mytime, NULL);
return (mytime.tv_sec*1000 + mytime.tv_usec/1000);
}
static void *thread_sleep_func( void *data )
{
while(1)
{
sleep(10);
printf( ".. sleep thread msec=%lld\n", get_cur_msec() );
}
return (void *)0;
}
static void *thread_usleep_func( void *data )
{
while(1)
{
usleep(10*1000*1000);
printf( "..usleep thread msec=%lld\n", get_cur_msec() );
}
return (void *)0;
}
//------------------------------------------------------------------------------
/** @brief 메인함수이다.
@remark
*///----------------------------------------------------------------------------
int main( int argc, char **argv )
{
printf( "\n %s ver 0.1.0 \n\n", argv[0]);
{
pthread_t thr_id;
pthread_attr_t thr_attributes;
int thr_status;
// 쓰레드 생성 : 프로세스와 분리
pthread_attr_init( &thr_attributes );
pthread_attr_setdetachstate( &thr_attributes, PTHREAD_CREATE_DETACHED );
thr_status = pthread_create( &thr_id, &thr_attributes, thread_sleep_func, (void *)0 );
if ( thr_status != 0 )
{
perror( "sleep pthread_create() " );
}
// 쓰레드 생성 : 프로세스와 분리
pthread_attr_init( &thr_attributes );
pthread_attr_setdetachstate( &thr_attributes, PTHREAD_CREATE_DETACHED );
thr_status = pthread_create( &thr_id, &thr_attributes, thread_usleep_func, (void *)0 );
if ( thr_status != 0 )
{
perror( "usleep pthread_create() " );
}
}
while(1)
{
int rtn;
struct pollfd poll_fds[4];
rtn = poll( (struct pollfd *)&poll_fds, 0, 10*1000 );
if ( 0 == rtn )
{
printf( "..poll timeout msec=%lld\n", get_cur_msec() );
}
else
{
printf( " what happen!!\n" );
}
}
return 0;
}
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
#include <fcntl.h>
#include <unistd.h>
#include <errno.h>
#include <signal.h>
#include <sys/ioctl.h>
#include <sys/time.h>
#include <sys/socket.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <sys/poll.h>
#include <time.h>
#include <pthread.h>
long long get_cur_msec( void )
{
struct timeval mytime;
// 현재 시간을 얻어온다.
gettimeofday(&mytime, NULL);
return (mytime.tv_sec*1000 + mytime.tv_usec/1000);
}
static void *thread_sleep_func( void *data )
{
while(1)
{
sleep(10);
printf( ".. sleep thread msec=%lld\n", get_cur_msec() );
}
return (void *)0;
}
static void *thread_usleep_func( void *data )
{
while(1)
{
usleep(10*1000*1000);
printf( "..usleep thread msec=%lld\n", get_cur_msec() );
}
return (void *)0;
}
//------------------------------------------------------------------------------
/** @brief 메인함수이다.
@remark
*///----------------------------------------------------------------------------
int main( int argc, char **argv )
{
printf( "\n %s ver 0.1.0 \n\n", argv[0]);
{
pthread_t thr_id;
pthread_attr_t thr_attributes;
int thr_status;
// 쓰레드 생성 : 프로세스와 분리
pthread_attr_init( &thr_attributes );
pthread_attr_setdetachstate( &thr_attributes, PTHREAD_CREATE_DETACHED );
thr_status = pthread_create( &thr_id, &thr_attributes, thread_sleep_func, (void *)0 );
if ( thr_status != 0 )
{
perror( "sleep pthread_create() " );
}
// 쓰레드 생성 : 프로세스와 분리
pthread_attr_init( &thr_attributes );
pthread_attr_setdetachstate( &thr_attributes, PTHREAD_CREATE_DETACHED );
thr_status = pthread_create( &thr_id, &thr_attributes, thread_usleep_func, (void *)0 );
if ( thr_status != 0 )
{
perror( "usleep pthread_create() " );
}
}
while(1)
{
int rtn;
struct pollfd poll_fds[4];
rtn = poll( (struct pollfd *)&poll_fds, 0, 10*1000 );
if ( 0 == rtn )
{
printf( "..poll timeout msec=%lld\n", get_cur_msec() );
}
else
{
printf( " what happen!!\n" );
}
}
return 0;
}
---소스 끝---
아마도 task의 지연은 task의 정보에 tick count가 있어서 매 tick 마다 감소하면서 깨어나기 때문이 아닐까요~