/[winpt]/trunk/PTD/wptZIP.cpp
ViewVC logotype

Diff of /trunk/PTD/wptZIP.cpp

Parent Directory Parent Directory | Revision Log Revision Log | View Patch Patch

revision 45 by twoaday, Tue Oct 25 07:46:20 2005 UTC revision 46 by werner, Fri Oct 28 12:57:05 2005 UTC
# Line 1  Line 1 
1  /* wptZIP.cpp  /* wptZIP.cpp
2   *        Copyright (C) 2002-2004 Timo Schulz   *        Copyright (C) 2002-2004 Timo Schulz
3   *   *
4   * This file is part of WinPT.   * This file is part of WinPT.
5   *   *
6   * WinPT is free software; you can redistribute it and/or modify   * WinPT is free software; you can redistribute it and/or modify
7   * it under the terms of the GNU General Public License as published by   * it under the terms of the GNU General Public License as published by
8   * the Free Software Foundation; either version 2 of the License, or   * the Free Software Foundation; either version 2 of the License, or
9   * (at your option) any later version.   * (at your option) any later version.
10   *   *
11   * WinPT is distributed in the hope that it will be useful,   * WinPT is distributed in the hope that it will be useful,
12   * but WITHOUT ANY WARRANTY; without even the implied warranty of   * but WITHOUT ANY WARRANTY; without even the implied warranty of
13   * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the   * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14   * GNU General Public License for more details.   * GNU General Public License for more details.
15   *   *
16   * You should have received a copy of the GNU General Public License   * You should have received a copy of the GNU General Public License
17   * along with PTD; if not, write to the Free Software Foundation,   * along with PTD; if not, write to the Free Software Foundation,
18   * Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA   * Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
19   */   */
20  #include <windows.h>  #ifdef HAVE_CONFIG_H
21  #include <assert.h>  #include <config.h>
22  #include <stdlib.h>  #endif
23  #include <stdio.h>  
24  #include <string.h>  #include <windows.h>
25  #include <sys/stat.h>  #include <windows.h>
26  #include <direct.h>  #include <assert.h>
27  #include <time.h>  #include <stdlib.h>
28    #include <stdio.h>
29  #include "wptZIP.h"  #include <string.h>
30    #include <sys/stat.h>
31  /*static int debug = 0;*/  #include <direct.h>
32    #include <time.h>
33  enum zip_sig_t {  
34      PK_SIG_LOCAL = 0x04034b50,  #include "wptZIP.h"
35      PK_SIG_FILE  = 0x02014b50,  
36      PK_SIG_END   = 0x06054b50  /*static int debug = 0;*/
37  };  
38    enum zip_sig_t {
39  enum zip_flag_t {      PK_SIG_LOCAL = 0x04034b50,
40      PK_FLAG_ENCRYPTED = 1,      /* archive is encrypted. */      PK_SIG_FILE  = 0x02014b50,
41      PK_FLAG_8KDICT    = 2,      /* used 8k dictionary */      PK_SIG_END   = 0x06054b50
42      PK_FLAG_SF        = 4  };
43  };  
44    enum zip_flag_t {
45        PK_FLAG_ENCRYPTED = 1,      /* archive is encrypted. */
46  typedef struct {      PK_FLAG_8KDICT    = 2,      /* used 8k dictionary */
47      unsigned long   magic;      PK_FLAG_SF        = 4
48      unsigned short  ver;  };
49      unsigned short  flags;  
50      unsigned short  method;  
51      unsigned short  ftime;  typedef struct {
52      unsigned short  fdate;      unsigned long   magic;
53      unsigned long   crc;      unsigned short  ver;
54      unsigned long   c_size;      unsigned short  flags;
55      unsigned long   u_size;      unsigned short  method;
56      unsigned short  f_len;      unsigned short  ftime;
57      unsigned short  extra_len;      unsigned short  fdate;
58      char            *name;      unsigned long   crc;
59      FILE            *fp;      unsigned long   c_size;
60  } PK_local_hdr;      unsigned long   u_size;
61        unsigned short  f_len;
62  typedef struct {      unsigned short  extra_len;
63      unsigned long   magic;      char            *name;
64      unsigned short  ver_made;      FILE            *fp;
65      unsigned short  ver_ext;  } PK_local_hdr;
66      unsigned short  flags;  
67      unsigned short  method;  typedef struct {
68      unsigned short  ftime;      unsigned long   magic;
69      unsigned short  fdate;      unsigned short  ver_made;
70      unsigned long   crc;      unsigned short  ver_ext;
71      unsigned long   c_size;      unsigned short  flags;
72      unsigned long   u_size;      unsigned short  method;
73      unsigned short  f_len;      unsigned short  ftime;
74      unsigned short  extra_len;      unsigned short  fdate;
75      unsigned short  comment_len;      unsigned long   crc;
76      unsigned short  disc_nr;      unsigned long   c_size;
77      unsigned short  int_attr;      unsigned long   u_size;
78      unsigned long   ext_attr;      unsigned short  f_len;
79      unsigned long   lochdr_off;      unsigned short  extra_len;
80      char            *name;      unsigned short  comment_len;
81      size_t          size;      unsigned short  disc_nr;
82  } PK_file_hdr;      unsigned short  int_attr;
83        unsigned long   ext_attr;
84        unsigned long   lochdr_off;
85  typedef struct {      char            *name;
86      unsigned long   magic;      size_t          size;
87      unsigned short  disc_nr;  } PK_file_hdr;
88      unsigned short  disc_nr_cd;  
89      unsigned short  total_dirs_disc;  
90      unsigned short  total_dirs;  typedef struct {
91      unsigned long   size_of_dir;      unsigned long   magic;
92      unsigned long   off_dir;      unsigned short  disc_nr;
93      unsigned short  comment_len;      unsigned short  disc_nr_cd;
94      char            *comment;      unsigned short  total_dirs_disc;
95  } PK_end_hdr;      unsigned short  total_dirs;
96        unsigned long   size_of_dir;
97        unsigned long   off_dir;
98  typedef struct {      unsigned short  comment_len;
99      union {      char            *comment;
100          PK_local_hdr *local;  } PK_end_hdr;
101          PK_file_hdr  *file;  
102          PK_end_hdr   *end;  
103      } u;  typedef struct {
104      unsigned long pkttype;      union {
105  } PK_packet;          PK_local_hdr *local;
106            PK_file_hdr  *file;
107            PK_end_hdr   *end;
108  struct PK_file_list {      } u;
109      struct PK_file_list *next;      unsigned long pkttype;
110      PK_local_hdr        *hdr;  } PK_packet;
111      size_t              off;  
112      size_t              len;  
113      char                *d;  struct PK_file_list {
114  };      struct PK_file_list *next;
115        PK_local_hdr        *hdr;
116        size_t              off;
117  static unsigned long crc_table[256] = {      size_t              len;
118      0x00000000L, 0x77073096L, 0xee0e612cL, 0x990951baL, 0x076dc419L,      char                *d;
119      0x706af48fL, 0xe963a535L, 0x9e6495a3L, 0x0edb8832L, 0x79dcb8a4L,  };
120      0xe0d5e91eL, 0x97d2d988L, 0x09b64c2bL, 0x7eb17cbdL, 0xe7b82d07L,  
121      0x90bf1d91L, 0x1db71064L, 0x6ab020f2L, 0xf3b97148L, 0x84be41deL,  
122      0x1adad47dL, 0x6ddde4ebL, 0xf4d4b551L, 0x83d385c7L, 0x136c9856L,  static unsigned long crc_table[256] = {
123      0x646ba8c0L, 0xfd62f97aL, 0x8a65c9ecL, 0x14015c4fL, 0x63066cd9L,      0x00000000L, 0x77073096L, 0xee0e612cL, 0x990951baL, 0x076dc419L,
124      0xfa0f3d63L, 0x8d080df5L, 0x3b6e20c8L, 0x4c69105eL, 0xd56041e4L,      0x706af48fL, 0xe963a535L, 0x9e6495a3L, 0x0edb8832L, 0x79dcb8a4L,
125      0xa2677172L, 0x3c03e4d1L, 0x4b04d447L, 0xd20d85fdL, 0xa50ab56bL,      0xe0d5e91eL, 0x97d2d988L, 0x09b64c2bL, 0x7eb17cbdL, 0xe7b82d07L,
126      0x35b5a8faL, 0x42b2986cL, 0xdbbbc9d6L, 0xacbcf940L, 0x32d86ce3L,      0x90bf1d91L, 0x1db71064L, 0x6ab020f2L, 0xf3b97148L, 0x84be41deL,
127      0x45df5c75L, 0xdcd60dcfL, 0xabd13d59L, 0x26d930acL, 0x51de003aL,      0x1adad47dL, 0x6ddde4ebL, 0xf4d4b551L, 0x83d385c7L, 0x136c9856L,
128      0xc8d75180L, 0xbfd06116L, 0x21b4f4b5L, 0x56b3c423L, 0xcfba9599L,      0x646ba8c0L, 0xfd62f97aL, 0x8a65c9ecL, 0x14015c4fL, 0x63066cd9L,
129      0xb8bda50fL, 0x2802b89eL, 0x5f058808L, 0xc60cd9b2L, 0xb10be924L,      0xfa0f3d63L, 0x8d080df5L, 0x3b6e20c8L, 0x4c69105eL, 0xd56041e4L,
130      0x2f6f7c87L, 0x58684c11L, 0xc1611dabL, 0xb6662d3dL, 0x76dc4190L,      0xa2677172L, 0x3c03e4d1L, 0x4b04d447L, 0xd20d85fdL, 0xa50ab56bL,
131      0x01db7106L, 0x98d220bcL, 0xefd5102aL, 0x71b18589L, 0x06b6b51fL,      0x35b5a8faL, 0x42b2986cL, 0xdbbbc9d6L, 0xacbcf940L, 0x32d86ce3L,
132      0x9fbfe4a5L, 0xe8b8d433L, 0x7807c9a2L, 0x0f00f934L, 0x9609a88eL,      0x45df5c75L, 0xdcd60dcfL, 0xabd13d59L, 0x26d930acL, 0x51de003aL,
133      0xe10e9818L, 0x7f6a0dbbL, 0x086d3d2dL, 0x91646c97L, 0xe6635c01L,      0xc8d75180L, 0xbfd06116L, 0x21b4f4b5L, 0x56b3c423L, 0xcfba9599L,
134      0x6b6b51f4L, 0x1c6c6162L, 0x856530d8L, 0xf262004eL, 0x6c0695edL,      0xb8bda50fL, 0x2802b89eL, 0x5f058808L, 0xc60cd9b2L, 0xb10be924L,
135      0x1b01a57bL, 0x8208f4c1L, 0xf50fc457L, 0x65b0d9c6L, 0x12b7e950L,      0x2f6f7c87L, 0x58684c11L, 0xc1611dabL, 0xb6662d3dL, 0x76dc4190L,
136      0x8bbeb8eaL, 0xfcb9887cL, 0x62dd1ddfL, 0x15da2d49L, 0x8cd37cf3L,      0x01db7106L, 0x98d220bcL, 0xefd5102aL, 0x71b18589L, 0x06b6b51fL,
137      0xfbd44c65L, 0x4db26158L, 0x3ab551ceL, 0xa3bc0074L, 0xd4bb30e2L,      0x9fbfe4a5L, 0xe8b8d433L, 0x7807c9a2L, 0x0f00f934L, 0x9609a88eL,
138      0x4adfa541L, 0x3dd895d7L, 0xa4d1c46dL, 0xd3d6f4fbL, 0x4369e96aL,      0xe10e9818L, 0x7f6a0dbbL, 0x086d3d2dL, 0x91646c97L, 0xe6635c01L,
139      0x346ed9fcL, 0xad678846L, 0xda60b8d0L, 0x44042d73L, 0x33031de5L,      0x6b6b51f4L, 0x1c6c6162L, 0x856530d8L, 0xf262004eL, 0x6c0695edL,
140      0xaa0a4c5fL, 0xdd0d7cc9L, 0x5005713cL, 0x270241aaL, 0xbe0b1010L,      0x1b01a57bL, 0x8208f4c1L, 0xf50fc457L, 0x65b0d9c6L, 0x12b7e950L,
141      0xc90c2086L, 0x5768b525L, 0x206f85b3L, 0xb966d409L, 0xce61e49fL,      0x8bbeb8eaL, 0xfcb9887cL, 0x62dd1ddfL, 0x15da2d49L, 0x8cd37cf3L,
142      0x5edef90eL, 0x29d9c998L, 0xb0d09822L, 0xc7d7a8b4L, 0x59b33d17L,      0xfbd44c65L, 0x4db26158L, 0x3ab551ceL, 0xa3bc0074L, 0xd4bb30e2L,
143      0x2eb40d81L, 0xb7bd5c3bL, 0xc0ba6cadL, 0xedb88320L, 0x9abfb3b6L,      0x4adfa541L, 0x3dd895d7L, 0xa4d1c46dL, 0xd3d6f4fbL, 0x4369e96aL,
144      0x03b6e20cL, 0x74b1d29aL, 0xead54739L, 0x9dd277afL, 0x04db2615L,      0x346ed9fcL, 0xad678846L, 0xda60b8d0L, 0x44042d73L, 0x33031de5L,
145      0x73dc1683L, 0xe3630b12L, 0x94643b84L, 0x0d6d6a3eL, 0x7a6a5aa8L,      0xaa0a4c5fL, 0xdd0d7cc9L, 0x5005713cL, 0x270241aaL, 0xbe0b1010L,
146      0xe40ecf0bL, 0x9309ff9dL, 0x0a00ae27L, 0x7d079eb1L, 0xf00f9344L,      0xc90c2086L, 0x5768b525L, 0x206f85b3L, 0xb966d409L, 0xce61e49fL,
147      0x8708a3d2L, 0x1e01f268L, 0x6906c2feL, 0xf762575dL, 0x806567cbL,      0x5edef90eL, 0x29d9c998L, 0xb0d09822L, 0xc7d7a8b4L, 0x59b33d17L,
148      0x196c3671L, 0x6e6b06e7L, 0xfed41b76L, 0x89d32be0L, 0x10da7a5aL,      0x2eb40d81L, 0xb7bd5c3bL, 0xc0ba6cadL, 0xedb88320L, 0x9abfb3b6L,
149      0x67dd4accL, 0xf9b9df6fL, 0x8ebeeff9L, 0x17b7be43L, 0x60b08ed5L,      0x03b6e20cL, 0x74b1d29aL, 0xead54739L, 0x9dd277afL, 0x04db2615L,
150      0xd6d6a3e8L, 0xa1d1937eL, 0x38d8c2c4L, 0x4fdff252L, 0xd1bb67f1L,      0x73dc1683L, 0xe3630b12L, 0x94643b84L, 0x0d6d6a3eL, 0x7a6a5aa8L,
151      0xa6bc5767L, 0x3fb506ddL, 0x48b2364bL, 0xd80d2bdaL, 0xaf0a1b4cL,      0xe40ecf0bL, 0x9309ff9dL, 0x0a00ae27L, 0x7d079eb1L, 0xf00f9344L,
152      0x36034af6L, 0x41047a60L, 0xdf60efc3L, 0xa867df55L, 0x316e8eefL,      0x8708a3d2L, 0x1e01f268L, 0x6906c2feL, 0xf762575dL, 0x806567cbL,
153      0x4669be79L, 0xcb61b38cL, 0xbc66831aL, 0x256fd2a0L, 0x5268e236L,      0x196c3671L, 0x6e6b06e7L, 0xfed41b76L, 0x89d32be0L, 0x10da7a5aL,
154      0xcc0c7795L, 0xbb0b4703L, 0x220216b9L, 0x5505262fL, 0xc5ba3bbeL,      0x67dd4accL, 0xf9b9df6fL, 0x8ebeeff9L, 0x17b7be43L, 0x60b08ed5L,
155      0xb2bd0b28L, 0x2bb45a92L, 0x5cb36a04L, 0xc2d7ffa7L, 0xb5d0cf31L,      0xd6d6a3e8L, 0xa1d1937eL, 0x38d8c2c4L, 0x4fdff252L, 0xd1bb67f1L,
156      0x2cd99e8bL, 0x5bdeae1dL, 0x9b64c2b0L, 0xec63f226L, 0x756aa39cL,      0xa6bc5767L, 0x3fb506ddL, 0x48b2364bL, 0xd80d2bdaL, 0xaf0a1b4cL,
157      0x026d930aL, 0x9c0906a9L, 0xeb0e363fL, 0x72076785L, 0x05005713L,      0x36034af6L, 0x41047a60L, 0xdf60efc3L, 0xa867df55L, 0x316e8eefL,
158      0x95bf4a82L, 0xe2b87a14L, 0x7bb12baeL, 0x0cb61b38L, 0x92d28e9bL,      0x4669be79L, 0xcb61b38cL, 0xbc66831aL, 0x256fd2a0L, 0x5268e236L,
159      0xe5d5be0dL, 0x7cdcefb7L, 0x0bdbdf21L, 0x86d3d2d4L, 0xf1d4e242L,      0xcc0c7795L, 0xbb0b4703L, 0x220216b9L, 0x5505262fL, 0xc5ba3bbeL,
160      0x68ddb3f8L, 0x1fda836eL, 0x81be16cdL, 0xf6b9265bL, 0x6fb077e1L,      0xb2bd0b28L, 0x2bb45a92L, 0x5cb36a04L, 0xc2d7ffa7L, 0xb5d0cf31L,
161      0x18b74777L, 0x88085ae6L, 0xff0f6a70L, 0x66063bcaL, 0x11010b5cL,      0x2cd99e8bL, 0x5bdeae1dL, 0x9b64c2b0L, 0xec63f226L, 0x756aa39cL,
162      0x8f659effL, 0xf862ae69L, 0x616bffd3L, 0x166ccf45L, 0xa00ae278L,      0x026d930aL, 0x9c0906a9L, 0xeb0e363fL, 0x72076785L, 0x05005713L,
163      0xd70dd2eeL, 0x4e048354L, 0x3903b3c2L, 0xa7672661L, 0xd06016f7L,      0x95bf4a82L, 0xe2b87a14L, 0x7bb12baeL, 0x0cb61b38L, 0x92d28e9bL,
164      0x4969474dL, 0x3e6e77dbL, 0xaed16a4aL, 0xd9d65adcL, 0x40df0b66L,      0xe5d5be0dL, 0x7cdcefb7L, 0x0bdbdf21L, 0x86d3d2d4L, 0xf1d4e242L,
165      0x37d83bf0L, 0xa9bcae53L, 0xdebb9ec5L, 0x47b2cf7fL, 0x30b5ffe9L,      0x68ddb3f8L, 0x1fda836eL, 0x81be16cdL, 0xf6b9265bL, 0x6fb077e1L,
166      0xbdbdf21cL, 0xcabac28aL, 0x53b39330L, 0x24b4a3a6L, 0xbad03605L,      0x18b74777L, 0x88085ae6L, 0xff0f6a70L, 0x66063bcaL, 0x11010b5cL,
167      0xcdd70693L, 0x54de5729L, 0x23d967bfL, 0xb3667a2eL, 0xc4614ab8L,      0x8f659effL, 0xf862ae69L, 0x616bffd3L, 0x166ccf45L, 0xa00ae278L,
168      0x5d681b02L, 0x2a6f2b94L, 0xb40bbe37L, 0xc30c8ea1L, 0x5a05df1bL,      0xd70dd2eeL, 0x4e048354L, 0x3903b3c2L, 0xa7672661L, 0xd06016f7L,
169      0x2d02ef8dL      0x4969474dL, 0x3e6e77dbL, 0xaed16a4aL, 0xd9d65adcL, 0x40df0b66L,
170  };      0x37d83bf0L, 0xa9bcae53L, 0xdebb9ec5L, 0x47b2cf7fL, 0x30b5ffe9L,
171        0xbdbdf21cL, 0xcabac28aL, 0x53b39330L, 0x24b4a3a6L, 0xbad03605L,
172        0xcdd70693L, 0x54de5729L, 0x23d967bfL, 0xb3667a2eL, 0xc4614ab8L,
173  /* Update the crc in @crc with the buffer @buf and the length @buflen. */      0x5d681b02L, 0x2a6f2b94L, 0xb40bbe37L, 0xc30c8ea1L, 0x5a05df1bL,
174  static unsigned long      0x2d02ef8dL
175  update_crc (unsigned long crc, unsigned char *buf, size_t buflen)  };
176  {  
177      crc ^= 0xffffffffL;  
178      while (buflen--)  /* Update the crc in @crc with the buffer @buf and the length @buflen. */
179          crc = crc_table[((int)(crc) ^ (*buf++)) & 0xff] ^ ((crc) >> 8);  static unsigned long
180      crc ^= 0xffffffffL;  update_crc (unsigned long crc, unsigned char *buf, size_t buflen)
181      return crc;  {
182  }      crc ^= 0xffffffffL;
183        while (buflen--)
184                    crc = crc_table[((int)(crc) ^ (*buf++)) & 0xff] ^ ((crc) >> 8);
185  static unsigned short      crc ^= 0xffffffffL;
186  read_16 (FILE *in)      return crc;
187  {  }
188      unsigned short u;  
189      u  = fgetc (in)     ;          
190      u |= fgetc (in) << 8;  static unsigned short
191      return u;  read_16 (FILE *in)
192  }  {
193        unsigned short u;
194        u  = fgetc (in)     ;
195  static void      u |= fgetc (in) << 8;
196  write_16 (FILE *out, unsigned short a)      return u;
197  {  }
198      fputc (a     , out);  
199      fputc (a >> 8, out);  
200  }  static void
201    write_16 (FILE *out, unsigned short a)
202    {
203  static unsigned long      fputc (a     , out);
204  read_32 (FILE *in)      fputc (a >> 8, out);
205  {  }
206      unsigned long u;  
207      u  = fgetc (in)      ;  
208      u |= fgetc (in) <<  8;  static unsigned long
209      u |= fgetc (in) << 16;  read_32 (FILE *in)
210      u |= fgetc (in) << 24;  {
211      return u;      unsigned long u;
212  }      u  = fgetc (in)      ;
213        u |= fgetc (in) <<  8;
214        u |= fgetc (in) << 16;
215  static void      u |= fgetc (in) << 24;
216  write_32 (FILE * out, unsigned long a)      return u;
217  {  }
218      fputc (a      , out);  
219      fputc (a >> 8 , out);  
220      fputc (a >> 16, out);  static void
221      fputc (a >> 24, out);  write_32 (FILE * out, unsigned long a)
222  }  {
223        fputc (a      , out);
224        fputc (a >> 8 , out);
225  static unsigned short      fputc (a >> 16, out);
226  date_to_dos (time_t t)      fputc (a >> 24, out);
227  {  }
228      struct tm * tm;  
229      tm = localtime (&t);  
230      return tm->tm_mday | (tm->tm_mon+1)<<5 | ((tm->tm_year-80)<<9);  static unsigned short
231  }  date_to_dos (time_t t)
232    {
233        struct tm * tm;
234  static unsigned short      tm = localtime (&t);
235  time_to_dos (time_t t)      return tm->tm_mday | (tm->tm_mon+1)<<5 | ((tm->tm_year-80)<<9);
236  {  }
237      struct tm * tm;  
238      tm = localtime (&t);  
239      return (tm->tm_hour<<11) | (tm->tm_min<<5) | (tm->tm_sec>>1);  static unsigned short
240  }  time_to_dos (time_t t)
241    {
242        struct tm * tm;
243  static char*      tm = localtime (&t);
244  xstrdup (const char * s)      return (tm->tm_hour<<11) | (tm->tm_min<<5) | (tm->tm_sec>>1);
245  {  }
246      char *p = new char[strlen (s)+1];  
247      if (!p)  
248          abort ();  static char*
249      strcpy (p, s);  xstrdup (const char * s)
250      return p;  {
251  }      char *p = new char[strlen (s)+1];
252        if (!p)
253            abort ();
254  static PK_local_hdr*      strcpy (p, s);
255  create_local_header (const char *name, FILE *fp)      return p;
256  {  }
257      struct stat statbuf;  
258      PK_local_hdr *a;  
259    static PK_local_hdr*
260      if (fstat (fileno (fp), &statbuf))  create_local_header (const char *name, FILE *fp)
261          return NULL;  {
262      a = new PK_local_hdr;      struct stat statbuf;
263      if (!a)      PK_local_hdr *a;
264          return NULL;  
265      memset (a, 0, sizeof *a);      if (fstat (fileno (fp), &statbuf))
266      a->magic = PK_SIG_LOCAL;          return NULL;
267      a->ver = 0 | (10 << 8);      a = new PK_local_hdr;
268      a->flags = 0;      if (!a)
269      a->method = 0;          return NULL;
270      a->fdate = date_to_dos (statbuf.st_mtime);      memset (a, 0, sizeof *a);
271      a->ftime = time_to_dos (statbuf.st_mtime);      a->magic = PK_SIG_LOCAL;
272      a->crc = 0;      a->ver = 0 | (10 << 8);
273      a->c_size = statbuf.st_size;      a->flags = 0;
274      a->u_size = statbuf.st_size;      a->method = 0;
275      a->f_len = strlen (name);      a->fdate = date_to_dos (statbuf.st_mtime);
276      a->name = xstrdup (name);      a->ftime = time_to_dos (statbuf.st_mtime);
277      a->extra_len = 0;      a->crc = 0;
278      a->fp = fp;      a->c_size = statbuf.st_size;
279      return a;      a->u_size = statbuf.st_size;
280  }      a->f_len = strlen (name);
281        a->name = xstrdup (name);
282        a->extra_len = 0;
283  static int      a->fp = fp;
284  write_local_header (FILE *out, PK_local_hdr *hdr)      return a;
285  {  }
286      long crc_pos = 0, curr_pos = 0;  
287        
288      write_32 (out, hdr->magic);  static int
289      write_16 (out, hdr->ver);  write_local_header (FILE *out, PK_local_hdr *hdr)
290      write_16 (out, hdr->flags);  {
291      write_16 (out, hdr->method);      long crc_pos = 0, curr_pos = 0;
292      write_16 (out, hdr->ftime);      
293      write_16 (out, hdr->fdate);      write_32 (out, hdr->magic);
294      crc_pos = ftell (out);      write_16 (out, hdr->ver);
295      write_32 (out, hdr->crc);      write_16 (out, hdr->flags);
296      write_32 (out, hdr->c_size);      write_16 (out, hdr->method);
297      write_32 (out, hdr->u_size);      write_16 (out, hdr->ftime);
298      write_16 (out, hdr->f_len);      write_16 (out, hdr->fdate);
299      write_16 (out, hdr->extra_len);      crc_pos = ftell (out);
300      if (hdr->f_len > 0)      write_32 (out, hdr->crc);
301          fwrite (hdr->name, 1, hdr->f_len, out);      write_32 (out, hdr->c_size);
302      if (hdr->extra_len)      write_32 (out, hdr->u_size);
303          fwrite (NULL, 1, hdr->extra_len, out); /* xxx */      write_16 (out, hdr->f_len);
304      while (!feof (hdr->fp)) {      write_16 (out, hdr->extra_len);
305          unsigned char buf[2048];      if (hdr->f_len > 0)
306          unsigned long nread;          fwrite (hdr->name, 1, hdr->f_len, out);
307          nread = fread (buf, 1, sizeof buf-1, hdr->fp);      if (hdr->extra_len)
308          if (nread > 0) {          fwrite (NULL, 1, hdr->extra_len, out); /* xxx */
309              /*fprintf (stderr, "** nread=%d\n", nread);*/      while (!feof (hdr->fp)) {
310              hdr->crc = update_crc (hdr->crc, buf, nread);          unsigned char buf[2048];
311              fwrite (buf, 1, nread, out);          unsigned long nread;
312          }          nread = fread (buf, 1, sizeof buf-1, hdr->fp);
313      }          if (nread > 0) {
314      curr_pos = ftell (out);              /*fprintf (stderr, "** nread=%d\n", nread);*/
315      fseek (out, crc_pos, SEEK_SET);              hdr->crc = update_crc (hdr->crc, buf, nread);
316      write_32 (out, hdr->crc);              fwrite (buf, 1, nread, out);
317      fseek (out, curr_pos, SEEK_SET);          }
318      return 0;      }
319  }      curr_pos = ftell (out);
320        fseek (out, crc_pos, SEEK_SET);
321        write_32 (out, hdr->crc);
322  static int      fseek (out, curr_pos, SEEK_SET);
323  create_missing_dirs (const char *name)      return 0;
324  {  }
325      struct stat dirbuf;  
326      char *p, *dir;  
327      int rc;  static int
328        create_missing_dirs (const char *name)
329      p = strrchr (name, '/');  {
330      if (!p)      struct stat dirbuf;
331          return PKERR_GENERAL;      char *p, *dir;
332      dir = new char[(p-name)+1];      int rc;
333      if (!dir)      
334          abort ();      p = strrchr (name, '/');
335      memset (dir, 0, (p-name)+1);      if (!p)
336      strncpy (dir, name, (p-name));          return PKERR_GENERAL;
337      if (!stat (dir, &dirbuf) && (dirbuf.st_mode & _S_IFDIR))      dir = new char[(p-name)+1];
338          rc = 0;      if (!dir)
339      else          abort ();
340          rc = mkdir (dir);      memset (dir, 0, (p-name)+1);
341      delete []dir;      strncpy (dir, name, (p-name));
342      return rc;      if (!stat (dir, &dirbuf) && (dirbuf.st_mode & _S_IFDIR))
343  }          rc = 0;
344        else
345            rc = mkdir (dir);
346  static PK_local_hdr*      delete []dir;
347  read_local_header (FILE *in, unsigned long magic, int create)      return rc;
348  {  }
349      PK_local_hdr *hdr;  
350      FILE *out = NULL;  
351      size_t n;  static PK_local_hdr*
352    read_local_header (FILE *in, unsigned long magic, int create)
353      if (magic != PK_SIG_LOCAL)  {
354          return NULL;      PK_local_hdr *hdr;
355      hdr = new PK_local_hdr;      FILE *out = NULL;
356      if (!hdr)      size_t n;
357          return NULL;  
358      memset (hdr, 0, sizeof * hdr);      if (magic != PK_SIG_LOCAL)
359      hdr->magic = magic;          return NULL;
360      hdr->ver = read_16 (in);      hdr = new PK_local_hdr;
361      hdr->flags = read_16 (in);      if (!hdr)
362      hdr->method = read_16 (in);          return NULL;
363      hdr->ftime = read_16 (in);      memset (hdr, 0, sizeof * hdr);
364      hdr->fdate = read_16 (in);      hdr->magic = magic;
365      hdr->crc = read_32 (in);      hdr->ver = read_16 (in);
366      hdr->c_size = read_32 (in);      hdr->flags = read_16 (in);
367      hdr->u_size = read_32 (in);      hdr->method = read_16 (in);
368      hdr->f_len = read_16 (in);      hdr->ftime = read_16 (in);
369      hdr->extra_len = read_16 (in);      hdr->fdate = read_16 (in);
370        hdr->crc = read_32 (in);
371      /*if( debug ) {      hdr->c_size = read_32 (in);
372          printf("=====BEGIN LOCAL HEADER=====\n");      hdr->u_size = read_32 (in);
373          printf( "magic %08lX version=%d\n", hdr->magic, hdr->ver );      hdr->f_len = read_16 (in);
374          printf( "flags encrypted=%d 8k dict=%d shannon=%d\n",      hdr->extra_len = read_16 (in);
375                  hdr->flags & PK_FLAG_ENCRYPTED, hdr->flags & PK_FLAG_8KDICT,  
376                  hdr->flags & PK_FLAG_SF );      /*if( debug ) {
377          printf( "method=" );          printf("=====BEGIN LOCAL HEADER=====\n");
378          switch( hdr->method ) {          printf( "magic %08lX version=%d\n", hdr->magic, hdr->ver );
379          case 0: printf( "stored\n" ); break;          printf( "flags encrypted=%d 8k dict=%d shannon=%d\n",
380          default: printf( "unknown (%d)\n", hdr->method );                  hdr->flags & PK_FLAG_ENCRYPTED, hdr->flags & PK_FLAG_8KDICT,
381          }                  hdr->flags & PK_FLAG_SF );
382          printf( "filetime=%d %d\n", hdr->ftime, hdr->fdate );          printf( "method=" );
383          printf( "CRC=%08lX\n", hdr->crc );          switch( hdr->method ) {
384          printf( "size: compressed=%lu uncompressed=%lu\n",          case 0: printf( "stored\n" ); break;
385                  hdr->c_size, hdr->u_size );          default: printf( "unknown (%d)\n", hdr->method );
386          printf( "filename len=%d extra_len=%d\n", hdr->f_len, hdr->extra_len );          }
387      }*/          printf( "filetime=%d %d\n", hdr->ftime, hdr->fdate );
388            printf( "CRC=%08lX\n", hdr->crc );
389      if (hdr->f_len) {          printf( "size: compressed=%lu uncompressed=%lu\n",
390          hdr->name = new char[hdr->f_len+1];                  hdr->c_size, hdr->u_size );
391          if (!hdr->name)          printf( "filename len=%d extra_len=%d\n", hdr->f_len, hdr->extra_len );
392              abort ();      }*/
393          memset (hdr->name, 0, hdr->f_len+1);  
394          fread (hdr->name, 1, hdr->f_len, in);      if (hdr->f_len) {
395          /*if (debug)          hdr->name = new char[hdr->f_len+1];
396              printf ("filename %s\n", hdr->name);*/          if (!hdr->name)
397      }              abort ();
398      /*if (debug)          memset (hdr->name, 0, hdr->f_len+1);
399          printf ("skip extra header (%d)\n", hdr->extra_len);*/          fread (hdr->name, 1, hdr->f_len, in);
400      n = hdr->extra_len;          /*if (debug)
401      while (n--)              printf ("filename %s\n", hdr->name);*/
402          fgetc (in);      }
403      /*if (debug)      /*if (debug)
404          printf ("skip compressed data (%lu)\n", hdr->c_size);*/          printf ("skip extra header (%d)\n", hdr->extra_len);*/
405      if (create && hdr->name) {      n = hdr->extra_len;
406          create_missing_dirs (hdr->name);      while (n--)
407          out = fopen (hdr->name, "wb");          fgetc (in);
408          /*if (debug)      /*if (debug)
409              printf( "create output `%s' (status %s)\n", hdr->name,          printf ("skip compressed data (%lu)\n", hdr->c_size);*/
410                      out? "success" : "failed" );*/      if (create && hdr->name) {
411      }          create_missing_dirs (hdr->name);
412      n = hdr->c_size;          out = fopen (hdr->name, "wb");
413      while (n--) {          /*if (debug)
414          int c = fgetc (in);              printf( "create output `%s' (status %s)\n", hdr->name,
415          if (out)                      out? "success" : "failed" );*/
416              fputc (c, out);      }
417      }      n = hdr->c_size;
418      if (out)      while (n--) {
419          fclose (out);          int c = fgetc (in);
420      return hdr;          if (out)
421  }              fputc (c, out);
422        }
423        if (out)
424  static PK_file_hdr*          fclose (out);
425  create_file_header (PK_local_hdr * loc, long loc_off)      return hdr;
426  {  }
427      PK_file_hdr * a;  
428        
429      a = new PK_file_hdr;  static PK_file_hdr*
430      if (!a)  create_file_header (PK_local_hdr * loc, long loc_off)
431          abort ();  {
432      memset (a, 0, sizeof *a);      PK_file_hdr * a;
433      a->magic = PK_SIG_FILE;      
434      a->ver_made = loc->ver;      a = new PK_file_hdr;
435      a->ver_ext = loc->ver;      if (!a)
436      a->flags = loc->flags;          abort ();
437      a->method = loc->method;      memset (a, 0, sizeof *a);
438      a->ftime = loc->ftime;      a->magic = PK_SIG_FILE;
439      a->fdate = loc->fdate;      a->ver_made = loc->ver;
440      a->crc = loc->crc;      a->ver_ext = loc->ver;
441      a->c_size = loc->c_size;      a->flags = loc->flags;
442      a->u_size = loc->u_size;      a->method = loc->method;
443      a->f_len = loc->f_len;      a->ftime = loc->ftime;
444      a->extra_len = loc->extra_len;      a->fdate = loc->fdate;
445      a->comment_len = 0;      a->crc = loc->crc;
446      a->disc_nr = 0;      a->c_size = loc->c_size;
447      a->int_attr = 0;      a->u_size = loc->u_size;
448      a->ext_attr = 0;      a->f_len = loc->f_len;
449      a->lochdr_off = loc_off;      a->extra_len = loc->extra_len;
450      a->size = 46 + a->f_len;      a->comment_len = 0;
451      a->name = xstrdup (loc->name);      a->disc_nr = 0;
452      return a;      a->int_attr = 0;
453  }      a->ext_attr = 0;
454        a->lochdr_off = loc_off;
455        a->size = 46 + a->f_len;
456  static int      a->name = xstrdup (loc->name);
457  write_file_header (FILE *out, PK_file_hdr *hdr)      return a;
458  {  }
459      write_32 (out, hdr->magic);  
460      write_16 (out, hdr->ver_made);  
461      write_16 (out, hdr->ver_ext);  static int
462      write_16 (out, hdr->flags);  write_file_header (FILE *out, PK_file_hdr *hdr)
463      write_16 (out, hdr->method);  {
464      write_16 (out, hdr->ftime);      write_32 (out, hdr->magic);
465      write_16 (out, hdr->fdate);      write_16 (out, hdr->ver_made);
466      write_32 (out, hdr->crc);      write_16 (out, hdr->ver_ext);
467      write_32 (out, hdr->c_size);      write_16 (out, hdr->flags);
468      write_32 (out, hdr->u_size);      write_16 (out, hdr->method);
469      write_16 (out, hdr->f_len);      write_16 (out, hdr->ftime);
470      write_16 (out, hdr->extra_len);      write_16 (out, hdr->fdate);
471      write_16 (out, hdr->comment_len);      write_32 (out, hdr->crc);
472      write_16 (out, hdr->disc_nr);      write_32 (out, hdr->c_size);
473      write_16 (out, hdr->int_attr);      write_32 (out, hdr->u_size);
474      write_32 (out, hdr->ext_attr);      write_16 (out, hdr->f_len);
475      write_32 (out, hdr->lochdr_off);      write_16 (out, hdr->extra_len);
476      if (hdr->f_len > 0)      write_16 (out, hdr->comment_len);
477          fwrite (hdr->name, 1, hdr->f_len, out);      write_16 (out, hdr->disc_nr);
478      if (hdr->extra_len > 0)      write_16 (out, hdr->int_attr);
479          fwrite (NULL, 1, hdr->extra_len, out); /* xxx */      write_32 (out, hdr->ext_attr);
480      if (hdr->comment_len > 0)      write_32 (out, hdr->lochdr_off);
481          fwrite (NULL, 1, hdr->comment_len, out); /* xxx */      if (hdr->f_len > 0)
482      return 0;          fwrite (hdr->name, 1, hdr->f_len, out);
483  }      if (hdr->extra_len > 0)
484                fwrite (NULL, 1, hdr->extra_len, out); /* xxx */
485        if (hdr->comment_len > 0)
486  static PK_file_hdr*          fwrite (NULL, 1, hdr->comment_len, out); /* xxx */
487  read_file_header (FILE * in, unsigned long magic)      return 0;
488  {  }
489      PK_file_hdr * hdr;      
490      size_t n;  
491    static PK_file_hdr*
492      if (magic != PK_SIG_FILE)  read_file_header (FILE * in, unsigned long magic)
493          return NULL;  {
494      hdr = new PK_file_hdr;      PK_file_hdr * hdr;
495      if (!hdr)      size_t n;
496          return NULL;  
497      memset (hdr, 0, sizeof * hdr);      if (magic != PK_SIG_FILE)
498      hdr->magic = magic;          return NULL;
499      hdr->ver_made = read_16( in );      hdr = new PK_file_hdr;
500      hdr->ver_ext = read_16( in );      if (!hdr)
501      hdr->flags = read_16( in );          return NULL;
502      hdr->method = read_16( in );      memset (hdr, 0, sizeof * hdr);
503      hdr->ftime = read_16( in );      hdr->magic = magic;
504      hdr->fdate = read_16( in );      hdr->ver_made = read_16( in );
505      hdr->crc = read_32( in );      hdr->ver_ext = read_16( in );
506      hdr->c_size = read_32( in );      hdr->flags = read_16( in );
507      hdr->u_size = read_32( in );      hdr->method = read_16( in );
508      hdr->f_len = read_16( in );      hdr->ftime = read_16( in );
509      hdr->extra_len = read_16( in );      hdr->fdate = read_16( in );
510      hdr->comment_len = read_16( in );      hdr->crc = read_32( in );
511      hdr->disc_nr = read_16( in );      hdr->c_size = read_32( in );
512      hdr->int_attr = read_16( in );      hdr->u_size = read_32( in );
513      hdr->ext_attr = read_32( in );      hdr->f_len = read_16( in );
514      hdr->lochdr_off = read_32( in );      hdr->extra_len = read_16( in );
515        hdr->comment_len = read_16( in );
516      /*if( debug ) {      hdr->disc_nr = read_16( in );
517          printf("=====BEGIN FILE HEADER=====\n");      hdr->int_attr = read_16( in );
518          printf( "magic=%08lX\n", hdr->magic );      hdr->ext_attr = read_32( in );
519          printf( "version made=%d needed=%d\n", hdr->ver_made, hdr->ver_ext );      hdr->lochdr_off = read_32( in );
520          printf( "flags encrypted=%d endheader=%d extended=%d\n",  
521                  hdr->flags & PK_FLAG_ENCRYPTED, hdr->flags & PK_FLAG_8KDICT,      /*if( debug ) {
522                  hdr->flags & PK_FLAG_SF );          printf("=====BEGIN FILE HEADER=====\n");
523          printf( "method=" );          printf( "magic=%08lX\n", hdr->magic );
524          switch( hdr->method ) {          printf( "version made=%d needed=%d\n", hdr->ver_made, hdr->ver_ext );
525          case 0: printf( "stored\n" ); break;          printf( "flags encrypted=%d endheader=%d extended=%d\n",
526          default: printf( "unknown (%d)\n", hdr->method );                    hdr->flags & PK_FLAG_ENCRYPTED, hdr->flags & PK_FLAG_8KDICT,
527          }                  hdr->flags & PK_FLAG_SF );
528          printf( "filetime=%d %d\n", hdr->ftime, hdr->fdate );          printf( "method=" );
529          printf( "CRC=%08lX\n", hdr->crc );          switch( hdr->method ) {
530          printf( "size compressed=%lu uncompressed=%lu\n",          case 0: printf( "stored\n" ); break;
531                  hdr->c_size, hdr->u_size );          default: printf( "unknown (%d)\n", hdr->method );  
532          printf( "extra len=%d comment len=%d\n", hdr->extra_len,          }
533                  hdr->comment_len );          printf( "filetime=%d %d\n", hdr->ftime, hdr->fdate );
534          printf( "disk nummer=%d\n", hdr->disc_nr );          printf( "CRC=%08lX\n", hdr->crc );
535          printf( "attrs intern=%d extern=%lu\n", hdr->int_attr, hdr->ext_attr );          printf( "size compressed=%lu uncompressed=%lu\n",
536          printf( "disk offset=%lu\n", hdr->lochdr_off );                  hdr->c_size, hdr->u_size );
537      }*/          printf( "extra len=%d comment len=%d\n", hdr->extra_len,
538                        hdr->comment_len );
539      if (hdr->f_len > 0) {          printf( "disk nummer=%d\n", hdr->disc_nr );
540          hdr->name = new char[hdr->f_len + 1];          printf( "attrs intern=%d extern=%lu\n", hdr->int_attr, hdr->ext_attr );
541          if (!hdr->name)          printf( "disk offset=%lu\n", hdr->lochdr_off );
542              abort ();      }*/
543          memset (hdr->name, 0, hdr->f_len+1);      
544          fread (hdr->name, 1, hdr->f_len, in);      if (hdr->f_len > 0) {
545          /*if( debug )          hdr->name = new char[hdr->f_len + 1];
546              printf( "filename=%s\n", hdr->name );*/          if (!hdr->name)
547      }              abort ();
548      n = hdr->extra_len;          memset (hdr->name, 0, hdr->f_len+1);
549      while (n--)          fread (hdr->name, 1, hdr->f_len, in);
550          fgetc (in);          /*if( debug )
551      n = hdr->comment_len;              printf( "filename=%s\n", hdr->name );*/
552      while (n--)      }
553          fgetc (in);      n = hdr->extra_len;
554      return hdr;      while (n--)
555  }          fgetc (in);
556        n = hdr->comment_len;
557        while (n--)
558  static PK_end_hdr*          fgetc (in);
559  create_end_header (size_t ntotal, size_t nsize, long off_dir)      return hdr;
560  {  }
561      PK_end_hdr *a;  
562    
563      a = new PK_end_hdr;  static PK_end_hdr*
564      if (!a)  create_end_header (size_t ntotal, size_t nsize, long off_dir)
565          abort ();  {
566      memset (a, 0, sizeof * a);      PK_end_hdr *a;
567      a->magic = PK_SIG_END;  
568      a->disc_nr = 0;      a = new PK_end_hdr;
569      a->disc_nr_cd = 0;      if (!a)
570      a->total_dirs = ntotal;          abort ();
571      a->total_dirs_disc = ntotal;      memset (a, 0, sizeof * a);
572      a->size_of_dir = nsize;      a->magic = PK_SIG_END;
573      a->off_dir = off_dir;      a->disc_nr = 0;
574      a->comment_len = 0;      a->disc_nr_cd = 0;
575      return a;      a->total_dirs = ntotal;
576  }      a->total_dirs_disc = ntotal;
577        a->size_of_dir = nsize;
578        a->off_dir = off_dir;
579  static int      a->comment_len = 0;
580  write_end_header (FILE *out, PK_end_hdr *hdr)      return a;
581  {  }
582      write_32 (out, hdr->magic);  
583      write_16 (out, hdr->disc_nr);  
584      write_16 (out, hdr->disc_nr_cd);  static int
585      write_16 (out, hdr->total_dirs);  write_end_header (FILE *out, PK_end_hdr *hdr)
586      write_16 (out, hdr->total_dirs_disc);  {
587      write_32 (out, hdr->size_of_dir);      write_32 (out, hdr->magic);
588      write_32 (out, hdr->off_dir);      write_16 (out, hdr->disc_nr);
589      write_16 (out, hdr->comment_len);      write_16 (out, hdr->disc_nr_cd);
590      if (hdr->comment_len > 0)      write_16 (out, hdr->total_dirs);
591          fwrite (hdr->comment, 1, hdr->comment_len, out);      write_16 (out, hdr->total_dirs_disc);
592      return 0;      write_32 (out, hdr->size_of_dir);
593  }      write_32 (out, hdr->off_dir);
594        write_16 (out, hdr->comment_len);
595        if (hdr->comment_len > 0)
596  static PK_end_hdr*          fwrite (hdr->comment, 1, hdr->comment_len, out);
597  read_end_header (FILE * in, unsigned long magic)      return 0;
598  {  }
599      PK_end_hdr * hdr;  
600    
601      if( magic != PK_SIG_END )  static PK_end_hdr*
602          return NULL;  read_end_header (FILE * in, unsigned long magic)
603      hdr = new PK_end_hdr;  {
604      if( !hdr )      PK_end_hdr * hdr;
605          abort ();  
606      memset (hdr, 0, sizeof *hdr);      if( magic != PK_SIG_END )
607      hdr->magic = magic;          return NULL;
608      hdr->disc_nr = read_16( in );      hdr = new PK_end_hdr;
609      hdr->disc_nr_cd = read_16( in );      if( !hdr )
610      hdr->total_dirs = read_16( in );          abort ();
611      hdr->total_dirs_disc = read_16( in );      memset (hdr, 0, sizeof *hdr);
612      hdr->size_of_dir = read_32( in );      hdr->magic = magic;
613      hdr->off_dir = read_32( in );      hdr->disc_nr = read_16( in );
614      hdr->comment_len = read_16( in );      hdr->disc_nr_cd = read_16( in );
615        hdr->total_dirs = read_16( in );
616      /*if( debug ) {      hdr->total_dirs_disc = read_16( in );
617          printf("=====BEGIN END HEADER=====\n");      hdr->size_of_dir = read_32( in );
618          printf( "magic=%08lX\n", hdr->magic );      hdr->off_dir = read_32( in );
619          printf( "disc number=%d in this directory=%d\n", hdr->disc_nr,      hdr->comment_len = read_16( in );
620                  hdr->disc_nr_cd );  
621          printf( "total number of disc=%d in this directory=%d\n",      /*if( debug ) {
622                  hdr->total_dirs, hdr->total_dirs_disc );          printf("=====BEGIN END HEADER=====\n");
623          printf( "offset of central directory=%lu\n", hdr->off_dir );          printf( "magic=%08lX\n", hdr->magic );
624          printf( "size of directory=%lu\n", hdr->size_of_dir );          printf( "disc number=%d in this directory=%d\n", hdr->disc_nr,
625      }*/                  hdr->disc_nr_cd );
626                printf( "total number of disc=%d in this directory=%d\n",
627      if (hdr->comment_len > 0) {                  hdr->total_dirs, hdr->total_dirs_disc );
628          hdr->comment = new char[hdr->comment_len+1];                printf( "offset of central directory=%lu\n", hdr->off_dir );
629          if( !hdr->comment )          printf( "size of directory=%lu\n", hdr->size_of_dir );
630              abort ();      }*/
631          memset (hdr->comment, 0, hdr->comment_len+1);      
632          fread( hdr->comment, 1, hdr->comment_len, in );      if (hdr->comment_len > 0) {
633          /*if( debug )          hdr->comment = new char[hdr->comment_len+1];      
634              printf( "comment(%d)=%s\n", hdr->comment_len, hdr->comment );*/          if( !hdr->comment )
635      }              abort ();
636      return hdr;          memset (hdr->comment, 0, hdr->comment_len+1);
637  }          fread( hdr->comment, 1, hdr->comment_len, in );
638            /*if( debug )
639                printf( "comment(%d)=%s\n", hdr->comment_len, hdr->comment );*/
640  static void      }
641  free_packet (PK_packet *pkt)      return hdr;
642  {  }
643      switch( pkt->pkttype ) {  
644      case PK_SIG_LOCAL:  
645          if (pkt->u.local->name)  static void
646              delete []pkt->u.local->name;  free_packet (PK_packet *pkt)
647          delete pkt->u.local;  {
648          break;      switch( pkt->pkttype ) {
649      case PK_SIG_FILE:      case PK_SIG_LOCAL:
650          if (pkt->u.file->name)          if (pkt->u.local->name)
651              delete[] pkt->u.file->name;              delete []pkt->u.local->name;
652          delete pkt->u.file;          delete pkt->u.local;
653          break;          break;
654      case PK_SIG_END:      case PK_SIG_FILE:
655          if (pkt->u.end->comment)          if (pkt->u.file->name)
656              delete [] pkt->u.end->comment;              delete[] pkt->u.file->name;
657          delete pkt->u.end;          delete pkt->u.file;
658          break;          break;
659      }      case PK_SIG_END:
660      pkt->pkttype = 0;          if (pkt->u.end->comment)
661  }              delete [] pkt->u.end->comment;
662            delete pkt->u.end;
663            break;
664  int      }
665  pk_archiv_parse (FILE *in)      pkt->pkttype = 0;
666  {  }
667      unsigned long magic;  
668      PK_packet pkt;  
669        int
670      while( !feof( in ) ) {  pk_archiv_parse (FILE *in)
671          magic = read_32( in );  {
672          if( feof( in ) )      unsigned long magic;
673              break;      PK_packet pkt;
674          /*printf("\n** read magic value %08lX\n\n", magic );*/      
675          switch( magic ) {      while( !feof( in ) ) {
676          case PK_SIG_LOCAL:          magic = read_32( in );
677              pkt.u.local = read_local_header( in, magic, 1 );          if( feof( in ) )
678              pkt.pkttype = PK_SIG_LOCAL;              break;
679              break;          /*printf("\n** read magic value %08lX\n\n", magic );*/
680                        switch( magic ) {
681          case PK_SIG_FILE:          case PK_SIG_LOCAL:
682              pkt.u.file = read_file_header( in, magic );              pkt.u.local = read_local_header( in, magic, 1 );
683              pkt.pkttype = PK_SIG_FILE;              pkt.pkttype = PK_SIG_LOCAL;
684              break;              break;
685                            
686          case PK_SIG_END:          case PK_SIG_FILE:
687              pkt.u.end = read_end_header( in, magic );              pkt.u.file = read_file_header( in, magic );
688              pkt.pkttype = PK_SIG_END;              pkt.pkttype = PK_SIG_FILE;
689              break;              break;
690                            
691          default:          case PK_SIG_END:
692              /*printf( "unknown magic value (%08lX).\n", magic );*/              pkt.u.end = read_end_header( in, magic );
693              if( ftell( in ) == 4 ) {              pkt.pkttype = PK_SIG_END;
694                  free_packet( &pkt );              break;
695                  return PKERR_INV_FILE;              
696              }          default:
697              break;              /*printf( "unknown magic value (%08lX).\n", magic );*/
698          }              if( ftell( in ) == 4 ) {
699          free_packet( &pkt );                  free_packet( &pkt );
700      }                  return PKERR_INV_FILE;
701      return 0;              }
702  }              break;
703            }
704            free_packet( &pkt );
705  static int      }
706  is_directory (const char * fname)      return 0;
707  {  }
708      struct stat statbuf;  
709      if (stat (fname, &statbuf))  
710          return 0;  static int
711      return statbuf.st_mode & S_IFDIR;  is_directory (const char * fname)
712  }  {
713        struct stat statbuf;
714        if (stat (fname, &statbuf))
715  int          return 0;
716  pk_archiv_create (struct PK_file_list *list, const char *output)      return statbuf.st_mode & S_IFDIR;
717  {  }
718      struct PK_file_list *r;  
719      PK_file_hdr *f;  
720      PK_end_hdr *e;  int
721      PK_packet pkt;  pk_archiv_create (struct PK_file_list *list, const char *output)
722      FILE *fp, *out;  {
723      long foff = 0, n = 0;      struct PK_file_list *r;
724      size_t size = 0;      PK_file_hdr *f;
725        PK_end_hdr *e;
726      out = fopen (output, "wb");      PK_packet pkt;
727      if (!out)      FILE *fp, *out;
728          return PKERR_FILE;      long foff = 0, n = 0;
729            size_t size = 0;
730      for (r = list; r; r = r->next) {  
731          fprintf (stderr, "process file `%s'\n", r->d);      out = fopen (output, "wb");
732          if (is_directory (r->d))      if (!out)
733              continue;          return PKERR_FILE;
734          fp = fopen (r->d, "rb");      
735          if (!fp) {      for (r = list; r; r = r->next) {
736              fclose (out);          fprintf (stderr, "process file `%s'\n", r->d);
737              return PKERR_FILE;          if (is_directory (r->d))
738          }              continue;
739          r->off = ftell (out);          fp = fopen (r->d, "rb");
740          r->hdr = create_local_header( r->d, fp );          if (!fp) {
741          if (!r->hdr) {              fclose (out);
742              fclose (fp);              return PKERR_FILE;
743              fclose (out);          }
744              return PKERR_GENERAL;          r->off = ftell (out);
745          }          r->hdr = create_local_header( r->d, fp );
746          if (r->off)          if (!r->hdr) {
747              r->off += r->hdr->c_size;              fclose (fp);
748          write_local_header (out, r->hdr);              fclose (out);
749          n++;              return PKERR_GENERAL;
750          fclose (fp);          }
751      }          if (r->off)
752      foff = ftell( out );              r->off += r->hdr->c_size;
753      for (r = list; r; r = r->next) {          write_local_header (out, r->hdr);
754          if (is_directory (r->d))          n++;
755              continue;          fclose (fp);
756          fp = fopen (r->d, "rb");      }
757          if (!fp) {      foff = ftell( out );
758              fclose (out);      for (r = list; r; r = r->next) {
759              return PKERR_FILE;          if (is_directory (r->d))
760          }              continue;
761          f = create_file_header (r->hdr, r->off);          fp = fopen (r->d, "rb");
762          size += f->size;          if (!fp) {
763          write_file_header (out, f);              fclose (out);
764          fclose (fp);              return PKERR_FILE;
765          pkt.u.file = f;          }
766          free_packet (&pkt);          f = create_file_header (r->hdr, r->off);
767      }          size += f->size;
768                write_file_header (out, f);
769      e = create_end_header (n, size, foff);          fclose (fp);
770      write_end_header (out, e);          pkt.u.file = f;
771      fclose (out);          free_packet (&pkt);
772      return 0;      }
773  }      
774        e = create_end_header (n, size, foff);
775        write_end_header (out, e);
776  void      fclose (out);
777  pk_list_add (struct PK_file_list **list, const char *name)      return 0;
778  {  }
779      struct PK_file_list * l;  
780    
781      l = new PK_file_list;  void
782      if (!l)  pk_list_add (struct PK_file_list **list, const char *name)
783          abort ();  {
784      memset (l, 0, sizeof *l);        struct PK_file_list * l;
785      l->next = *list;  
786      l->d = new char[strlen (name)+2];        l = new PK_file_list;
787      if (!l->d)          if (!l)
788          abort ();                abort ();
789      strcpy (l->d, name);              memset (l, 0, sizeof *l);  
790      *list = l;      l->next = *list;
791  }      l->d = new char[strlen (name)+2];  
792        if (!l->d)    
793            abort ();      
794  void      strcpy (l->d, name);        
795  pk_list_free (struct PK_file_list *list)      *list = l;
796  {  }
797      struct PK_file_list * l;  
798      PK_packet pkt;  
799    void
800      while (list) {  pk_list_free (struct PK_file_list *list)
801          l = list->next;  {
802          if (list->hdr) {      struct PK_file_list * l;
803              pkt.pkttype = PK_SIG_LOCAL;      PK_packet pkt;
804              pkt.u.local = list->hdr;  
805              free_packet (&pkt);      while (list) {
806          }          l = list->next;
807          if (list->d)          if (list->hdr) {
808              delete []list->d;              pkt.pkttype = PK_SIG_LOCAL;
809          delete list;              pkt.u.local = list->hdr;
810          list = l;              free_packet (&pkt);
811      }          }
812  }          if (list->d)
813                delete []list->d;
814            delete list;
815  #ifdef TEST          list = l;
816        }
817  static void  }
818  test (const char *patt, const char *path, const char *out)  
819  {  
820      PK_FILE_LIST list = NULL;  #ifdef TEST
821      WIN32_FIND_DATA findbuf;  
822      HANDLE hd;      static void
823      int rc = 0;  test (const char *patt, const char *path, const char *out)
824        {
825      hd = FindFirstFile (patt, &findbuf );          PK_FILE_LIST list = NULL;
826      if( !hd )      WIN32_FIND_DATA findbuf;
827          return;      HANDLE hd;    
828        int rc = 0;
829      if( strcmp( findbuf.cFileName, "." ) && strcmp( findbuf.cFileName, ".." ) ) {      
830          char p[256];      hd = FindFirstFile (patt, &findbuf );    
831          _snprintf (p, sizeof (p)-1, "%s\\%s", path, findbuf.cFileName);      if( !hd )
832          pk_list_add (&list, p);          return;
833      }  
834      while( FindNextFile( hd, &findbuf ) ) {      if( strcmp( findbuf.cFileName, "." ) && strcmp( findbuf.cFileName, ".." ) ) {
835          if( strcmp( findbuf.cFileName, "." ) && strcmp( findbuf.cFileName, ".." ) ) {          char p[256];
836              char p[256];          _snprintf (p, sizeof (p)-1, "%s\\%s", path, findbuf.cFileName);
837              _snprintf (p, sizeof (p)-1, "%s\\%s", path, findbuf.cFileName);          pk_list_add (&list, p);
838              pk_list_add (&list, p);      }
839          }      while( FindNextFile( hd, &findbuf ) ) {
840      }          if( strcmp( findbuf.cFileName, "." ) && strcmp( findbuf.cFileName, ".." ) ) {
841                char p[256];
842      rc = pk_archiv_create (list, out);              _snprintf (p, sizeof (p)-1, "%s\\%s", path, findbuf.cFileName);
843                pk_list_add (&list, p);
844      pk_list_free (list);          }
845      FindClose (hd);      }
846  }  
847        rc = pk_archiv_create (list, out);
848  int  
849  main (int argc, char **argv)      pk_list_free (list);
850  {      FindClose (hd);
851      test ("c:\\gnupg\\*", "c:\\gnupg", "c:\\gnupg\\\\test\\sample.zip");  }
852      return 0;  
853  }  int
854  #endif  main (int argc, char **argv)
855    {
856        test ("c:\\gnupg\\*", "c:\\gnupg", "c:\\gnupg\\\\test\\sample.zip");
857        return 0;
858    }
859    #endif

Legend:
Removed from v.45  
changed lines
  Added in v.46

[email protected]
ViewVC Help
Powered by ViewVC 1.1.26