snap: fix readseg() to cope with > 2gb segments

This commit is contained in:
cinap_lenrek 2015-03-07 15:21:01 +01:00
parent 7b7c7f4451
commit 0c705580ab
2 changed files with 16 additions and 18 deletions

View file

@ -26,9 +26,9 @@ struct Data {
struct Seg { struct Seg {
char* name; char* name;
uvlong offset; uvlong offset;
uvlong len; uvlong len;
Page** pg; Page** pg;
int npg; ulong npg;
}; };
struct Page { struct Page {

View file

@ -96,47 +96,45 @@ readsection(long pid, char *sec)
} }
static Seg* static Seg*
readseg(int fd, vlong off, ulong len, char *name) readseg(int fd, uvlong off, uvlong len, char *name)
{ {
char buf[Pagesize]; char buf[Pagesize];
ulong npg;
Page **pg; Page **pg;
int npg;
Seg *s; Seg *s;
ulong i;
int n; int n;
s = emalloc(sizeof(*s)); s = emalloc(sizeof(*s));
s->name = estrdup(name); s->name = estrdup(name);
if(seek(fd, off, 0) < 0) { if(seek(fd, off, 0) < 0) {
fprint(2, "seek fails\n"); fprint(2, "seek fails\n");
goto Die; goto Die;
} }
s->offset = off;
s->len = 0;
pg = nil; pg = nil;
npg = 0; npg = 0;
for(i=0; i<len; ) { while(s->len < len){
n = Pagesize; n = Pagesize;
if(n > len-i) if(n > len - s->len)
n = len-i; n = len - s->len;
if((n = readn(fd, buf, n)) <= 0) if((n = readn(fd, buf, n)) <= 0)
break; break;
pg = erealloc(pg, sizeof(*pg)*(npg+1)); s->len += n;
if((npg & (npg-1)) == 0)
pg = erealloc(pg, sizeof(*pg) * (npg==0 | npg*2));
pg[npg++] = datapage(buf, n); pg[npg++] = datapage(buf, n);
i += n;
if(n != Pagesize) /* any short read, planned or otherwise */ if(n != Pagesize) /* any short read, planned or otherwise */
break; break;
} }
if(s->len==0 && len!=0){
if(i==0 && len!=0) free(pg);
goto Die; goto Die;
}
s->offset = off; pg = erealloc(pg, sizeof(*pg) * npg);
s->len = i;
s->pg = pg; s->pg = pg;
s->npg = npg; s->npg = npg;
return s; return s;
Die: Die:
free(s->name); free(s->name);
free(s); free(s);