Стандартная программа сервера TCP С++, использующая pthreads, привязка, прослушивание и принятие. У меня есть сценарий, по которому сервер заканчивается (read: crashes), когда я убиваю подключенного клиента.
Причиной сбоя является то, что вызов write()
в файле не работает, поэтому программа получает SIGPIPE. И я думаю, это заставляет сервер выйти.
Я подумал: "Конечно, необработанный сигнал означает" выход ", поэтому используйте signal()
:
signal(SIGPIPE, SIG_IGN);
потому что, взятый из man 2 write
:
EPIPE fd подключается к трубе или гнезду, конец считывания которого закрыт. Когда это произойдет, процесс записи также получит сигнал SIGPIPE. (Таким образом, значение возврата записи видно только в том случае, если программа ловит, блокирует или игнорирует этот сигнал.)
Увы, нет. Ни в потоке сервера, ни в клиентских потоках это не помогает.
Итак, , как я могу предотвратить вызов write()
от повышения этого сигнала или (чтобы быть прагматичным), как остановить сервер от выхода.
Моя диагностика:
- начальный поток сервера, привязка, прослушивание, прием.
- позвольте клиенту подключиться (например, через telnet)
- отправить
pkill telnet
, чтобы свернуть клиент.
нежелательное поведение: выходы сервера, в gdb с
... in write () at ../sysdeps/unix/syscall-template.S:82
82 T_PSEUDO (SYSCALL_SYMBOL, SYSCALL_NAME, SYSCALL_NARGS)
и backtrace:
#0 ... in write () at ../sysdeps/unix/syscall-template.S:82
#1 ... in ClientHandler::mesg(std::string) ()
#2 ... in ClientHandler::handle() ()
#3 ... in start_thread (arg=<value optimized out>) at pthread_create.c:300
#4 ... in clone () at ../sysdeps/unix/sysv/linux/x86_64/clone.S:112
#5 ... in ?? ()