을 설정하고 당신이 그것을 FDS 때문에 제대로 0, 1을 작동하지 않습니다 터미널에서 실행하려고하면 나는 다음과 같은 예를내가는 epoll을 사용 배우고
#include <assert.h>
#include <errno.h>
#include <fcntl.h>
#include <stdio.h>
#include <stdlib.h>
#include <sys/epoll.h>
#include <unistd.h>
int main() {
int epfd;
struct epoll_event ev;
struct epoll_event ret;
char buf[200];
int n,k,t;
epfd = epoll_create(100);
assert(0 ==
fcntl(0, F_SETFL, fcntl(0, F_GETFL) | O_NONBLOCK)
);
ev.data.fd = 0;
ev.events = EPOLLIN | EPOLLET;
if(epoll_ctl(epfd, EPOLL_CTL_ADD, 0, &ev) != 0)
perror("epoll_ctl");
while((n = epoll_wait(epfd, &ret, 1, -1)) > 0) {
printf("tick!\n");
if(ret.data.fd == 0) {
k=0;
while((t=read(0, buf, 100)) > 0) {
k+=t;
}
if(k == 0) {
close(0);
printf("stdin done\n");
}
}
}
perror("epoll");
return 0;
}
을 쓴 2는 모두 같은 열린 파일을 가리키고 있으므로 close (0)는 epoll 세트에서 stdin을 제거하지 않습니다. "cat | ./a.out"을하면이 문제를 해결할 수 있습니다. 더러운 속임수, 알아, 명명 된 파이프 또는 소켓 작은 예제를 설정하는 것은 더 복잡합니다.
이제 모든 것이 작동하고 파일이 epoll 세트에서 제거되지만 다음 epoll_wait 호출은 빈 세트에 있기 때문에 영구적으로 차단됩니다! 따라서 epoll 파일 설명자 (epfd)가 빈 epoll 세트인지 여부를 감지해야합니다.
어떻게이 문제를 해결할 수 있습니까? (일반적인 방법으로 stdin이 끝났을 때 exit 만 호출하는 것이 아닙니다) 감사합니다!
"제대로 작동하지 않는다"고 말할 때 정확히 무엇을 기대합니까? 'epoll_wait'가 stdin이 닫히고'while' 루프가 종료 된 후에 실패 할 것인가? –
@AustinPhillips ./a.out으로 프로그램을 시작하면. 파일 기술자 0, 1 및 2는 모두 동일한 열린 파일 (터미널)을 참조합니다. 그래서 epoll은 fd가 아닌 열려있는 파일들과 작동하기 때문에 stdin (0)을 닫는 것은 효과가 없습니다. 'man epoll '의 질문 6은이 점을 더 잘 설명합니다. 'cat | ./a.out', 이제 fd 0은 파이프이고 fd의 1과 2는 터미널입니다. – Guido
예상 한 내용을 설명하지 않았습니다. 설명서 페이지의 A6에서 설명하는 것처럼, '파일 설명'에 대한 참조가 더 이상 없을 때 파일 설명자는 epoll 세트에서 제거됩니다. 'close (0)'하면 아마 프로그램에 계속 관심이 없습니다. 이 경우, epoll 세트에서'EPOLL_CTL_DEL' fd 0을 할 수 있고,'epfd'에서 미해결 파일 디스크립터의 수를 세는 카운터를 어딘가에 줄여서 0에 도달하면 프로그램을 종료 할 수 있습니다. –