OSDN Git Service

* config.h.in (HAVE_LIBAPPLEFILE): added `b' option which extract the MacBinary....
authorarai <arai@6a8cc165-1e22-0410-a132-eb4e3f353aba>
Mon, 11 Sep 2006 13:31:49 +0000 (13:31 +0000)
committerarai <arai@6a8cc165-1e22-0410-a132-eb4e3f353aba>
Mon, 11 Sep 2006 13:31:49 +0000 (13:31 +0000)
* configure.ac: ditto.

* src/lha.h (decode_macbinary_contents): ditto.

* src/lhadd.c (build_temporary_file): ditto.

* src/lharc.c (decode_macbinary_contents, print_tiny_usage, parse_suboption): ditto.

* src/lhext.c (extract_one, decode_macbinary): ditto.

* src/prototypes.h (build_temporary_file): ditto.

git-svn-id: svn+ssh://svn.sourceforge.jp/svnroot/lha/lha/trunk@843 6a8cc165-1e22-0410-a132-eb4e3f353aba

ChangeLog
config.h.in
configure.ac
src/lha.h
src/lhadd.c
src/lharc.c
src/lhext.c
src/prototypes.h

index 8602e31..bc589f3 100644 (file)
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,3 +1,25 @@
+2006-09-11  Koji Arai  <jca02266@nifty.com>
+
+       * config.h.in (HAVE_LIBAPPLEFILE): added `b' option which extract
+       the MacBinary. Thanks to Hiroto Sakai.
+
+       * configure.ac: ditto.
+
+       * src/lha.h (decode_macbinary_contents): ditto.
+
+       * src/lhadd.c (build_temporary_file): ditto.
+
+       * src/lharc.c (decode_macbinary_contents, print_tiny_usage, parse_suboption): ditto.
+
+       * src/lhext.c (extract_one, decode_macbinary): ditto.
+
+       * src/prototypes.h (build_temporary_file): ditto.
+
+2006-09-11  Koji Arai  <jca02266@nifty.com>
+
+       * src/lharc.c (parse_suboption): `-X' option has been ineffective.
+       Thanks to Hiroto Sakai.
+
 2005-10-15  Koji Arai  <jca02266@nifty.com>
 
        * src/lha_macro.h (UPDATE_CRC): To casting with (unsigned char)
index 1186dbb..b0c1962 100644 (file)
@@ -74,6 +74,9 @@
 /* Define to 1 if you have the `lchown' function. */
 #undef HAVE_LCHOWN
 
+/* Define to 1 if you have the `applefile' library (-lapplefile). */
+#undef HAVE_LIBAPPLEFILE
+
 /* Define to 1 if you have the <limits.h> header file. */
 #undef HAVE_LIMITS_H
 
 /* the type of system on which the package will run. */
 #undef PLATFORM
 
-/* Define if compiler has function prototypes */
+/* Define to 1 if the C compiler supports function prototypes. */
 #undef PROTOTYPES
 
 /* Define as the return type of signal handlers (`int' or `void'). */
 /* Define to 1 if you need to in order for `stat' and other things to work. */
 #undef _POSIX_SOURCE
 
+/* Define like PROTOTYPES; this can be used by system headers. */
+#undef __PROTOTYPES
+
 /* Define to empty if `const' does not conform to ANSI C. */
 #undef const
index 4251b93..0d7914a 100644 (file)
@@ -20,6 +20,7 @@ AC_CHECK_PROGS(sh_for_lha_test, [zsh bash ksh pdksh], [sh])
 
 # Checks for libraries.
 AC_SEARCH_LIBS(opendir, [mingwex])
+AC_CHECK_LIB(applefile, af_open)
 
 # Checks for header files.
 AC_HEADER_DIRENT
index 1baf905..d8bc778 100644 (file)
--- a/src/lha.h
+++ b/src/lha.h
@@ -150,6 +150,10 @@ int fnmatch(const char *pattern, const char *string, int flags);
 # define FNM_PERIOD   4
 #endif
 
+#if HAVE_LIBAPPLEFILE
+#include <applefile.h>
+#endif
+
 #ifndef SEEK_SET
 #define SEEK_SET        0
 #define SEEK_CUR        1
@@ -322,6 +326,7 @@ EXTERN int      quiet_mode;
 
 EXTERN boolean backup_old_archive;
 EXTERN boolean  extract_broken_archive;
+EXTERN boolean decode_macbinary_contents;
 
 /* ------------------------------------------------------------------------ */
 /*  Globale Variable                                                        */
index 37f83bd..4eb3a21 100644 (file)
@@ -248,7 +248,7 @@ delete(oafp, nafp)
 /* ------------------------------------------------------------------------ */
 /*                                                                          */
 /* ------------------------------------------------------------------------ */
-static FILE    *
+FILE    *
 build_temporary_file()
 {
     FILE *afp;
index ee274c5..974ced3 100644 (file)
@@ -105,6 +105,7 @@ init_variable()     /* Added N.Watazaki */
 #endif
 
     extract_broken_archive = FALSE;
+    decode_macbinary_contents = FALSE;
 }
 
 /* ------------------------------------------------------------------------ */
@@ -118,6 +119,17 @@ init_variable()     /* Added N.Watazaki */
 static void
 print_tiny_usage()
 {
+#if HAVE_LIBAPPLEFILE
+    fprintf(stderr, "\
+usage: lha [-]<commands>[<options>] [-<options> ...] archive_file [file...]\n\
+  commands:  [axelvudmcpt]\n\
+  options:   [q[012]vnfto[567]dizg012eb[w=<dir>|x=<pattern>]]\n\
+  long options: --system-kanji-code={euc,sjis,utf8,cap}\n\
+                --archive-kanji-code={euc,sjis,utf8,cap}\n\
+                --extract-broken-archive\n\
+                --help\n\
+                --version\n");
+#else
     fprintf(stderr, "\
 usage: lha [-]<commands>[<options>] [-<options> ...] archive_file [file...]\n\
   commands:  [axelvudmcpt]\n\
@@ -127,6 +139,7 @@ usage: lha [-]<commands>[<options>] [-<options> ...] archive_file [file...]\n\
                 --extract-broken-archive\n\
                 --help\n\
                 --version\n");
+#endif
 }
 
 static void
@@ -174,6 +187,11 @@ commands:                           options:\n\
                                      e  TEXT code convert from/to EUC\n\
 ");
 #endif
+#if HAVE_LIBAPPLEFILE
+    fprintf(stderr, "\
+                                     b  decode MacBinary (x/e)\n\
+");
+#endif
     fprintf(stderr, "\
                                      w=<dir> specify extract directory (x/e)\n\
                                      x=<pattern>  eXclude files (a/u/c)\n\
@@ -193,12 +211,6 @@ commands:                           options:\n\
 static int
 parse_suboption(int argc, char **argv)
 {
-#if IGNORE_DOT_FILES
-    char *short_options = "q[012]vnfto[567]dizg012ew:x:X";
-#else
-    char *short_options = "q[012]vnfto[567]dizg012ew:x:";
-#endif
-    /* "[...]" means optional 1 byte argument (original extention) */
     enum {
         HELP_OPTION = 256,
         VERSION_OPTION,
@@ -218,6 +230,16 @@ parse_suboption(int argc, char **argv)
     };
     int i;
 
+    char short_options[256] = "q[012]vnfto[567]dizg012ew:x:";
+    /* "[...]" means optional 1 byte argument (original extention) */
+
+#if IGNORE_DOT_FILES
+    strncat(short_options, "X", sizeof(short_options)-strlen(short_options)-1);
+#endif
+#if HAVE_LIBAPPLEFILE
+    strncat(short_options, "b", sizeof(short_options)-strlen(short_options)-1);
+#endif
+
     /* parse option */
     while (1) {
         int option_index = 0;
@@ -278,6 +300,11 @@ parse_suboption(int argc, char **argv)
             euc_mode = TRUE;
             break;
 #endif
+#if HAVE_LIBAPPLEFILE
+        case 'b':
+            decode_macbinary_contents = TRUE;
+            break;
+#endif
         case 'n':
             noexec = TRUE;
             break;
index c185621..0b7743a 100644 (file)
@@ -28,6 +28,10 @@ static char    *methods[] =
 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);
+#endif
+
 /* ------------------------------------------------------------------------ */
 static          boolean
 inquire_extract(name)
@@ -213,6 +217,9 @@ extract_one(afp, hdr)
     LzHeader       *hdr;
 {
     FILE           *fp; /* output file */
+#if HAVE_LIBAPPLEFILE
+    FILE           *tfp; /* temporary output file */
+#endif
     struct stat     stbuf;
     char            name[FILENAME_LENGTH];
     unsigned int crc;
@@ -282,6 +289,14 @@ extract_one(afp, hdr)
         reading_filename = archive_name;
         writing_filename = name;
         if (output_to_stdout || verify_mode) {
+            /* "Icon\r" should be a resource fork file encoded in MacBinary
+               format, so that it should be skipped. */
+            if (hdr->extend_type == EXTEND_MACOS
+                && strcmp(basename(name), "Icon\r") == 0
+                && decode_macbinary_contents) {
+                return read_size;
+            }
+
             if (noexec) {
                 printf("%s %s\n", verify_mode ? "VERIFY" : "EXTRACT", name);
                 return read_size;
@@ -306,9 +321,29 @@ extract_one(afp, hdr)
                 old_mode = setmode(fileno(stdout), O_BINARY);
 #endif
 
+#if HAVE_LIBAPPLEFILE
+            /* On default, MacLHA encodes into MacBinary. */
+            if (hdr->extend_type == EXTEND_MACOS && !verify_mode && decode_macbinary_contents) {
+                /* build temporary file */
+                tfp = NULL; /* avoid compiler warnings `uninitialized' */
+                tfp = build_temporary_file();
+
+                crc = decode_lzhuf(afp, tfp,
+                                   hdr->original_size, hdr->packed_size,
+                                   name, method, &read_size);
+                fclose(tfp);
+                decode_macbinary(stdout, hdr->original_size, name);
+                unlink(temporary_name);
+            } else {
+                crc = decode_lzhuf(afp, stdout,
+                                   hdr->original_size, hdr->packed_size,
+                                   name, method, &read_size);
+            }
+#else
             crc = decode_lzhuf(afp, stdout,
                                hdr->original_size, hdr->packed_size,
                                name, method, &read_size);
+#endif /* HAVE_LIBAPPLEFILE */
 #if __MINGW32__
                 fflush(stdout);
                 setmode(fileno(stdout), old_mode);
@@ -318,6 +353,16 @@ extract_one(afp, hdr)
             verbose = save_verbose;
         }
         else {
+#ifndef __APPLE__
+            /* "Icon\r" should be a resource fork of parent folder's icon,
+               so that it can be skipped when system is not Mac OS X. */
+            if (hdr->extend_type == EXTEND_MACOS
+                && strcmp(basename(name), "Icon\r") == 0
+                && decode_macbinary_contents) {
+                make_parent_path(name); /* create directory only */
+                return read_size;
+            }
+#endif /* __APPLE__ */
             if (skip_flg == FALSE)  {
                 up_flag = inquire_extract(name);
                 if (up_flag == FALSE && force == FALSE) {
@@ -347,9 +392,35 @@ extract_one(afp, hdr)
             remove_extracting_file_when_interrupt = TRUE;
 
             if ((fp = open_with_make_path(name)) != NULL) {
+#if HAVE_LIBAPPLEFILE
+                if (hdr->extend_type == EXTEND_MACOS && !verify_mode && decode_macbinary_contents) {
+                    /* build temporary file */
+                    tfp = NULL; /* avoid compiler warnings `uninitialized' */
+                    tfp = build_temporary_file();
+
+                    crc = decode_lzhuf(afp, tfp,
+                                       hdr->original_size, hdr->packed_size,
+                                       name, method, &read_size);
+                    fclose(tfp);
+                    decode_macbinary(fp, hdr->original_size, name);
+#ifdef __APPLE__
+                    /* TODO: set resource fork */
+                    /* after processing, "Icon\r" is not needed. */
+                    if (strcmp(basename(name), "Icon\r") == 0) {
+                        unlink(name);
+                    }
+#endif /* __APPLE__ */
+                    unlink(temporary_name);
+                } else {
+                    crc = decode_lzhuf(afp, fp,
+                                       hdr->original_size, hdr->packed_size,
+                                       name, method, &read_size);
+                }
+#else /* HAVE_LIBAPPLEFILE */
                 crc = decode_lzhuf(afp, fp,
                                    hdr->original_size, hdr->packed_size,
                                    name, method, &read_size);
+#endif /* HAVE_LIBAPPLEFILE */
                 fclose(fp);
             }
             remove_extracting_file_when_interrupt = FALSE;
@@ -557,3 +628,36 @@ static void adjust_dirinfo()
         }
     }
 }
+
+#if HAVE_LIBAPPLEFILE
+static boolean
+decode_macbinary(ofp, size, outPath)
+    FILE *ofp;
+    size_t size;
+    const char *outPath;
+{
+    af_file_t *afp = NULL;
+    FILE *ifp = NULL;
+    unsigned char *datap;
+    size_t dlen;
+
+    if ((afp = af_open(temporary_name)) != NULL) {
+        /* fetch datafork */
+        datap = af_data(afp, &dlen);
+        fwrite(datap, sizeof(unsigned char), dlen, ofp);
+        af_close(afp);
+        return TRUE;
+    } else { /* it may be not encoded in MacBinary */
+        /* try to copy */
+        if ((ifp = fopen(temporary_name, READ_BINARY)) == NULL) {
+            error("Cannot open a temporary file \"%s\"", temporary_name);
+            return FALSE;
+        }
+        copyfile(ifp, ofp, size, 0, 0);
+        fclose(ifp);
+        return TRUE;
+    }
+
+    return FALSE;
+}
+#endif /* HAVE_LIBAPPLEFILE */
index 81be245..e70b93b 100644 (file)
@@ -66,6 +66,7 @@ unsigned short decode_p_lz5 P_((void));
 void decode_start_lz5 P_((void));
 /* lhadd.c */
 FILE *append_it P_((char *name, FILE *oafp, FILE *nafp));
+FILE *build_temporary_file P_((void));
 void temporary_to_new_archive_file P_((size_t new_archive_size));
 void cmd_add P_((void));
 void cmd_delete P_((void));