2012-06-11 4 views
0

Я использую Epoll построить сервер, это код, в котором я инициализации Epoll:Unix: Epoll, поймать Ctrl + d и CTRL + C в сервере

core->fd_epoll = epoll_create(LIMIT_CLIENT); 
ev.events = EPOLLIN | EPOLLPRI | EPOLLERR | EPOLLHUP; 
ev.data.fd = core->socket_main; 
epoll_ctl(core->fd_epoll, EPOLL_CTL_ADD, core->socket_main, &ev); 
while (1) 
{ 
    nfds = epoll_wait(core->fd_epoll, &ev, 90000, -1); 
    ... 
} 

И когда я использую его, чтобы проверить, есть ли что-то новое на моих FDS:

for (i = 0; i < nfds; i++) 
{ 
    fd = ev[i].data.fd; 
    if (fd == core->socket_main) 
    { 
     socket_fils = socket_accept(core->socket_main, 0); 
     event.data.fd = socket_fils; 
     event.events = EPOLLIN | EPOLLET | EPOLLRDHUP; 
     xepoll_ctl(core->fd_epoll, EPOLL_CTL_ADD, socket_fils, &event); 
     printf("Incoming => FD fils %d\n", socket_fils); 
    } 
    else 
    printf("Event %x\n", ev[i].events); 
} 

Когда я использую Netcat, чтобы отправить сообщение на сервер в битовом события равно 1 (EPOLLIN) Когда я посылаю Ctrl + C, Netcat завершает работу и мои битовый равно до 2001 года (EPOLLIN и EPOLLRDHUP) Когда я отправляю ctrl + d, netcat не уходит, но мой битф ield равно 2001 тоже ...

После ctrl + d мой сервер закрывает сокет. Это не нормально ... Ctrl + D не должен закрывать сокет и возвращать другое битовое поле.

Как узнать, на сервере, если это ctrl + c или ctrl + d?

спасибо.

ответ

3

ctrl + c и ctrl + d keypress на терминале, который запускает netcat, не могут быть «видимы» непосредственно вашим сервером. Они вызывают, соответственно, сигнал SIGINT для отправки в netcat и условие EOF, которое будет видно netcat на его stdin. То, что netcat делает с этим, действительно зависит от netcat, а не от вашего сервера. Вот что они делают для меня:

  • CTRL + C, которая посылает SIGINT на NetCat: Netcat убит, потому что это действие по умолчанию SIGINT и Netcat не меняет его. Когда netcat умирает, розетка автоматически закрывается. Сервер воспринимает это как доступные входящие данные, соответствующие состоянию EPOLLIN|EPOLLRDHUP, которое вы видите. Если вы прочитаете сокет, вы обнаружите, что EOF ждет вас.

  • ctrl + d, который посылает EOF на stdin netcat: netcat заметил EOF. Он не будет отправлять дополнительные данные через сокет. Тем не менее, он продолжает работать и считывать из сокета, если у сервера больше данных для отправки.

Другими словами, я не могу воспроизвести поведение NetCat вы видите (с Linux 2.6 и NetCat v1.10-38). Возможно, ваша версия netcat отключает сокет для записи после прочтения EOF на stdin?

+0

Я не знаю, как увидеть версию Netcat (без опции --version) Но я вижу в человеке: > Соединение может быть прекращено с помощью EOF («^ D»). Итак, это нормально? Разница между ctrl + c и ctrl + d заключается в том, что netcat ждет входящих данных при возникновении ctrl + d и закрывает сокет как ctrl + c? –

+0

Похоже, это так, да. – Celada

+0

Вы можете использовать telnet вместо netcat. Он отправляет символ^D (0x04) для Ctrl-D. –

Смежные вопросы