728x90
더보기

「Linux, system call, operating system, asynchronus programming, 비동기 프로그래밍


오늘은 학교 과제하다가 잘 복습해두고픈 내용이 있어서 써본다

Linux system programming 수업에서 요즘 Signal 부분 과제를 하고있다...

오늘 실습한 코드는signal(알람수신자) 과 alarm(알람발신자) 을 사용해서 동기적 프로그래밍하기!

나를 혼란스럽게 했던 내용...
* signal 은 signal 보내는게 아니라 받는 함수다 ㅡㅡ .... 진짜 넘하지않냐....
* 뭐..안넣어도 세상이 워낙 좋아 컴파일이 되긴했지만 alarm 사용을 위해 unistd.h 헤더 포함시켜주기...
*signal인터페이스

typedef void (*sighandler_t)(int);
sighandler_t signal(int signum, sighandler_t handler);

첫번째 인자 signum 은 MACRO를 사용한다 ( SIGINT, SIGBUS,SIGALRM,SIGTERM 등...)
(man signal 참고*)
두번째 인자는 함수 포인터이다... 위 형식에 맞게 함수를 선언하고 넣어주면 된다.

첫번째 인자에 해당하는 signal 을 받으면 두번째 인자의 함수가 실행된다.
default 동작도 있다(무시, 종료 등..)


흐름은....
1. alram signal 을 받았을 때(alarm 함수를 통해 'SIGALRM' 시그널 보냄) 어떤 동작을 수행할지 변경하기위해
SigAlarmHandler 함수를 만든다.(이 함수가 signal 의 두번째 인자, 함수 포인터로 들어간다)
SigAlarmHandler :
여기에는 점을 하나 찍어주는 코드와
signal을 다시 호출하는 코드가 들어간다.
( 여기에서 또 두번째 인자로 핸들러를 재귀적으로 넣어주는데, 일부 운영체제에서 핸들러는 한 번 수행된 뒤 초기화되기 때문이다...)

2. 최초로 signal 을보낼 setPeriodicAlarm 함수를 선언해준다.
signal함수로 SIGALRM 받았을 시의 Handler를 설정해주고
alarm() 호출! 파라미터는 시간이 들어간다 (unsigned int, 초단위.. )
0이면 pending 중인 모든 알람이 취소된다

3. main 에서 setPeriodic Alarm 을 호출한다...

그러면 다른 동작이 모두 종료될때까지 반복해서 alarm handler 에 등록한 내용이 주기적으로 수행된다.

실습코드

#include <stdlib.h> #include <stdio.h> #include <signal.h> #include <unistd.h> static unsigned int AlarmSecs; // 함수 종료시에도 값 유지되는 전역변수 // static : 다른 파일 접근을 막기 위함 // void SigAlarmHandler(int signo) { // 한 번 호출 후 Hanlder 사라지는 OS가 있으므로 // 재귀적으로 재등록 if( signal(SIGALRM, SigAlarmHandler) == SIG_ERR) { perror("signal"); exit(1); } // 다시 알람 시스템 콜 요청 // 전역변수 사용(함수가 사라지므로) alarm(AlarmSecs); /* DO something */ // 버퍼캐시 바로 flush printf("."); fflush(stdout); return; } int SetPeriodicAlarm(unsigned int nsecs) { if( signal(SIGALRM, SigAlarmHandler) == SIG_ERR) { return -1; } // 정상종료 시 -1 return AlarmSecs = nsecs; alarm(nsecs); return 0; } int main() { int i,j; printf("Doing something every one sec.\n"); // 1초마다 정해진 동작 하는 함수(asynchronus) SetPeriodicAlarm(1); //위 알람과 상관없이 자기 일 하는 코드.. // asynchronuos 함을 더 직접적으로 보기 위해 내맘대로 넣어본 yum! for(i = 0;i < 1000000;i++){ if( i%100000 == 0) printf("\nyum!\n"); for(j = 0; j<20000; j++) {} } return 0; } 67,1 Bot


어마어마한루프는... 일부러 시간끌기용으로 넣어보았다 숫자는 별의미없음

수행결과는 이렇게 나왔당


끝!

참고한것 :학교수업자료, 아오키미네로 「모두를위한 리눅스 프로그래밍」, man alarm

728x90

+ Recent posts