OSDN Git Service

* src/lhext.c: replaced bcmp() with memcmp().
[lha/lha.git] / src / lhext.c
index 76adc3c..6542166 100644 (file)
@@ -19,7 +19,7 @@ static int      skip_flg = FALSE;     /* FALSE..No Skip , TRUE..Skip */
 static char       *methods[] =
 {
        LZHUFF0_METHOD, LZHUFF1_METHOD, LZHUFF2_METHOD, LZHUFF3_METHOD,
-       LZHUFF4_METHOD, LZHUFF5_METHOD, LZHUFF6_METHOD,
+       LZHUFF4_METHOD, LZHUFF5_METHOD, LZHUFF6_METHOD, LZHUFF7_METHOD,
        LARC_METHOD, LARC5_METHOD, LARC4_METHOD,
        LZHDIRS_METHOD,
        NULL
@@ -35,7 +35,7 @@ inquire_extract(name)
        skip_flg = FALSE;
        if (stat(name, &stbuf) >= 0) {
                if (!is_regularfile(&stbuf)) {
-                       error("Already exist (not a file)", name);
+                       error("\"%s\" already exists (not a file)", name);
                        return FALSE;
                }
 
@@ -90,32 +90,41 @@ make_parent_path(name)
                }
 
        if (p == path) {
-               message("Why?", "ROOT");
+               message("invalid path name \"%s\"", name);
                return FALSE;   /* no more parent. */
        }
 
        if (GETSTAT(path, &stbuf) >= 0) {
                if (is_directory(&stbuf))
                        return TRUE;
-               error("Not a directory", path);
+               error("Not a directory \"%s\"", path);
                return FALSE;
        }
-       errno = 0;
 
        if (verbose)
-               printf("Making directory \"%s\".\n", path);
+               message("Making directory \"%s\".", path);
 
+#if defined __MINGW32__
+    if (mkdir(path) >= 0)
+        return TRUE;
+#else
        if (mkdir(path, 0777) >= 0)     /* try */
                return TRUE;    /* successful done. */
-       errno = 0;
+#endif
 
        if (!make_parent_path(path))
                return FALSE;
 
+#if defined __MINGW32__
+    if (mkdir(path) < 0)
+               error("Cannot make directory", path);
+        return FALSE;
+#else
        if (mkdir(path, 0777) < 0) {    /* try again */
-               message("Cannot make directory", path);
+               error("Cannot make directory", path);
                return FALSE;
        }
+#endif
 
        return TRUE;
 }
@@ -128,11 +137,9 @@ open_with_make_path(name)
        FILE           *fp;
 
        if ((fp = fopen(name, WRITE_BINARY)) == NULL) {
-               errno = 0;
                if (!make_parent_path(name) ||
                    (fp = fopen(name, WRITE_BINARY)) == NULL)
-                       error("Cannot extract", name);
-               errno = 0;
+                       error("Cannot extract a file \"%s\"", name);
        }
        return fp;
 }
@@ -160,15 +167,28 @@ adjust_info(name, hdr)
                if ((hdr->unix_mode & UNIX_FILE_TYPEMASK) != UNIX_FILE_SYMLINK)
                        chmod(name, hdr->unix_mode);
 #endif
-               if (!getuid()) {
-#ifndef HAVE_NO_LCHOWN
-            if ((hdr->unix_mode & UNIX_FILE_TYPEMASK) != UNIX_FILE_SYMLINK)
-                           lchown(name, hdr->unix_uid, hdr->unix_gid);
+               if (!getuid()){
+            uid_t uid = hdr->unix_uid;
+            gid_t gid = hdr->unix_gid;
+
+#if HAVE_GETPWNAM && HAVE_GETGRNAM
+            if (hdr->user[0]) {
+                struct passwd *ent = getpwnam(hdr->user);
+                if (ent) uid = ent->pw_uid;
+            }
+            if (hdr->group[0]) {
+                struct group *ent = getgrnam(hdr->group);
+                if (ent) gid = ent->gr_gid;
+            }
+#endif
+
+#if HAVE_LCHOWN
+                       if ((hdr->unix_mode & UNIX_FILE_TYPEMASK) == UNIX_FILE_SYMLINK)
+                               lchown(name, uid, gid);
                        else
-#endif /* HAVE_NO_LCHWON */
-                           chown(name, hdr->unix_uid, hdr->unix_gid);
+#endif /* HAVE_LCHWON */
+                               chown(name, uid, gid);
                }
-               errno = 0;
        }
 }
 
@@ -186,8 +206,8 @@ extract_one(afp, hdr)
        boolean         save_quiet, save_verbose, up_flag;
        char           *q = hdr->name, c;
 
-       if (ignore_directory && rindex(hdr->name, '/')) {
-               q = (char *) rindex(hdr->name, '/') + 1;
+       if (ignore_directory && strrchr(hdr->name, '/')) {
+               q = (char *) strrchr(hdr->name, '/') + 1;
        }
        else {
                if (*q == '/') {
@@ -207,7 +227,7 @@ extract_one(afp, hdr)
        }
 
        if (extract_directory)
-               sprintf(name, "%s/%s", extract_directory, q);
+               xsnprintf(name, sizeof(name), "%s/%s", extract_directory, q);
        else
                strcpy(name, q);
 
@@ -216,10 +236,11 @@ extract_one(afp, hdr)
        /* 1999.4.30 t.okamoto */
        for (method = 0;; method++) {
                if (methods[method] == NULL) {
-                       error("Unknown method skiped ...", name);
+                       error("Unknown method \"%.*s\"; \"%s\" will be skiped ...",
+                  5, hdr->method, name);
                        return;
                }
-               if (bcmp(hdr->method, methods[method], 5) == 0)
+               if (memcmp(hdr->method, methods[method], 5) == 0)
                        break;
        }
 
@@ -228,10 +249,11 @@ extract_one(afp, hdr)
 #if 0
                for (method = 0;; method++) {
                        if (methods[method] == NULL) {
-                               error("Unknown method skiped ...", name);
+                error("Unknown method \"%.*s\"; \"%s\" will be skiped ...",
+                      5, hdr->method, name);
                                return;
                        }
-                       if (bcmp(hdr->method, methods[method], 5) == 0)
+                       if (memcmp(hdr->method, methods[method], 5) == 0)
                                break;
                }
 #endif
@@ -261,8 +283,20 @@ extract_one(afp, hdr)
                                verbose = TRUE;
                        }
 
+#if __MINGW32__
+            {
+                int old_mode;
+                fflush(stdout);
+                old_mode = setmode(fileno(stdout), O_BINARY);
+#endif
+
                        crc = decode_lzhuf
                                (afp, stdout, hdr->original_size, hdr->packed_size, name, method);
+#if __MINGW32__
+                fflush(stdout);
+                setmode(fileno(stdout), old_mode);
+            }
+#endif
                        quiet = save_quiet;
                        verbose = save_verbose;
                }
@@ -293,10 +327,11 @@ extract_one(afp, hdr)
                        }
 
                        signal(SIGINT, interrupt);
+#ifdef SIGHUP
                        signal(SIGHUP, interrupt);
+#endif
 
                        unlink(name);
-                       errno = 0;
                        remove_extracting_file_when_interrupt = TRUE;
 
                        if ((fp = open_with_make_path(name)) != NULL) {
@@ -306,20 +341,20 @@ extract_one(afp, hdr)
                        }
                        remove_extracting_file_when_interrupt = FALSE;
                        signal(SIGINT, SIG_DFL);
+#ifdef SIGHUP
                        signal(SIGHUP, SIG_DFL);
-
+#endif
                        if (!fp)
                                return;
                }
 
-               errno = 0;
                if (hdr->has_crc && crc != hdr->crc)
-                       error("CRC error", name);
+                       error("CRC error: \"%s\"", name);
        }
        else if ((hdr->unix_mode & UNIX_FILE_TYPEMASK) == UNIX_FILE_DIRECTORY
                         || (hdr->unix_mode & UNIX_FILE_TYPEMASK) == UNIX_FILE_SYMLINK
                         || method == LZHDIRS_METHOD_NUM) {
-               /* ¢¬¤³¤ì¤Ç¡¢Symblic Link ¤Ï¡¢Âç¾æÉפ«¡© */
+               /* ¢¬¤³¤ì¤Ç¡¢Symbolic Link ¤Ï¡¢Âç¾æÉפ«¡© */
                if (!ignore_directory && !verify_mode) {
                        if (noexec) {
                                if (quiet != TRUE)
@@ -354,15 +389,15 @@ extract_one(afp, hdr)
                                l_code = symlink(bb2, bb1);
                                if (l_code < 0) {
                                        if (quiet != TRUE)
-                                               warning("Can't make Symbolic Link : ");
+                                               warning("Can't make Symbolic Link \"%s\" -> \"%s\"",
+                                bb1, bb2);
                                }
                                if (quiet != TRUE) {
-                                       printf("Symbolic Link %s -> %s\n", bb1, bb2);
+                                       message("Symbolic Link %s -> %s", bb1, bb2);
                                }
                                strcpy(name, bb1);      /* Symbolic's name set */
 #else
-                               sprintf(buf, "%s -> %s", bb1, bb2);
-                               warning("Can't make Symbolic Link", buf);
+                               warning("Can't make Symbolic Link %s -> %s", bb1, bb2);
                                return;
 #endif
                        } else { /* make directory */
@@ -372,7 +407,7 @@ extract_one(afp, hdr)
                }
        }
        else {
-               error("Unknown information", name);
+               error("Unknown information: \"%s\"", name);
        }
 
        if (!output_to_stdout)
@@ -391,7 +426,7 @@ cmd_extract()
 
        /* open archive file */
        if ((afp = open_old_archive()) == NULL)
-               fatal_error(archive_name);
+               fatal_error("Cannot open archive file \"%s\"", archive_name);
 
        if (archive_is_msdos_sfx1(archive_name))
                skip_msdos_sfx1_code(afp);
@@ -401,9 +436,17 @@ cmd_extract()
                if (need_file(hdr.name)) {
                        pos = ftell(afp);
                        extract_one(afp, &hdr);
-                       fseek(afp, pos + hdr.packed_size, SEEK_SET);
-               }
-               else {
+            /* when error occurred in extract_one(), should adjust
+               point of file stream */
+                       if (afp != stdin)
+                fseek(afp, pos + hdr.packed_size, SEEK_SET);
+            else {
+                /* FIXME: assume that the extract_one() has read
+                   packed_size bytes from stdin. */
+                long i = 0;
+                               while (i--) fgetc(afp);
+            }
+               } else {
                        if (afp != stdin)
                                fseek(afp, hdr.packed_size, SEEK_CUR);
                        else {
@@ -419,3 +462,9 @@ cmd_extract()
 
        return;
 }
+
+/* Local Variables: */
+/* mode:c */
+/* tab-width:4 */
+/* End: */
+/* vi: set tabstop=4: */