scp hangs if you ask it to copy a named pipe whose other end is closed, rather than printing the "not a regular file" error the way it's supposed to. strace shows that this is because it does open() then fstat(), but doing open() on a closed FIFO hangs. Perhaps it should open with O_NONBLOCK? My open(2) manual page says: "When possible, the file is opened in non-blocking mode. Neither the open nor any subsequent operations on the file descriptor which is returned will cause the calling process to wait." See http://www.opengroup.org/onlinepubs/009695399/functions/open.html for SuSv3/POSIX's description of O_NONBLOCK, which explicitly mentions its behaviour on FIFOs, block specials, and character specials.
The last bit of the description of O_NONBLOCK (after the description of the behaviour with FIFOs and block/char specials) is: "Otherwise, the behavior of O_NONBLOCK is unspecified." Can we rely on all platforms to do something reasonable with O_NONBLOCK on normal files? On the other hand, stat'ing it to find out if it's a FIFO or device first is racy...
Just thought I'd drop in to ask for this bug to be solved and add another vote to solving this bug... I was trying to copy my CrossOver Office config (about 470M worth of data) using scp to another machine configured as follows: The source: kernel 2.6.10 (compiled manually), full-duplex 100Mbps The target: kernel 2.6.8 (from Debian), half-duplex 10 Mbps scp just hang after transferring data for a while. I eventually isolated the problem to a specific directory: $ strace scp -v -r ~/.cxoffice/dotwine/fake_windows/Windows/Temp 142.225.125.203: debug1: Sending command: scp -v -r -t . "\0", 1) = 1 open(".cxoffice/dotwine/fake_windows/Windows/Temp", O_RDONLY|O_LARGEFILE) = 3 fstat64(3, {st_mode=S_IFDIR|0755, st_size=4096, ...}) = 0 open(".cxoffice/dotwine/fake_windows/Windows/Temp", O_RDONLY|O_NONBLOCK|O_LARGEFILE|O_DIRECTORY) = 4 fstat64(4, {st_mode=S_IFDIR|0755, st_size=4096, ...}) = 0 fcntl64(4, F_SETFD, FD_CLOEXEC) = 0 write(2, "Entering directory: D0755 0 Temp"..., 33Entering directory: D0755 0 Temp ) = 33 write(6, "D0755 0 Temp\n", 13) = 13 read(7, "\0", 1) = 1 getdents64(4, /* 50 entries */, 4096) = 1928 open(".cxoffice/dotwine/fake_windows/Windows/Temp/IExplorer6.log.fifo", O_RDONLY|O_LARGEFILE [CTRL-C] $ file ~/.cxoffice/dotwine/fake_windows/Windows/Temp/IExplorer6.log.fifo .cxoffice/dotwine/fake_windows/Windows/Temp/IExplorer6.log.fifo: fifo (named pipe) It took me a while to figure this out, find that there was an existing Debian bug #246774 that referred to this one. I think it is rather important from a usability POV as the cause of this hang is entirely non-obvious.
Created attachment 892 [details] Don't block on FIFOs This works on OpenBSD, and shouldn't hurt on other platforms
fix applied - will be in 4.7, thanks!
Close resolved bugs after release.