Enhance raw io reliability
PATCH 1/1 Enhance raw io reliability
For raw block device only : log any I/O error and perform automatic read retry for CDrom (improves MediaCheck with old installers).
Signed-off-by Ben Guthro <[email protected]>
Signed-off-by Josh Nicholas <[email protected]>
tools/ioemu/block-raw.c +92 -2
@@ -59,6 +59,13 @@//#define DEBUG_FLOPPY +#define DEBUG_BLOCK +#ifdef DEBUG_BLOCK +#define DEBUG_BLOCK_PRINT( formatCstr, args... ) fprintf( logfile, formatCstr, ##args ); fflush( logfile ) +#else +#define DEBUG_BLOCK_PRINT( formatCstr, args... ) +#endif +#define FTYPE_FILE 0#define FTYPE_CD 1#define FTYPE_FD 2
@@ -70,6 +77,7 @@ typedef struct BDRVRawState { typedef struct BDRVRawState { int fd; int type; + unsigned int lseek_err_cnt; #if defined(__linux__) /* linux floppy specific */ int fd_open_flags;
@@ -87,6 +95,8 @@ static int raw_open(BlockDriverState *bsBDRVRawState *s = bs->opaque;int fd, open_flags, ret; + s->lseek_err_cnt =0 ; + open_flags =O_BINARY ;if ((flags &BDRV_O_ACCESS ) ==O_RDWR ) { open_flags |=O_RDWR ;
@@ -137,8 +147,58 @@ static int raw_pread(BlockDriverState *bif (ret <0 )return ret; -lseek (s->fd, offset,SEEK_SET ); +if (lseek (s->fd, offset,SEEK_SET ) == (off_t)-1 ) { + ++(s->lseek_err_cnt); +if (s->lseek_err_cnt <=10 ) { +DEBUG_BLOCK_PRINT ("raw_pread(%d:%s, %ld, %p, %d) [%ld] lseek failed : %d = %s\n" , + s->fd, + bs->filename, + offset, + buf, + count, + bs->total_sectors, errno,strerror (errno) ); + } +return -1 ; + } + s->lseek_err_cnt=0 ; + ret =read (s->fd, buf, count); +if (ret == count) + goto label__raw_read__success; + +DEBUG_BLOCK_PRINT ("raw_read(%d:%s, %ld, %p, %d) [%ld] read failed %d : %d = %s\n" , + s->fd, + bs->filename, + offset, + buf, + count, + bs->total_sectors, + ret, errno,strerror (errno) ); + +if (bs->type ==BDRV_TYPE_CDROM ) {// Try harder for CDrom +lseek (s->fd, offset,SEEK_SET ); + ret =read (s->fd, buf, count); +if (ret == count) + goto label__raw_read__success; +lseek (s->fd, offset,SEEK_SET ); + ret =read (s->fd, buf, count); +if (ret == count) + goto label__raw_read__success; + +DEBUG_BLOCK_PRINT ("raw_read(%d:%s, %ld, %p, %d) [%ld] retry read failed %d : %d = %s\n" , + s->fd, + bs->filename, + offset, + buf, + count, + bs->total_sectors, + ret, errno,strerror (errno) ); + } + +return -1 ; + +label__raw_read__success: +return ret; }
@@ -152,8 +212,38 @@ static int raw_pwrite(BlockDriverState *if (ret <0 )return ret; -lseek (s->fd, offset,SEEK_SET ); +if (lseek (s->fd, offset,SEEK_SET ) == (off_t)-1 ) { + ++(s->lseek_err_cnt); +if (s->lseek_err_cnt) { +DEBUG_BLOCK_PRINT ("raw_write(%d:%s, %ld, %p, %d) [%ld] lseek failed : %d = %s\n" , + s->fd, + bs->filename, + offset, + buf, + count, + bs->total_sectors, errno,strerror (errno) ); + } +return -1 ; + } + s->lseek_err_cnt =0 ; + ret =write (s->fd, buf, count); +if (ret == count) + goto label__raw_write__success; + +DEBUG_BLOCK_PRINT ("raw_write(%d:%s, %ld, %p, %d) [%ld] write failed %d : %d = %s\n" , + s->fd, + bs->filename, + offset, + buf, + count, + bs->total_sectors, + ret, errno,strerror (errno) ); + +return -1 ; + +label__raw_write__success: +return ret; }
_______________________________________________
Xen-devel mailing list
[email protected]
http://lists.xensource.com/xen-devel