X-Git-Url: http://git.osdn.net/view?p=lha%2Flha.git;a=blobdiff_plain;f=src%2Flhext.c;h=ba73f969e13f9faf585aaddd41bb2f82d7427f0d;hp=d386bac5ece9bffbe0ab992e111d704ca92b24ea;hb=62e045aaf28eb72fe746540bc50a3f19369e7c3e;hpb=a989239e749c153ea6709b6299fd9f0e024b9899 diff --git a/src/lhext.c b/src/lhext.c index d386bac..ba73f96 100644 --- a/src/lhext.c +++ b/src/lhext.c @@ -30,7 +30,7 @@ static void add_dirinfo(char* name, LzHeader* hdr); static void adjust_dirinfo(); #ifdef HAVE_LIBAPPLEFILE -static boolean decode_macbinary(FILE *ofp, size_t size, const char *outPath); +static boolean decode_macbinary(FILE *ofp, off_t size, const char *outPath); #endif /* ------------------------------------------------------------------------ */ @@ -99,6 +99,7 @@ make_name_with_pathcheck(char *name, size_t namesz, const char *q) offset += sz; } +#ifdef S_IFLNK while ((p = strchr(q, '/')) != NULL) { if (namesz - offset < (p - q) + 2) { return FALSE; @@ -118,6 +119,7 @@ make_name_with_pathcheck(char *name, size_t namesz, const char *q) } name[offset++] = '/'; } +#endif str_safe_copy(name + offset, q, namesz - offset); @@ -480,7 +482,7 @@ extract_one(afp, hdr) || (hdr->unix_mode & UNIX_FILE_TYPEMASK) == UNIX_FILE_SYMLINK || method == LZHDIRS_METHOD_NUM) { /* ↑これで、Symbolic Link は、大丈夫か? */ - if (!ignore_directory && !verify_mode) { + if (!ignore_directory && !verify_mode && !output_to_stdout) { if (noexec) { if (quiet != TRUE) printf("EXTRACT %s (directory)\n", name); @@ -525,7 +527,7 @@ extract_one(afp, hdr) #endif } else { /* make directory */ - if (!output_to_stdout && !make_parent_path(name)) + if (!make_parent_path(name)) return read_size; /* save directory information */ add_dirinfo(name, hdr); @@ -547,6 +549,25 @@ extract_one(afp, hdr) return read_size; } +static int +skip_to_nextpos(FILE *fp, off_t pos, off_t off, off_t read_size) +{ + if (pos != -1) { + if (fseeko(fp, pos + off, SEEK_SET) != 0) { + return -1; + } + } + else { + off_t i = off - read_size; + while (i--) { + if (fgetc(fp) == EOF) { + return -1; + } + } + } + return 0; +} + /* ------------------------------------------------------------------------ */ /* EXTRACT COMMAND MAIN */ /* ------------------------------------------------------------------------ */ @@ -567,25 +588,19 @@ cmd_extract() /* extract each files */ while (get_header(afp, &hdr)) { + pos = ftello(afp); if (need_file(hdr.name)) { - pos = ftello(afp); read_size = extract_one(afp, &hdr); if (read_size != hdr.packed_size) { /* when error occurred in extract_one(), should adjust point of file stream */ - if (pos != -1 && afp != stdin) - fseeko(afp, pos + hdr.packed_size, SEEK_SET); - else { - off_t i = hdr.packed_size - read_size; - while (i--) fgetc(afp); + if (skip_to_nextpos(afp, pos, hdr.packed_size, read_size) == -1) { + fatal_error("Cannot seek to next header position from \"%s\"", hdr.name); } } } else { - if (afp != stdin) - fseeko(afp, hdr.packed_size, SEEK_CUR); - else { - off_t i = hdr.packed_size; - while (i--) fgetc(afp); + if (skip_to_nextpos(afp, pos, hdr.packed_size, 0) == -1) { + fatal_error("Cannot seek to next header position from \"%s\"", hdr.name); } } } @@ -721,7 +736,7 @@ decode_macbinary(ofp, size, outPath) af_file_t *afp = NULL; FILE *ifp = NULL; unsigned char *datap; - off_t dlen; + size_t dlen; if ((afp = af_open(temporary_name)) != NULL) { /* fetch datafork */