SQLite

Check-in [72256634]
Login

Many hyperlinks are disabled.
Use anonymous login to enable hyperlinks.

Overview
Comment:If the read() system call in unix returns fewer bytes than expected, retry it until it either returns zero or an error.
Downloads: Tarball | ZIP archive | SQL archive
Timelines: family | ancestors | retry-short-reads
Files: files | file ages | folders
SHA1: 72256634773f6cba0aabaa3c953cd5daefd50e67
User & Date: drh 2011-11-01 15:45:28
Context
2011-11-01
15:45
If the read() system call in unix returns fewer bytes than expected, retry it until it either returns zero or an error. (Closed-Leaf check-in: 72256634 user: drh tags: retry-short-reads)
00:52
Version 3.7.9 (check-in: c7c6050e user: drh tags: trunk, release, version-3.7.9)
Changes
Hide Diffs Unified Diffs Ignore Whitespace Patch

Changes to src/os_unix.c.

2940
2941
2942
2943
2944
2945
2946

2947
2948
2949
2950

2951
2952
2953
2954
2955
2956
2957
2958
2959
2960
2961
2962
2963
2964
2965
2966
2967
2968
2969






2970
2971
2972

2973
2974
2975
2976
2977
2978
2979
2980
2981
2982
** See tickets #2741 and #2681.
**
** To avoid stomping the errno value on a failed read the lastErrno value
** is set before returning.
*/
static int seekAndRead(unixFile *id, sqlite3_int64 offset, void *pBuf, int cnt){
  int got;

#if (!defined(USE_PREAD) && !defined(USE_PREAD64))
  i64 newOffset;
#endif
  TIMER_START;

#if defined(USE_PREAD)
  do{ got = osPread(id->h, pBuf, cnt, offset); }while( got<0 && errno==EINTR );
  SimulateIOError( got = -1 );
#elif defined(USE_PREAD64)
  do{ got = osPread64(id->h, pBuf, cnt, offset); }while( got<0 && errno==EINTR);
  SimulateIOError( got = -1 );
#else
  newOffset = lseek(id->h, offset, SEEK_SET);
  SimulateIOError( newOffset-- );
  if( newOffset!=offset ){
    if( newOffset == -1 ){
      ((unixFile*)id)->lastErrno = errno;
    }else{
      ((unixFile*)id)->lastErrno = 0;			
    }
    return -1;
  }
  do{ got = osRead(id->h, pBuf, cnt); }while( got<0 && errno==EINTR );
#endif






  TIMER_END;
  if( got<0 ){
    ((unixFile*)id)->lastErrno = errno;

  }
  OSTRACE(("READ    %-3d %5d %7lld %llu\n", id->h, got, offset, TIMER_ELAPSED));
  return got;
}

/*
** Read data from a file into a buffer.  Return SQLITE_OK if all
** bytes were read successfully and SQLITE_IOERR if anything goes
** wrong.
*/







>




>

|
|

|
|

|
|
|
|
|
|
|
|
|
|
|

>
>
>
>
>
>



>

|
|







2940
2941
2942
2943
2944
2945
2946
2947
2948
2949
2950
2951
2952
2953
2954
2955
2956
2957
2958
2959
2960
2961
2962
2963
2964
2965
2966
2967
2968
2969
2970
2971
2972
2973
2974
2975
2976
2977
2978
2979
2980
2981
2982
2983
2984
2985
2986
2987
2988
2989
2990
2991
** See tickets #2741 and #2681.
**
** To avoid stomping the errno value on a failed read the lastErrno value
** is set before returning.
*/
static int seekAndRead(unixFile *id, sqlite3_int64 offset, void *pBuf, int cnt){
  int got;
  int total = 0;
#if (!defined(USE_PREAD) && !defined(USE_PREAD64))
  i64 newOffset;
#endif
  TIMER_START;
  while( cnt>0 ){
#if defined(USE_PREAD)
    do{ got = osPread(id->h, pBuf, cnt, offset); }while(got<0 && errno==EINTR);
    SimulateIOError( got = -1 );
#elif defined(USE_PREAD64)
    do{ got = osPread64(id->h, pBuf,cnt,offset); }while(got<0 && errno==EINTR);
    SimulateIOError( got = -1 );
#else
    newOffset = lseek(id->h, offset, SEEK_SET);
    SimulateIOError( newOffset-- );
    if( newOffset!=offset ){
      if( newOffset == -1 ){
        ((unixFile*)id)->lastErrno = errno;
      }else{
        ((unixFile*)id)->lastErrno = 0;			
      }
      return -1;
    }
    do{ got = osRead(id->h, pBuf, cnt); }while( got<0 && errno==EINTR );
#endif
    if( got<=0 ) break;
    total += got;
    cnt -= got;
    offset += got;
    pBuf = (void*)(got + (char*)pBuf);
  }
  TIMER_END;
  if( got<0 ){
    ((unixFile*)id)->lastErrno = errno;
    total = got;
  }
  OSTRACE(("READ    %-3d %5d %7lld %llu\n", id->h,total,offset,TIMER_ELAPSED));
  return total;
}

/*
** Read data from a file into a buffer.  Return SQLITE_OK if all
** bytes were read successfully and SQLITE_IOERR if anything goes
** wrong.
*/