[Bugme-new] [Bug 21612] New: unexpected splice() behaviour

bugzilla-daemon at bugzilla.kernel.org bugzilla-daemon at bugzilla.kernel.org
Sun Oct 31 23:16:39 PDT 2010


https://bugzilla.kernel.org/show_bug.cgi?id=21612

           Summary: unexpected splice()  behaviour
           Product: IO/Storage
           Version: 2.5
    Kernel Version: ubuntu 2.6.32-25-generic-pae
          Platform: All
        OS/Version: Linux
              Tree: Mainline
            Status: NEW
          Severity: normal
          Priority: P1
         Component: Other
        AssignedTo: io_other at kernel-bugs.osdl.org
        ReportedBy: socketpair at gmail.com
        Regression: No


How to reproduce:
1. # echo "0 $((512*10000)) error" | dmsetup create ioerr
2. 

#define _GNU_SOURCE
#include <sys/socket.h>
#include <sys/un.h>
#include <fcntl.h>
#include <unistd.h>

#define CNT (4096)
int main ()
{
    int errfd=open("/dev/mapper/ioerr",O_RDONLY|O_NONBLOCK);
    int goodfd=open("/dev/urandom",O_RDONLY|O_NONBLOCK);
    int p[2];
    char buf[CNT*(3+1)];
    pipe(p);
    splice(goodfd,0,p[1],0,CNT,SPLICE_F_MOVE|SPLICE_F_NONBLOCK);

    /* marked line. see below */
    splice(errfd,0,p[1],0,CNT,SPLICE_F_MOVE|SPLICE_F_NONBLOCK); 

    splice(goodfd,0,p[1],0,CNT,SPLICE_F_MOVE|SPLICE_F_NONBLOCK);
    close(errfd);
    close(goodfd);
    read(p[0],buf,sizeof(buf));
    read(p[0],buf,sizeof(buf));
    read(p[0],buf,sizeof(buf));
    read(p[0],buf,sizeof(buf));
    return 0;
}
3. strace:
open("/dev/mapper/ioerr", O_RDONLY|O_NONBLOCK) = 3
open("/dev/urandom", O_RDONLY|O_NONBLOCK) = 4
pipe([5, 6])                            = 0
splice(0x4, 0, 0x6, 0, 0x1000, 0x3)     = 4096
splice(0x3, 0, 0x6, 0, 0x1000, 0x3)     = 4096
splice(0x4, 0, 0x6, 0, 0x1000, 0x3)     = 4096
close(3)                                = 0
close(4)                                = 0
read(5, "\222\272\376\22N\310\371_kM!G\3212\336\306g\25\341\r\361\321\273\242
`\26f\317G\235\314"..., 16384) = 4096
read(5, "", 16384)                      = 0
read(5, "", 16384)                      = 0
read(5, "", 16384)                      = 0
exit_group(0)                           = ?

4. ACHTUNG. read() should return at least 2*4096 bytes (two pages from urandom)
!!!!!
5. got to marked line. replace errfd with goodfd, and voila! read returns 3
pages.

The bug: There is no way to detect io erros. in mmap()'ed environment we will
receive signal, in splice()'ed io we will get o_O.

-- 
Configure bugmail: https://bugzilla.kernel.org/userprefs.cgi?tab=email
------- You are receiving this mail because: -------
You are on the CC list for the bug.


More information about the Bugme-new mailing list