mirror of
https://github.com/9fans/plan9port.git
synced 2025-01-27 11:52:03 +00:00
better ext2 block read (sigh)
This commit is contained in:
parent
dbf91a04cc
commit
fa5af68711
1 changed files with 23 additions and 21 deletions
|
@ -655,7 +655,7 @@ ext2readfile(Fsys *fsys, SunAuthUnix *au, Nfs3Handle *h, u32int count,
|
||||||
uchar *data;
|
uchar *data;
|
||||||
Block *b;
|
Block *b;
|
||||||
Ext2 *fs;
|
Ext2 *fs;
|
||||||
int off, want, fragcount;
|
int skip1, tot, want, fragcount;
|
||||||
Inode ino;
|
Inode ino;
|
||||||
Nfs3Status ok;
|
Nfs3Status ok;
|
||||||
|
|
||||||
|
@ -674,34 +674,36 @@ ext2readfile(Fsys *fsys, SunAuthUnix *au, Nfs3Handle *h, u32int count,
|
||||||
}
|
}
|
||||||
if(offset+count > ino.size)
|
if(offset+count > ino.size)
|
||||||
count = ino.size-offset;
|
count = ino.size-offset;
|
||||||
if(offset/fs->blocksize != (offset+count-1)/fs->blocksize)
|
|
||||||
count = fs->blocksize - offset%fs->blocksize;
|
|
||||||
|
|
||||||
data = malloc(count);
|
data = malloc(count);
|
||||||
if(data == nil)
|
if(data == nil)
|
||||||
return Nfs3ErrNoMem;
|
return Nfs3ErrNoMem;
|
||||||
|
memset(data, 0, count);
|
||||||
|
|
||||||
want = offset%fs->blocksize+count;
|
skip1 = offset%fs->blocksize;
|
||||||
if(want%fs->blocksize)
|
offset -= skip1;
|
||||||
want += fs->blocksize - want%fs->blocksize;
|
want = skip1+count;
|
||||||
|
|
||||||
b = ext2fileblock(fs, &ino, offset/fs->blocksize, want);
|
/*
|
||||||
if(b == nil){
|
* have to read multiple blocks if we get asked for a big read.
|
||||||
/* BUG: distinguish sparse file from I/O error */
|
* Linux NFS client assumes that if you ask for 8k and only get 4k
|
||||||
memset(data, 0, count);
|
* back, the remaining 4k is zeros.
|
||||||
}else{
|
*/
|
||||||
off = offset%fs->blocksize;
|
for(tot=0; tot<want; tot+=fragcount){
|
||||||
fragcount = count; /* need signed variable */
|
b = ext2fileblock(fs, &ino, (offset+tot)/fs->blocksize, fs->blocksize);
|
||||||
if(off+fragcount > b->len){
|
fragcount = fs->blocksize;
|
||||||
fragcount = b->len - off;
|
if(b == nil)
|
||||||
if(fragcount < 0)
|
continue;
|
||||||
fragcount = 0;
|
if(tot+fragcount > want)
|
||||||
}
|
fragcount = want - tot;
|
||||||
if(fragcount > 0)
|
if(tot == 0)
|
||||||
memmove(data, b->data+off, fragcount);
|
memmove(data, b->data+skip1, fragcount-skip1);
|
||||||
count = fragcount;
|
else
|
||||||
|
memmove(data+tot-skip1, b->data, fragcount);
|
||||||
blockput(b);
|
blockput(b);
|
||||||
}
|
}
|
||||||
|
count = tot - skip1;
|
||||||
|
|
||||||
*peof = (offset+count == ino.size);
|
*peof = (offset+count == ino.size);
|
||||||
*pcount = count;
|
*pcount = count;
|
||||||
*pdata = data;
|
*pdata = data;
|
||||||
|
|
Loading…
Reference in a new issue