From: Michael Gernoth Date: Sun, 1 Feb 2009 12:16:04 +0000 (+0100) Subject: add functions to reliably read files in the filesystem, to be used by the X-Git-Url: https://git.zerfleddert.de/cgi-bin/gitweb.cgi/rsbs2/commitdiff_plain/81a1093d3e69b4996e56bc291759f1c17dbc2344?ds=sidebyside add functions to reliably read files in the filesystem, to be used by the property functions. --- diff --git a/extract.c b/extract.c index 5d2a6fc..86491d1 100644 --- a/extract.c +++ b/extract.c @@ -12,43 +12,61 @@ #include "rsb-lz.h" #include "extract.h" +struct file_entry* get_next_file(unsigned char *fw, int len) +{ + static unsigned char *pos; + static unsigned char *end; + static struct file_entry fent; + int name_length; + + if (fw != NULL && len != 0) { + pos = fw + 0x28; + + printf("Start of filesystem: 0x%08x\n", *((unsigned int*)pos)); + pos = fw + *((unsigned int*)pos); + end = fw + len; + } + + fent.unknown = *pos; + pos++; + + name_length = *((unsigned int*)pos); + pos += 4; + + fent.length = *((unsigned int*)pos); + pos += 4; + + if ((fent.length > (end - pos)) || + (name_length > (end - pos))) { + printf("EOF reached\n"); + return NULL; + } + + fent.name = (char*)pos; + pos += name_length; + + fent.start = pos; + pos += fent.length; + + return &fent; +} + void extract_files(unsigned char *fw, int len) { - unsigned char *pos; - unsigned int content_length; - unsigned int name_length; - unsigned char unknown; - char *name; - - pos = fw + 0x28; - printf("Start of filesystem: 0x%08x\n", *((unsigned int*)pos)); - - pos = fw + *((unsigned int*)pos); - - while (pos < (fw + len)) { - unknown = *pos; pos++; - name_length = *((unsigned int*)pos); - pos += 4; - content_length = *((unsigned int*)pos); - pos += 4; - name = (char*)pos; - - if (((pos + content_length) > (fw + len)) || - ((pos + name_length) > (fw + len))) { - printf("EOF reached\n"); - break; - } - pos += name_length; + struct file_entry *fent; + fent = get_next_file(fw, len); + + while (fent) { printf("%s: unknown: 0x%02x, length: %d", - name, unknown, content_length); + fent->name, fent->unknown, fent->length); - if (content_length > 0) { - write_file(name, pos, content_length); - if (*((unsigned int*)pos) == LZ_MAGIC) { + if (fent->length > 0) { + write_file(fent->name, fent->start, fent->length); + if (*((unsigned int*)fent->start) == LZ_MAGIC) { char *lzname; - if ((lzname = strdup(name)) == NULL) { + if ((lzname = strdup(fent->name)) == NULL) { perror("strdup"); exit(1); } @@ -61,16 +79,16 @@ void extract_files(unsigned char *fw, int len) printf("%s: packed file found", lzname); - extract_lz_file(pos, (unsigned char*)lzname); + extract_lz_file(fent->start, (unsigned char*)lzname); free(lzname); - } else if (!strcmp(name, "firmware")) { + } else if (!strcmp(fent->name, "firmware")) { unsigned char *lzpos; char lzname[128]; bzero(lzname, sizeof(lzname)); strcpy(lzname, "firmware."); - lzpos = pos + *((unsigned int*)(pos + 0x20)); + lzpos = fent->start + *((unsigned int*)(fent->start + 0x20)); memcpy(lzname + strlen(lzname), lzpos - 4, 4); lzpos += 4; if (*((unsigned int*)(lzpos)) == LZ_MAGIC) { @@ -79,9 +97,7 @@ void extract_files(unsigned char *fw, int len) } } } - - pos += content_length; - + fent = get_next_file(NULL, 0); } } diff --git a/extract.h b/extract.h index d8b8d32..ee35618 100644 --- a/extract.h +++ b/extract.h @@ -1,2 +1,10 @@ +struct file_entry { + char *name; + unsigned char *start; + int length; + unsigned char unknown; +}; + +struct file_entry* get_next_file(unsigned char *fw, int len); void extract_files(unsigned char *fw, int len); void write_file(char *fname, unsigned char *buf, int len);