netcat-4.0.20100420-alt1 В случае, если в качестве stdin передаётся pipe, и затем все дескрипторы для записи закрываются, netcat зацикливается, пока не будет закрыто сетевое соединение: 17160 poll([{fd=3, events=POLLIN}, {fd=0, events=POLLIN}], 2, -1) = 1 ([{fd=0, revents=POLLHUP}]) 17160 poll([{fd=3, events=POLLIN}, {fd=0, events=POLLIN}], 2, -1) = 1 ([{fd=0, revents=POLLHUP}]) 17160 poll([{fd=3, events=POLLIN}, {fd=0, events=POLLIN}], 2, -1) = 1 ([{fd=0, revents=POLLHUP}]) ... (при отсутствии активности сетевого соединения продолжается бесконечно) (после закрытия сокета с другой стороны) 17160 poll([{fd=3, events=POLLIN}, {fd=0, events=POLLIN}], 2, -1) = 2 ([{fd=3, revents=POLLIN}, {fd=0, revents=POLLHUP}]) 17160 read(3, "", 2048) = 0 17160 shutdown(3, 0 /* receive */) = 0 17160 close(3) = 0 17160 exit_group(0) = ? Наблюдать это можно, например, при использовании ssh $host nc 127.0.0.1 $port; после этого нормальное закрытие входного потока ssh приводит к зацикливанию nc, причём данные в противоположном направлении в этом состоянии продолжают проходить. Такой вызов nc через ssh используется в libvirt (virt-manager, virt-viewer) для соединения с VNC-сервером qemu при подключении qemu+ssh://, в результате на сервере остаются висеть процессы nc, потребляющие процессорное время. (Для основного соединения с сокетом libvirtd в нормальной ситуации эта проблема не наблюдается из-за наличия в протоколе явной команды закрытия соединения, в результате nc завершает работу при закрытии сокета со стороны libvirtd.) В Linux для pipe или fifo в случае, если все дескрипторы для записи закрыты, и при этом в буфере нет данных, poll() возвращает для дескриптора чтения флаг POLLHUP без установки флага POLLIN; однако netcat не проверяет флаг POLLHUP - видимо, поведение ядра OpenBSD в такой ситуации отличается от Linux (похоже, там по EOF выставляется и POLLIN|POLLRDNORM). В Fedora подобная проблема была починена ещё в 2005 году: https://bugzilla.redhat.com/show_bug.cgi?id=156835 В январе 2010 года была попытка протолкнуть в апстрим патчи, среди которых был и чинящий обработку POLLHUP, но ответа не последовало: http://kerneltrap.org/mailarchive/openbsd-tech/2010/1/12/6700583 http://jzeleny.fedorapeople.org/patches/nc/01-pollhup.patch
PID USER PR NI VIRT RES SHR S %CPU %MEM TIME+ COMMAND 27097 stanv 20 0 8556 724 596 R 99.7 0.0 0:06.36 nc 27080 stanv 20 0 6324 456 356 R 92.1 0.0 0:05.92 nc
Дима, очень нужно исправление этой ошибки.
netcat-4.0.20100725-alt1 -> sisyphus: * Thu Dec 09 2010 Dmitry V. Levin <ldv@altlinux> 4.0.20100725-alt1 - Updated to 20100725 snapshot. - Imported a POLLHUP detection patch by Jan Zeleny (closes: #24657).