zip30/0040755000076400000060000000000011033727770007773 5ustar ediskzip30/acorn/0040755000076400000060000000000011033727770011075 5ustar ediskzip30/acorn/acornzip.c0100644000076400000060000004013510154331616013057 0ustar edisk/* Copyright (c) 1990-2002 Info-ZIP. All rights reserved. See the accompanying file LICENSE, version 2000-Apr-09 or later (the contents of which are also included in zip.h) for terms of use. If, for some reason, all these files are missing, the Info-ZIP license also may be found at: ftp://ftp.info-zip.org/pub/infozip/license.html */ #include #include #include "zip.h" #ifndef UTIL #define PAD 0 #define PATH_END '/' local int wild_recurse(char *whole, char *wildtail); local int uxtime2acornftime(unsigned *pexadr, unsigned *pldadr, time_t ut); extern char *label; local ulg label_time = 0; local ulg label_mode = 0; local time_t label_utim = 0; char *readd(DIR *d) /* Return a pointer to the next name in the directory stream d, or NULL if no more entries or an error occurs. */ { struct dirent *e; e = readdir(d); return (e == NULL ? (char *) NULL : e->d_name); } /* What we have here is a mostly-generic routine using opend()/readd() and */ /* isshexp()/MATCH() to find all the files matching a multi-part filespec */ /* using the portable pattern syntax. It shouldn't take too much fiddling */ /* to make it usable for any other platform that has directory hierarchies */ /* but no shell-level pattern matching. It works for patterns throughout */ /* the pathname, such as "foo:*.?/source/x*.[ch]". */ /* whole is a pathname with wildcards, wildtail points somewhere in the */ /* middle of it. All wildcards to be expanded must come AFTER wildtail. */ local int wild_recurse(whole, wildtail) char *whole; char *wildtail; { DIR *dir; char *subwild, *name, *newwhole = NULL, *glue = NULL, plug = 0, plug2; ush newlen, amatch = 0; struct stat statb; int disk_not_mounted=0; int e = ZE_MISS; if (!isshexp(wildtail)) { if (stat(whole,&statb)==0 && (statb.st_mode & S_IREAD)!=0) { return procname(whole, 0); } else return ZE_MISS; /* woops, no wildcards! */ } /* back up thru path components till existing dir found */ do { name = wildtail + strlen(wildtail) - 1; for (;;) if (name-- <= wildtail || *name == '.') { subwild = name + 1; plug2 = *subwild; *subwild = 0; break; } if (glue) *glue = plug; glue = subwild; plug = plug2; dir = opendir(whole); } while (!dir && !disk_not_mounted && subwild > wildtail); wildtail = subwild; /* skip past non-wild components */ if ((subwild = strchr(wildtail + 1, '.')) != NULL) { /* this "+ 1" dodges the ^^^ hole left by *glue == 0 */ *(subwild++) = 0; /* wildtail = one component pattern */ newlen = strlen(whole) + strlen(subwild) + 32; } else newlen = strlen(whole) + 31; if (!dir || !(newwhole = malloc(newlen))) { if (glue) *glue = plug; e = dir ? ZE_MEM : ZE_MISS; goto ohforgetit; } strcpy(newwhole, whole); newlen = strlen(newwhole); if (glue) *glue = plug; /* repair damage to whole */ if (!isshexp(wildtail)) { e = ZE_MISS; /* non-wild name not found */ goto ohforgetit; } while (name = readd(dir)) { if (MATCH(wildtail, name, 0)) { strcpy(newwhole + newlen, name); if (subwild) { name = newwhole + strlen(newwhole); *(name++) = '.'; strcpy(name, subwild); e = wild_recurse(newwhole, name); } else e = procname(newwhole, 0); newwhole[newlen] = 0; if (e == ZE_OK) amatch = 1; else if (e != ZE_MISS) break; } } ohforgetit: if (dir) closedir(dir); if (subwild) *--subwild = '.'; if (newwhole) free(newwhole); if (e == ZE_MISS && amatch) e = ZE_OK; return e; } int wild(p) char *p; { char *path; int toret; /* special handling of stdin request */ if (strcmp(p, "-") == 0) /* if compressing stdin */ return newname(p, 0, 0); path=p; if (strchr(p, ':')==NULL && *p!='@') { if (!(path=malloc(strlen(p)+3))) { return ZE_MEM; } strcpy(path,"@."); strcat(path,p); } toret=wild_recurse(path, path); if (path!=p) { free(path); } return toret; } int procname(n, caseflag) char *n; /* name to process */ int caseflag; /* true to force case-sensitive match */ /* Process a name or sh expression to operate on (or exclude). Return an error code in the ZE_ class. */ { char *a; /* path and name for recursion */ DIR *d; /* directory stream from opendir() */ char *e; /* pointer to name from readd() */ int m; /* matched flag */ char *p; /* path for recursion */ struct stat s; /* result of stat() */ struct zlist far *z; /* steps through zfiles list */ if (strcmp(n, "-") == 0) /* if compressing stdin */ return newname(n, 0, caseflag); else if (LSSTAT(n, &s)) { /* Not a file or directory--search for shell expression in zip file */ p = ex2in(n, 0, (int *)NULL); /* shouldn't affect matching chars */ m = 1; for (z = zfiles; z != NULL; z = z->nxt) { if (MATCH(p, z->iname, caseflag)) { z->mark = pcount ? filter(z->zname, caseflag) : 1; if (verbose) fprintf(mesg, "zip diagnostic: %scluding %s\n", z->mark ? "in" : "ex", z->name); m = 0; } } free((zvoid *)p); return m ? ZE_MISS : ZE_OK; } /* Live name--use if file, recurse if directory */ if ((s.st_mode & S_IFDIR) == 0) { /* add or remove name of file */ if ((m = newname(n, 0, caseflag)) != ZE_OK) return m; } else { /* Add trailing / to the directory name */ if ((p = malloc(strlen(n)+2)) == NULL) return ZE_MEM; if (strcmp(n, ".") == 0) { *p = '\0'; /* avoid "./" prefix and do not create zip entry */ } else { strcpy(p, n); a = p + strlen(p); if (a[-1] != '.') strcpy(a, "."); if (dirnames && (m = newname(p, 1, caseflag)) != ZE_OK) { free((zvoid *)p); return m; } } /* recurse into directory */ if (recurse && (d = opendir(n)) != NULL) { while ((e = readd(d)) != NULL) { if (strcmp(e, ".") && strcmp(e, "..")) { if ((a = malloc(strlen(p) + strlen(e) + 1)) == NULL) { closedir(d); free((zvoid *)p); return ZE_MEM; } strcat(strcpy(a, p), e); if ((m = procname(a, caseflag)) != ZE_OK) /* recurse on name */ { if (m == ZE_MISS) zipwarn("name not matched: ", a); else ziperr(m, a); } free((zvoid *)a); } } closedir(d); } free((zvoid *)p); } /* (s.st_mode & S_IFDIR) == 0) */ return ZE_OK; } char *ex2in(x, isdir, pdosflag) char *x; /* external file name */ int isdir; /* input: x is a directory */ int *pdosflag; /* output: force MSDOS file attributes? */ /* Convert the external file name to a zip file name, returning the malloc'ed string or NULL if not enough memory. */ { char *n; /* internal file name (malloc'ed) */ char *t; /* shortened name */ char *tmp; int dosflag; char *lastlastdir=NULL; /* pointer to 2 dirs before... */ char *lastdir=NULL; /* pointer to last dir... */ /* Malloc space for internal name and copy it */ if ((tmp = malloc(strlen(x) + 1)) == NULL) return NULL; strcpy(tmp, x); dosflag = dosify; /* default for non-DOS and non-OS/2 */ /* Find starting point in name before doing malloc */ for(t=tmp;*t;t++) { if (*t=='/') { *t='.'; } else if (*t=='.') { *t='/'; lastlastdir=lastdir; lastdir=t+1; } } t=strchr(tmp,'$'); /* skip FS name */ if (t!=NULL) t+=2; /* skip '.' after '$' */ else t=tmp; if (*t=='@') /* skip @. at the beginning of filenames */ t+=2; /* Make changes, if any, to the copied name (leave original intact) */ /* return a pointer to '\0' if the file is a directory with the same same name as an extension to swap (eg. 'c', 'h', etc.) */ if (isdir && exts2swap!=NULL) { if (lastlastdir==NULL) lastlastdir=t; if (checkext(lastlastdir)) { free((void *)tmp); n=malloc(1); if (n!=NULL) *n='\0'; return n; } } if (exts2swap!=NULL && lastdir!=NULL) { if (lastlastdir==NULL) lastlastdir=t; if (checkext(lastlastdir)) { if (swapext(lastlastdir,lastdir-1)) { free((void *)tmp); return NULL; } } } if (!pathput) t = last(t, PATH_END); /* Malloc space for internal name and copy it */ if ((n = malloc(strlen(t) + 1)) == NULL) { free((void *)tmp); return NULL; } strcpy(n, t); free((void *)tmp); if (dosify) msname(n); /* Returned malloc'ed name */ if (pdosflag) *pdosflag = dosflag; return n; } char *in2ex(n) char *n; /* internal file name */ /* Convert the zip file name to an external file name, returning the malloc'ed string or NULL if not enough memory. */ { char *x; /* external file name */ char *t; /* scans name */ char *lastext=NULL; /* pointer to last extension */ char *lastdir=NULL; /* pointer to last dir */ if ((x = malloc(strlen(n) + 1 + PAD)) == NULL) return NULL; strcpy(x, n); for(t=x;*t;t++) { if (*t=='.') { *t='/'; lastext=t+1; } else if (*t=='/') { *t='.'; lastdir=t+1; } } if (exts2swap!=NULL && (int)lastext>(int)lastdir) { if (lastdir==NULL) lastdir=x; if (checkext(lastext)) { if (swapext(lastdir,lastext-1)) { free((void *)x); return NULL; } } } return x; } local int uxtime2acornftime(unsigned *pexadr, unsigned *pldadr, time_t ut) { unsigned timlo; /* 3 lower bytes of acorn file-time plus carry byte */ unsigned timhi; /* 2 high bytes of acorn file-time */ timlo = ((unsigned)ut & 0x00ffffffU) * 100 + 0x00996a00U; timhi = ((unsigned)ut >> 24); timhi = timhi * 100 + 0x0000336eU + (timlo >> 24); if (timhi & 0xffff0000U) return 1; /* calculation overflow, do not change time */ /* insert the five time bytes into loadaddr and execaddr variables */ *pexadr = (timlo & 0x00ffffffU) | ((timhi & 0x000000ffU) << 24); *pldadr = (*pldadr & 0xffffff00U) | ((timhi >> 8) & 0x000000ffU); return 0; /* subject to future extension to signal overflow */ } void stamp(f, d) char *f; /* name of file to change */ ulg d; /* dos-style time to change it to */ /* Set last updated and accessed time of file f to the DOS time d. */ { time_t m_time; unsigned int loadaddr, execaddr; int attr; /* Convert DOS time to time_t format in m_time */ m_time = dos2unixtime(d); /* set the file's modification time */ SWI_OS_File_5(f,NULL,&loadaddr,NULL,NULL,&attr); if (uxtime2acornftime(&execaddr, &loadaddr, m_time) != 0) return; SWI_OS_File_1(f,loadaddr,execaddr,attr); } ulg filetime(f, a, n, t) char *f; /* name of file to get info on */ ulg *a; /* return value: file attributes */ long *n; /* return value: file size */ iztimes *t; /* return value: access, modific. and creation times */ /* If file *f does not exist, return 0. Else, return the file's last modified date and time as an MSDOS date and time. The date and time is returned in a long with the date most significant to allow unsigned integer comparison of absolute times. Also, if a is not a NULL pointer, store the file attributes there, with the high two bytes being the Unix attributes, and the low byte being a mapping of that to DOS attributes. If n is not NULL, store the file size there. If t is not NULL, the file's access, modification and creation times are stored there as UNIX time_t values. If f is "-", use standard input as the file. If f is a device, return a file size of -1 */ { struct stat s; /* results of stat() */ /* convert FNMAX to malloc - 11/8/04 EG */ char *name; unsigned int len = strlen(f); if (f == label) { if (a != NULL) *a = label_mode; if (n != NULL) *n = -2L; /* convention for a label name */ if (t != NULL) t->atime = t->mtime = t->ctime = label_utim; return label_time; } if ((name = malloc(len + 1)) == NULL) { ZIPERR(ZE_MEM, "filetime"); } strcpy(name, f); if (name[len - 1] == '.') name[len - 1] = '\0'; /* not all systems allow stat'ing a file with / appended */ if (strcmp(f, "-") == 0) { /* forge stat values for stdin since Amiga and RISCOS have no fstat() */ s.st_mode = (S_IREAD|S_IWRITE|S_IFREG); s.st_size = -1; s.st_mtime = time(&s.st_mtime); } else if (LSSTAT(name, &s) != 0) { /* Accept about any file kind including directories * (stored with trailing / with -r option) */ free(name); return 0; } free(name); if (a != NULL) { *a = ((ulg)s.st_mode << 16) | !(s.st_mode & S_IWRITE); if ((s.st_mode & S_IFDIR) != 0) { *a |= MSDOS_DIR_ATTR; } } if (n != NULL) *n = (s.st_mode & S_IFMT) == S_IFREG ? s.st_size : -1L; if (t != NULL) { t->atime = s.st_atime; t->mtime = s.st_mtime; t->ctime = s.st_ctime; } return unix2dostime((time_t *) &s.st_mtime); } int set_extra_field(z, z_utim) struct zlist far *z; iztimes *z_utim; { #ifdef USE_EF_UT_TIME char *eb_ptr; #endif /* USE_EF_UT_TIME */ char *name; extra_block *block; #define EB_SPARK_LEN 20 #define EB_SPARK_SIZE (EB_HEADSIZE+EB_SPARK_LEN) #ifdef USE_EF_UT_TIME # ifdef IZ_CHECK_TZ # define EB_UTTIME_SIZE (zp_tz_is_valid ? EB_HEADSIZE+EB_UT_LEN(1) : 0) # else # define EB_UTTIME_SIZE (EB_HEADSIZE+EB_UT_LEN(1)) # endif #else # define EB_UTTIME_SIZE 0 #endif #define EF_SPARK_TOTALSIZE (EB_SPARK_SIZE + EB_UTTIME_SIZE) if ((name=(char *)malloc(strlen(z->name)+1))==NULL) { fprintf(stderr," set_extra_field: not enough memory for directory name\n"); return ZE_MEM; } strcpy(name,z->name); if (name[strlen(name)-1]=='.') { /* remove the last '.' in directory names */ name[strlen(name)-1]=0; } z->extra=(char *)malloc(EF_SPARK_TOTALSIZE); if (z->extra==NULL) { fprintf(stderr," set_extra_field: not enough memory\n"); free(name); return ZE_MEM; } z->cextra = z->extra; z->cext = z->ext = EF_SPARK_TOTALSIZE; block=(extra_block *)z->extra; block->ID=SPARKID; block->size=EB_SPARK_LEN; block->ID_2=SPARKID_2; block->zero=0; if (SWI_OS_File_5(name,NULL,&block->loadaddr,&block->execaddr, NULL,&block->attr) != NULL) { fprintf(stderr," OS error while set_extra_field of %s\n",name); } free(name); #ifdef USE_EF_UT_TIME # ifdef IZ_CHECK_TZ if (zp_tz_is_valid) { # endif eb_ptr = z->extra + EB_SPARK_SIZE; eb_ptr[0] = 'U'; eb_ptr[1] = 'T'; eb_ptr[2] = EB_UT_LEN(1); /* length of data part of e.f. */ eb_ptr[3] = 0; eb_ptr[4] = EB_UT_FL_MTIME; eb_ptr[5] = (char)(z_utim->mtime); eb_ptr[6] = (char)(z_utim->mtime >> 8); eb_ptr[7] = (char)(z_utim->mtime >> 16); eb_ptr[8] = (char)(z_utim->mtime >> 24); # ifdef IZ_CHECK_TZ } # endif #endif /* USE_EF_UT_TIME */ return ZE_OK; } #endif /* !UTIL */ /******************************/ /* Function version_local() */ /******************************/ void version_local() { static ZCONST char CompiledWith[] = "Compiled with %s%s for %s%s%s%s.\n\n"; printf(CompiledWith, #ifdef __GNUC__ "gcc ", __VERSION__, #else # ifdef __CC_NORCROFT "Norcroft ", "cc", # else "cc", "", # endif #endif "RISC OS", " (Acorn Computers Ltd)", #ifdef __DATE__ " on ", __DATE__ #else "", "" #endif ); } /* end function version_local() */ zip30/acorn/GMakefile0100644000076400000060000000770710550050042012634 0ustar edisk# Makefile for Zip, ZipNote, ZipCloak and ZipSplit # add -g to CC to debug # add -d to BIND to debug CC = gcc -mlibscl BIND = $(CC) AS = $(CC) -c ASM = AS SQUEEZE = squeeze -v E = # flags # CFLAGS flags for C compile # LFLAGS1 flags after output file spec, before obj file list # LFLAGS2 flags after obj file list (libraries, etc) # LIB = CFLAGS = -O2 -mthrowback -DASMV ASMFLAGS = -throwback -objasm -upper LFLAGS1 = LFLAGS2 = $(LIB) # Uncomment the following line to enable support for Unix # Extra Field (Timezone) #CFLAGS = $(CFLAGS) -DUSE_EF_UT_TIME # object file lists OBJZ = o.zip o.zipfile o.zipup o.fileio o.util o.globals o.crc32 \ o.crypt o.ttyio o.riscos o.acornzip o.swiven OBJI = o.deflate o.trees OBJA = o.match o.sendbits OBJU = o.zipfile_ o.fileio_ o.util_ o.globals o.riscos o.acornzip_ o.swiven OBJN = o.zipnote $(OBJU) OBJC = o.zipcloak $(OBJU) o.crc32_ o.crypt_ o.ttyio OBJS = o.zipsplit $(OBJU) ZIP_H = h.zip h.ziperr h.tailor acorn.h.osdep acorn.h.riscos acorn.h.swiven all: zip zipnote zipsplit zipcloak install: %.zip %.zipnote %.zipsplit %.zipcloak %.acorn.zipsfx \ zip zipnote zipsplit zipcloak acorn.zipsfx $(SQUEEZE) zip %.zip $(SQUEEZE) zipnote %.zipnote $(SQUEEZE) zipsplit %.zipsplit $(SQUEEZE) zipcloak %.zipcloak copy acorn.zipsfx %.zipsfx ~CVF # rules for zip, zipnote, zipcloak and zipsplit o.api: c.api $(CC) $(CFLAGS) -c c.api -o o.api o.crc32: c.crc32 $(ZIP_H) h.crc32 $(CC) $(CFLAGS) -c c.crc32 -o o.crc32 o.crypt: c.crypt $(ZIP_H) h.crypt h.crc32 h.ttyio $(CC) $(CFLAGS) -c c.crypt -o o.crypt o.deflate: c.deflate $(ZIP_H) $(CC) $(CFLAGS) -c c.deflate -o o.deflate o.fileio: c.fileio $(ZIP_H) h.crc32 $(CC) $(CFLAGS) -c c.fileio -o o.fileio o.globals: c.globals $(ZIP_H) $(CC) $(CFLAGS) -c c.globals -o o.globals o.mktime: c.mktime $(CC) $(CFLAGS) -c c.mktime -o o.mktime o.trees: c.trees $(ZIP_H) $(CC) $(CFLAGS) -c c.trees -o o.trees o.ttyio: c.ttyio $(ZIP_H) h.crypt $(CC) $(CFLAGS) -c c.ttyio -o o.ttyio o.util: c.util $(ZIP_H) $(CC) $(CFLAGS) -c c.util -o o.util o.zip: c.zip $(ZIP_H) h.crc32 h.crypt h.revision h.ttyio $(CC) $(CFLAGS) -c c.zip -o o.zip o.zipcloak: c.zipcloak $(ZIP_H) h.crc32 h.crypt h.revision h.ttyio $(CC) $(CFLAGS) -c c.zipcloak -o o.zipcloak o.zipfile: c.zipfile $(ZIP_H) h.crc32 $(CC) $(CFLAGS) -c c.zipfile -o o.zipfile o.zipnote: c.zipnote $(ZIP_H) h.revision $(CC) $(CFLAGS) -c c.zipnote -o o.zipnote o.zipsplit: c.zipsplit $(ZIP_H) h.revision $(CC) $(CFLAGS) -c c.zipsplit -o o.zipsplit o.zipup: c.zipup $(ZIP_H) h.crc32 h.crypt h.revision $(CC) $(CFLAGS) -c c.zipup -o o.zipup o.crc32_: c.crc32 $(ZIP_H) h.crc32 $(CC) $(CFLAGS) -DUTIL -c c.crc32 -o o.crc32_ o.crypt_: c.crypt $(ZIP_H) h.crypt h.crc32 h.ttyio $(CC) $(CFLAGS) -DUTIL -c c.crypt -o o.crypt_ o.util_: c.util $(ZIP_H) $(CC) $(CFLAGS) -DUTIL -c c.util -o o.util_ o.fileio_: c.fileio $(ZIP_H) h.crc32 $(CC) $(CFLAGS) -DUTIL -c c.fileio -o o.fileio_ o.zipfile_: c.zipfile $(ZIP_H) h.crc32 $(CC) $(CFLAGS) -DUTIL -c c.zipfile -o o.zipfile_ o.acornzip_: acorn.c.acornzip $(ZIP_H) $(CC) $(CFLAGS) -I@ -DUTIL -c acorn.c.acornzip -o o.acornzip_ o.riscos: acorn.c.riscos acorn.h.riscos $(ZIP_H) $(CC) $(CFLAGS) -I@ -c acorn.c.riscos -o o.riscos o.acornzip: acorn.c.acornzip $(ZIP_H) $(CC) $(CFLAGS) -I@ -c acorn.c.acornzip -o o.acornzip o.match: acorn.s.match $(ASM) $(ASMFLAGS) -I@ acorn.s.match -o o.match o.sendbits: acorn.s.sendbits $(ASM) $(ASMFLAGS) -I@ acorn.s.sendbits -o o.sendbits o.swiven: acorn.s.swiven $(ASM) $(ASMFLAGS) -I@ acorn.s.swiven -o o.swiven zip: $(OBJZ) $(OBJI) $(OBJA) $(BIND) -o zip$(E) $(LFLAGS1) $(OBJZ) $(OBJI) $(OBJA) $(LFLAGS2) zipnote: $(OBJN) $(BIND) -o zipnote$(E) $(LFLAGS1) $(OBJN) $(LFLAGS2) zipcloak: $(OBJC) $(BIND) -o zipcloak$(E) $(LFLAGS1) $(OBJC) $(LFLAGS2) zipsplit: $(OBJS) $(BIND) -o zipsplit$(E) $(LFLAGS1) $(OBJS) $(LFLAGS2) clean: remove zip remove zipcloak remove zipsplit remove zipnote create o.!fake! 0 wipe o.* ~cf # end of Makefile zip30/acorn/makefile0100644000076400000060000000660110550047772012575 0ustar edisk# Makefile for Zip, ZipNote, ZipCloak and ZipSplit # add -g to CC to debug # add -d to BIND to debug CC = cc BIND = link AS = $(CC) -c ASM = objasm SQUEEZE = squeeze -v E = # flags # CFLAGS flags for C compile # LFLAGS1 flags after output file spec, before obj file list # LFLAGS2 flags after obj file list (libraries, etc) # LIB = CBASE = -throwback -wn -DASMV -apcs 3/26 CFLAGS = $(CBASE) -IC:,@. ASMFLAGS = -Throwback -Stamp -NoCache -CloseExec -quit -apcs 3/26 LFLAGS1 = LFLAGS2 = $(LIB) C:o.Stubs # Uncomment the following line to enable support for Unix # Extra Field (Timezone) #CFLAGS = $(CFLAGS) -DUSE_EF_UT_TIME # object file lists OBJZ = zip.o zipfile.o zipup.o fileio.o util.o globals.o crc32.o \ crypt.o ttyio.o riscos.o acornzip.o swiven.o OBJI = deflate.o trees.o OBJA = match.o sendbits.o OBJU = zipfile_.o fileio_.o util_.o globals.o riscos.o acornzip_.o swiven.o OBJN = zipnote.o $(OBJU) OBJC = zipcloak.o $(OBJU) crc32_.o crypt_.o ttyio.o OBJS = zipsplit.o $(OBJU) ZIP_H = zip.h ziperr.h tailor.h acorn/osdep.h acorn/riscos.h acorn/swiven.h all: zip zipnote zipsplit zipcloak install: %.zip %.zipnote %.zipsplit %.zipcloak %.zipsfx \ zip zipnote zipsplit zipcloak zipsfx $(SQUEEZE) zip %.zip $(SQUEEZE) zipnote %.zipnote $(SQUEEZE) zipsplit %.zipsplit $(SQUEEZE) zipcloak %.zipcloak copy acorn.zipsfx %.zipsfx ~CVF # suffix rules .SUFFIXES: _.o .o .c .c_.o: $(CC) $(CFLAGS) -DUTIL -c $*.c -o $*_.o .c.o: $(CC) $(CFLAGS) -c $< .s.o: $(ASM) $(ASMFLAGS) -from @*.s -to @*.o # rules for zip, zipnote, zipcloak and zipsplit $(OBJZ): $(ZIP_H) $(OBJI): $(ZIP_H) $(OBJN): $(ZIP_H) $(OBJS): $(ZIP_H) $(OBJC): $(ZIP_H) zip.o crc32.o crypt.o fileio.o zipfile.o zipup.o: crc32.h zipcloak.o crc32_.o crypt_.o fileio_.o zipfile_.o: crc32.h zip.o zipup.o crypt.o ttyio.o zipcloak.o crypt_.o: crypt.h zip.o zipup.o zipnote.o zipcloak.o zipsplit.o: revision.h zip.o crypt.o ttyio.o zipcloak.o crypt_.o: ttyio.h crc32_.o: crc32.c $(CC) $(CFLAGS) -DUTIL -c c.crc32 -o o.crc32_ crypt_.o: crypt.c $(CC) $(CFLAGS) -DUTIL -c c.crypt -o o.crypt_ util_.o: util.c $(CC) $(CFLAGS) -DUTIL -c c.util -o o.util_ fileio_.o: fileio.c $(CC) $(CFLAGS) -DUTIL -c c.fileio -o o.fileio_ zipfile_.o: zipfile.c $(CC) $(CFLAGS) -DUTIL -c c.zipfile -o o.zipfile_ acornzip_.o: acorn/acornzip.c $(ZIP_H) $(CC) $(CFLAGS) -DUTIL -c acorn/acornzip.c -o o.acornzip_ riscos.o: acorn/riscos.c acorn/riscos.h $(CC) $(CFLAGS) -c acorn/riscos.c acornzip.o: acorn/acornzip.c $(ZIP_H) $(CC) $(CFLAGS) -c acorn/acornzip.c match.o: acorn/match.s $(ASM) $(ASMFLAGS) -from acorn.s.match -to o.match sendbits.o: acorn/sendbits.s $(ASM) $(ASMFLAGS) -from acorn.s.sendbits -to o.sendbits swiven.o: acorn/swiven.s $(ASM) $(ASMFLAGS) -from acorn.s.swiven -to o.swiven zip: $(OBJZ) $(OBJI) $(OBJA) $(BIND) -o zip$(E) $(LFLAGS1) $(OBJZ) $(OBJI) $(OBJA) $(LFLAGS2) zipnote: $(OBJN) $(BIND) -o zipnote$(E) $(LFLAGS1) $(OBJN) $(LFLAGS2) zipcloak: $(OBJC) $(BIND) -o zipcloak$(E) $(LFLAGS1) $(OBJC) $(LFLAGS2) zipsplit: $(OBJS) $(BIND) -o zipsplit$(E) $(LFLAGS1) $(OBJS) $(LFLAGS2) clean: ;remove zip; remove zipcloak; remove zipsplit; remove zipnote; create o.!fake! 0 wipe o.* ~cf # end of Makefile zip30/acorn/match.s0100644000076400000060000001236707011110164012343 0ustar edisk;=========================================================================== ; Copyright (c) 1990-1999 Info-ZIP. All rights reserved. ; ; See the accompanying file LICENSE, version 1999-Oct-05 or later ; (the contents of which are also included in zip.h) for terms of use. ; If, for some reason, both of these files are missing, the Info-ZIP license ; also may be found at: ftp://ftp.cdrom.com/pub/infozip/license.html ;=========================================================================== ; match.s for ARM by Sergio Monesi. r0 RN 0 r1 RN 1 r2 RN 2 r3 RN 3 r4 RN 4 r5 RN 5 r6 RN 6 r7 RN 7 r8 RN 8 r9 RN 9 sl RN 10 fp RN 11 ip RN 12 sp RN 13 lr RN 14 pc RN 15 MAX_DIST EQU 32506 WMASK EQU 32767 MAX_MATCH EQU 258 AREA |C$$code|, CODE, READONLY ; r1 = chain_lenght ; r2 = scan ; r3 = match ; r4 = len (tmp) ; r5 = best_len ; r6 = limit ; r7 = strend ; r8 = scan_end1 ; r9 = scan_end ; lr = window ; fp = prev |__max_chain_length| IMPORT max_chain_length DCD max_chain_length |__window| IMPORT window DCD window |__prev| IMPORT prev DCD prev |__prev_length| IMPORT prev_length DCD prev_length |__strstart| IMPORT strstart DCD strstart |__good_match| IMPORT good_match DCD good_match |__nice_match| IMPORT nice_match DCD nice_match |__match_start| IMPORT match_start DCD match_start DCB "longest_match" DCB &00,&00,&00 DCD &ff000010 EXPORT longest_match longest_match STMFD sp!, {r4-r9,fp,lr} LDR fp, [pc, #|__prev|-.-8] LDR r1, [pc, #|__max_chain_length|-.-8] LDR r1, [r1] LDR lr, [pc, #|__window|-.-8] LDR ip, [pc, #|__strstart|-.-8] LDR ip, [ip] ADD r2, lr, ip LDR r5, [pc, #|__prev_length|-.-8] LDR r5, [r5] SUBS ip, ip, #MAX_DIST-250 ; if r6 > MAX_DIST SUBCSS r6, ip, #250 ; r6 = r6 - MAXDIST MOVLS r6, #0 ; else r6 = 0 ADD r7, r2, #MAX_MATCH-256 ADD r7, r7, #256 ; r7 = r2 + MAX_MATCH (=258); SUB ip, r5, #1 LDRB r8, [r2, ip] LDRB r9, [r2, r5] LDR ip, [pc, #|__good_match|-.-8] LDR ip, [ip] CMP r5, ip MOVCS r1, r1, LSR #2 cycle ADD r3, lr, r0 LDRB ip, [r3, r5] CMP ip, r9 BNE cycle_end SUB ip, r5, #1 LDRB ip, [r3, ip] CMP ip, r8 BNE cycle_end LDRB ip, [r2] LDRB r4, [r3] CMP ip, r4 BNE cycle_end LDRB ip, [r3, #1] LDRB r4, [r2, #1] CMP ip, r4 BNE cycle_end ADD r2, r2, #2 ADD r3, r3, #2 inn_cycle LDRB ip, [r2, #1]! LDRB r4, [r3, #1]! CMP ip, r4 BNE exit_inn_cycle LDRB ip, [r2, #1]! LDRB r4, [r3, #1]! CMP ip, r4 BNE exit_inn_cycle LDRB ip, [r2, #1]! LDRB r4, [r3, #1]! CMP ip, r4 BNE exit_inn_cycle LDRB ip, [r2, #1]! LDRB r4, [r3, #1]! CMP ip, r4 BNE exit_inn_cycle LDRB ip, [r2, #1]! LDRB r4, [r3, #1]! CMP ip, r4 BNE exit_inn_cycle LDRB ip, [r2, #1]! LDRB r4, [r3, #1]! CMP ip, r4 BNE exit_inn_cycle LDRB ip, [r2, #1]! LDRB r4, [r3, #1]! CMP ip, r4 BNE exit_inn_cycle LDRB ip, [r2, #1]! LDRB r4, [r3, #1]! CMP ip, r4 BNE exit_inn_cycle CMP r2, r7 BCC inn_cycle exit_inn_cycle SUB r4, r2, r7 ; len = MAX_MATCH - (int)(strend - scan); ADD r4, r4, #MAX_MATCH-256 ADD r4, r4, #256 SUB r2, r2, r4 ; scan = strend - MAX_MATCH CMP r4, r5 ; if (len > best_len) { BLE cycle_end LDR ip, [pc, #|__match_start|-.-8] ; match_start = cur_match; STR r0, [ip] MOV r5, r4 ; best_len = len; LDR ip, [pc, #|__nice_match|-.-8] ; if (len >= nice_match) LDR ip, [ip] CMP r4, ip BGE exit_match ; break; SUB ip, r5, #1 ; scan_end1 = scan[best_len-1]; LDRB r8, [r2, ip] LDRB r9, [r2, r5] ; scan_end = scan[best_len]; cycle_end MOV ip, r0, LSL #17 ; cur_match & WMASK MOV ip, ip, LSR #17 LDR r0, [fp, ip, ASL #1] ; cur_match = prev[cur_match & WMASK] MOV r0, r0, ASL #16 MOV r0, r0, LSR #16 CMP r0, r6 ; cur_match > limit BLS exit_match SUBS r1, r1, #1 ; --chain_length BNE cycle ; chain_length != 0 exit_match MOV r0, r5 LDMFD sp!, {r4-r9,fp,pc}^ END zip30/acorn/osdep.h0100644000076400000060000000145010655035164012353 0ustar edisk/* Copyright (c) 1990-2007 Info-ZIP. All rights reserved. See the accompanying file LICENSE, version 2007-Mar-4 or later (the contents of which are also included in zip.h) for terms of use. If, for some reason, all these files are missing, the Info-ZIP license also may be found at: ftp://ftp.info-zip.org/pub/infozip/license.html */ #include "riscos.h" #define RISCOS #define NO_SYMLINKS #define NO_FCNTL_H #define NO_UNISTD_H #define NO_MKTEMP #define PROCNAME(n) (action == ADD || action == UPDATE ? wild(n) : \ procname(n, 1)) #define isatty(a) 1 #define fseek(f,o,t) riscos_fseek((f),(o),(t)) #define localtime riscos_localtime #define gmtime riscos_gmtime #ifdef ZCRYPT_INTERNAL # define ZCR_SEED2 (unsigned)3141592654L /* use PI as seed pattern */ #endif zip30/acorn/ReadMe0100644000076400000060000001043306421302426012143 0ustar ediskAcorn-specific compile instructions ----------------------------------- Use the "RunMe1st" file (it is an Obey file) to convert all the files from "filename/[chs]" to "[chs].filename" (so that zip could be easily compiled under RISC OS). It will also set the correct makefile. To compile just set the CSD to the main zip directory and run 'amu'. Currently only the Acorn C V5 compiler has been tested but probably also Acorn C V4 and the Acorn Assembler V2 will be able to compile zip. The default makefile is configured without the support for the Extended Timestamp Extra Field. If you wan to enable it you have to add "-DUSE_EF_UT_TIME" to CFLAGS (see makefile). Without the Extended Timestamp Field support, zipfiles created by zip are identical to the zipfiles created by SparkFS. However, the Extended Timestamp Field can be useful if you are going to unzip your zipfiles on a non-RISC OS machine since the correct time stamp will be preserved across different timezones. Note that in this case, both the SparkFS Extra Field and the Extended Timestamp Extra Field will be used, so the zipfiles will still be fully compatible with SparkFS and with the RISC OS version of unzip. The executables-only distributions will be compiled without the support for the Extended Timestamp Extra Field. If you need it but you can't compile zip yourself, you can contact the authors at the Info-ZIP address who will do it for you. Acorn-specific usage instructions --------------------------------- An extra option ('I') has been added to the Acorn port: if it is specified zip will not consider Image files (eg. DOS partitions or Spark archives when SparkFS is loaded) as directories but will store them as single files. This means that if you have, say, SparkFS loaded, zipping a Spark archive will result in a zipfile containing a directory (and its content) while using the 'I' option will result in a zipfile containing a Spark archive. Obviously this second case will also be obtained (without the 'I' option) if SparkFS isn't loaded. When adding files to a zipfile; to maintain FileCore compliance, all files named "file/ext" will be added to the archive as "file.ext". This presents no problem if you wish to use unzip to extract them on any other machine, as the files are correctly named. This also presents no problem if you use unzip for RISC OS, as the files are converted back to "file/ext" format. The only problem appears when you use SparkFS to decompress the files, as a file called "file.ext" will be extracted as "file_ext", not what it was added as. You must be careful about this. Case Specific. Depending on how you type the command, files will be added exactly as named; in this example: *zip new/zip newfile *zip new/zip NewFile *zip new/zip NEWFILE will create an archive containing 3 copies of the same Risc OS file 'newfile' called 'newfile', 'NewFile' and 'NEWFILE'. Please be careful. The Acorn port conserves file attributes, including filetype, so if you zip on an Acorn, and unzip on another Acorn, filetypes will be maintained precisely as if you used uncompressed files. If you de-archive on another machine (PC, Mac, Unix etc..), filetypes will be ignored, but the files will be identical despite this. This feature is fully compatible with SparkFS, so zipfiles created by zip will be correctly uncompressed (including filetype, etc.) by SparkFS. An additional feature went into this port to cope better with C-code and extensions. This allows the acorn files "c.foo" to be added to the archive as "foo/c", eventually appearing in the archive as "foo.c", allowing for better handling of C or C++ code. Example: *Set Zip$Exts "dir1:dir2:dir3" *zip new/zip dir1.file *zip new/zip dir2.help *zip new/zip dir3.textfile Creates a zipfile new/zip, with entries file.dir1, help.dir2, textfile.dir3. The usual settings for Zip$Exts are "h:o:s:c", allowing C code to be added to the archive in standard form. A final note about the Acorn port regards the use of the 'n' option: this is used to specify a list of suffixes that will not be compressed (eg. .ZIP, since it is already a compressed file). Since RISC OS uses filetypes instead of suffixes, this list of suffixes is actually considered as a list of filetypes (3 hex digit format). By default, zip doesn't compress filetypes DDC (Archive, Spark or Zip), D96 (CFS files) and 68E (PackDir). zip30/acorn/ReadMe.GMakefile0100644000076400000060000000115107430421222013760 0ustar ediskGMakefile is for use with Acorn RISC OS and the forthcoming post-Acorn RISC OS for the compilation of both the current release and development versions of zip. It is recommended that you use gcc 2.95.4 or higher and you will need a suitable 'make' utility. Both are available from . You will need the files gcc.zip and cc1.zip for the C compiler with the documentation available in the gccdoc.zip archive. GNU make can be found in the utils.zip archive, although most versions of 'make' should be fine. When using gcc, check RunMe1st for two lines which need uncommenting. zip30/acorn/riscos.c0100644000076400000060000001704010154331616012533 0ustar edisk/* Copyright (c) 1990-2002 Info-ZIP. All rights reserved. See the accompanying file LICENSE, version 2000-Apr-09 or later (the contents of which are also included in zip.h) for terms of use. If, for some reason, all these files are missing, the Info-ZIP license also may be found at: ftp://ftp.info-zip.org/pub/infozip/license.html */ /* riscos.c */ #include #include #include #include "zip.h" #include "riscos.h" #define MAXEXT 256 /* External globals */ extern int scanimage; /* Local globals (!?!?) */ char *exts2swap = NULL; /* Extensions to swap (actually, directory names) */ int stat(char *filename,struct stat *res) { int attr; /* object attributes */ unsigned int load; /* load address */ unsigned int exec; /* exec address */ int type; /* type: 0 not found, 1 file, 2 dir, 3 image */ if (!res) return -1; if (SWI_OS_File_5(filename,&type,&load,&exec,(int *)&res->st_size,&attr)!=NULL) return -1; if (type==0) return -1; res->st_dev=0; res->st_ino=0; res->st_nlink=0; res->st_uid=1; res->st_gid=1; res->st_rdev=0; res->st_blksize=1024; res->st_mode = ((attr & 0001) << 8) | ((attr & 0002) << 6) | ((attr & 0020) >> 2) | ((attr & 0040) >> 4); switch (type) { case 1: /* File */ res->st_mode |= S_IFREG; break; case 2: /* Directory */ res->st_mode |= S_IFDIR | 0700; break; case 3: /* Image file */ if (scanimage) res->st_mode |= S_IFDIR | 0700; else res->st_mode |= S_IFREG; break; } if ((((unsigned int) load) >> 20) == 0xfff) { /* date stamped file */ unsigned int t1, t2, tc; t1 = (unsigned int) (exec); t2 = (unsigned int) (load & 0xff); tc = 0x6e996a00U; if (t1 < tc) t2--; t1 -= tc; t2 -= 0x33; /* 00:00:00 Jan. 1 1970 = 0x336e996a00 */ t1 = (t1 / 100) + (t2 * 42949673U); /* 0x100000000 / 100 = 42949672.96 */ t1 -= (t2 / 25); /* compensate for .04 error */ res->st_atime = res->st_mtime = res->st_ctime = t1; } else res->st_atime = res->st_mtime = res->st_ctime = 0; return 0; } #ifndef SFX DIR *opendir(char *dirname) { DIR *thisdir; int type; int attr; os_error *er; thisdir=(DIR *)malloc(sizeof(DIR)); if (thisdir==NULL) return NULL; thisdir->dirname=(char *)malloc(strlen(dirname)+1); if (thisdir->dirname==NULL) { free(thisdir); return NULL; } strcpy(thisdir->dirname,dirname); if (thisdir->dirname[strlen(thisdir->dirname)-1]=='.') thisdir->dirname[strlen(thisdir->dirname)-1]=0; if (er=SWI_OS_File_5(thisdir->dirname,&type,NULL,NULL,NULL,&attr),er!=NULL || type<=1 || (type==3 && !scanimage)) { free(thisdir->dirname); free(thisdir); return NULL; } thisdir->buf=malloc(DIR_BUFSIZE); if (thisdir->buf==NULL) { free(thisdir->dirname); free(thisdir); return NULL; } thisdir->size=DIR_BUFSIZE; thisdir->offset=0; thisdir->read=0; return thisdir; } struct dirent *readdir(DIR *d) { static struct dirent dent; if (d->read==0) { /* no more objects read in the buffer */ if (d->offset==-1) { /* no more objects to read */ return NULL; } d->read=255; if (SWI_OS_GBPB_9(d->dirname,d->buf,&d->read,&d->offset,DIR_BUFSIZE,NULL)!=NULL) return NULL; if (d->read==0) { d->offset=-1; return NULL; } d->read--; d->act=(char *)d->buf; } else { /* some object is ready in buffer */ d->read--; d->act=(char *)(d->act+strlen(d->act)+1); } strcpy(dent.d_name,d->act); dent.d_namlen=strlen(dent.d_name); return &dent; } void closedir(DIR *d) { if (d->buf!=NULL) free(d->buf); if (d->dirname!=NULL) free(d->dirname); free(d); } int unlink(f) char *f; /* file to delete */ /* Delete the file *f, returning non-zero on failure. */ { os_error *er; char canon[256]; int size=255; er=SWI_OS_FSControl_37(f,canon,&size); if (er==NULL) { er=SWI_OS_FSControl_27(canon,0x100); } else { er=SWI_OS_FSControl_27(f,0x100); } return (int)er; } int deletedir(char *d) { int objtype; char *s; int len; os_error *er; len = strlen(d); if ((s = malloc(len + 1)) == NULL) return -1; strcpy(s,d); if (s[len-1]=='.') s[len-1]=0; if (er=SWI_OS_File_5(s,&objtype,NULL,NULL,NULL,NULL),er!=NULL) { free(s); return -1; } if (objtype<2 || (!scanimage && objtype==3)) { /* this is a file or it doesn't exist */ free(s); return -1; } if (er=SWI_OS_File_6(s),er!=NULL) { /* maybe this is a problem with the DDEUtils module, try to canonicalise the path */ char canon[256]; int size=255; if (er=SWI_OS_FSControl_37(s,canon,&size),er!=NULL) { free(s); return -1; } if (er=SWI_OS_File_6(canon),er!=NULL) { free(s); return -1; } } free(s); return 0; } #endif /* !SFX */ int chmod(char *file, int mode) { /*************** NOT YET IMPLEMENTED!!!!!! ******************/ /* I don't know if this will be needed or not... */ file=file; mode=mode; return 0; } void setfiletype(char *fname,int ftype) { char str[256]; sprintf(str,"SetType %s &%3.3X",fname,ftype); SWI_OS_CLI(str); } void getRISCOSexts(char *envstr) { char *envptr; /* value returned by getenv */ envptr = getenv(envstr); if (envptr == NULL || *envptr == 0) return; exts2swap=malloc(1+strlen(envptr)); if (exts2swap == NULL) return; strcpy(exts2swap, envptr); } int checkext(char *suff) { register char *extptr=exts2swap; register char *suffptr; register int e,s; if (extptr != NULL) while(*extptr) { suffptr=suff; e=*extptr; s=*suffptr; while (e && e!=':' && s && s!='.' && s!='/' && e==s) { e=*++extptr; s=*++suffptr; } if (e==':') e=0; if (s=='.' || s=='/') s=0; if (!e && !s) { return 1; } while(*extptr!=':' && *extptr!='\0') /* skip to next extension */ extptr++; if (*extptr!='\0') extptr++; } return 0; } int swapext(char *name, char *exptr) { char *ext; char *p1=exptr; char *p2; int extchar=*exptr; unsigned int i=0; while(*++p1 && *p1!='.' && *p1!='/') ; ext=malloc(i=p1-exptr); if (!ext) return 1; memcpy(ext, exptr+1, i); p2=exptr-1; p1=exptr+i-1; while(p2 >= name) *p1--=*p2--; strcpy(name,ext); *p1=(extchar=='/'?'.':'/'); free(ext); return 0; } void remove_prefix(void) { SWI_DDEUtils_Prefix(NULL); } void set_prefix(void) { char *pref; int size=0; if (SWI_OS_FSControl_37("@",pref,&size)!=NULL) return; size=1-size; if (pref=malloc(size),pref!=NULL) { if (SWI_OS_FSControl_37("@",pref,&size)!=NULL) { free(pref); return; } if (SWI_DDEUtils_Prefix(pref)==NULL) { atexit(remove_prefix); } free(pref); } } #ifdef localtime # undef localtime #endif #ifdef gmtime # undef gmtime #endif /* Acorn's implementation of localtime() and gmtime() * doesn't consider the timezone offset, so we have to * add it before calling the library functions */ struct tm *riscos_localtime(const time_t *timer) { time_t localt=*timer; localt+=SWI_Read_Timezone()/100; return localtime(&localt); } struct tm *riscos_gmtime(const time_t *timer) { time_t localt=*timer; localt+=SWI_Read_Timezone()/100; return gmtime(&localt); } int riscos_fseek(FILE *fd, long offset, int whence) { int ret; switch (whence) { case SEEK_END: ret = (fseek) (fd, 0, SEEK_END); if (ret) return ret; /* fall through */ case SEEK_CUR: offset += ftell (fd); /* fall through */ default: /* SEEK_SET */ return (fseek) (fd, offset < 0 ? 0 : offset, SEEK_SET); } } zip30/acorn/riscos.h0100644000076400000060000000540207427043440012543 0ustar edisk/* Copyright (c) 1990-2002 Info-ZIP. All rights reserved. See the accompanying file LICENSE, version 2000-Apr-09 or later (the contents of which are also included in zip.h) for terms of use. If, for some reason, all these files are missing, the Info-ZIP license also may be found at: ftp://ftp.info-zip.org/pub/infozip/license.html */ /* riscos.h */ #ifndef __riscos_h #define __riscos_h #include #include typedef struct { int errnum; char errmess[252]; } os_error; #ifndef __swiven_h # include "swiven.h" #endif #define MAXPATHLEN 256 #define MAXFILENAMELEN 64 /* should be 11 for ADFS, 13 for DOS, 64 seems a sensible value... */ #define DIR_BUFSIZE 1024 /* this should be enough to read a whole E-Format directory */ struct stat { unsigned int st_dev; int st_ino; unsigned int st_mode; int st_nlink; unsigned short st_uid; unsigned short st_gid; unsigned int st_rdev; unsigned int st_size; unsigned int st_blksize; time_t st_atime; time_t st_mtime; time_t st_ctime; }; typedef struct { char *dirname; void *buf; int size; char *act; int offset; int read; } DIR; #define dstrm DIR struct dirent { unsigned int d_off; /* offset of next disk directory entry */ int d_fileno; /* file number of entry */ size_t d_reclen; /* length of this record */ size_t d_namlen; /* length of d_name */ char d_name[MAXFILENAMELEN]; /* name */ }; typedef struct { unsigned int load_addr; unsigned int exec_addr; int lenght; int attrib; int objtype; char name[13]; } riscos_direntry; #define SPARKID 0x4341 /* = "AC" */ #define SPARKID_2 0x30435241 /* = "ARC0" */ typedef struct { short ID; short size; int ID_2; unsigned int loadaddr; unsigned int execaddr; int attr; int zero; } extra_block; #define S_IFMT 0770000 #define S_IFDIR 0040000 #define S_IFREG 0100000 /* 0200000 in UnixLib !?!?!?!? */ #ifndef S_IEXEC # define S_IEXEC 0000100 # define S_IWRITE 0000200 # define S_IREAD 0000400 #endif extern char *exts2swap; /* Extensions to swap */ int stat(char *filename,struct stat *res); DIR *opendir(char *dirname); struct dirent *readdir(DIR *d); char *readd(DIR *d); void closedir(DIR *d); int unlink(char *f); int chmod(char *file, int mode); void setfiletype(char *fname,int ftype); void getRISCOSexts(char *envstr); int checkext(char *suff); int swapext(char *name, char *exptr); void remove_prefix(void); void set_prefix(void); struct tm *riscos_localtime(const time_t *timer); struct tm *riscos_gmtime(const time_t *timer); int riscos_fseek(FILE *fd, long offset, int whence); /* work around broken assumption that fseek() is OK with -ve file offsets */ #endif /* !__riscos_h */ zip30/acorn/RunMe1st0100644000076400000060000000146307420230360012464 0ustar edisk| This Obey file prepares the zip port for a Desktop C re-compile. | Run it and it will copy all the needed files into the correct | place. | Set the correct type of 'srcrename' so that the only requirement | for the user is to set 'RunMe1st' to Obey SetType .srcrename FF8 | Run 'srcrename' on the main zip directory with recursion enabled /.srcrename -r -e c:h:s:o .^ | Create the 'o' directory CDir .^.o | Put the Makefile in its correct place and set the correct filetype Copy .makefile .^.makefile ~C ~V F | Uncomment the following lines if you're using gcc || Put the Makefile in its correct place and set the correct filetype |Copy .GMakefile .^.makefile ~C~VF SetType .^.makefile FE1 SetType .zipsfx Obey zip30/acorn/sendbits.s0100644000076400000060000000536407011110216013057 0ustar edisk;=========================================================================== ; Copyright (c) 1990-1999 Info-ZIP. All rights reserved. ; ; See the accompanying file LICENSE, version 1999-Oct-05 or later ; (the contents of which are also included in zip.h) for terms of use. ; If, for some reason, both of these files are missing, the Info-ZIP license ; also may be found at: ftp://ftp.cdrom.com/pub/infozip/license.html ;=========================================================================== ; sendbits.s for ARM by Sergio Monesi and Darren Salt. r0 RN 0 r1 RN 1 r2 RN 2 r3 RN 3 r4 RN 4 r5 RN 5 r6 RN 6 r7 RN 7 r8 RN 8 r9 RN 9 sl RN 10 fp RN 11 ip RN 12 sp RN 13 lr RN 14 pc RN 15 AREA |Asm$$Code|, CODE, READONLY = "send_bits",0 ALIGN & &FF00000C IMPORT __rt_stkovf_split_small IMPORT flush_outbuf IMPORT bi_valid IMPORT bi_buf IMPORT out_size IMPORT out_offset IMPORT out_buf EXPORT send_bits send_bits MOV ip,sp STMDB sp!,{r4,r5,fp,ip,lr,pc} SUB fp,ip,#4 LDR r5,=bi_buf LDR r3,=bi_valid LDR r4,[r5] LDR r2,[r3] ORR r4,r4,r0,LSL r2 ; |= value<= out_size-1 LDRHS r0,=out_buf LDRHS r0,[r0] BLHS flush_outbuf ; then flush the buffer LDR r0,=out_buf LDR r1,=out_offset LDR r0,[r0] LDR r2,[r1] MOV r5,r4,LSR #8 STRB r4,[r0,r2]! ; store 'old' bi_buf STRB r5,[r0,#1] ADD r2,r2,#2 STR r2,[r1] LDMDB fp,{r4,r5,fp,sp,pc}^ ptr_bi & bi_valid & bi_buf = "bi_reverse",0 ALIGN & &FF00000C EXPORT bi_reverse bi_reverse MOV r2,#0 loop MOVS r0,r0,LSR #1 ADCS r2,r2,r2 SUBS r1,r1,#1 BNE loop MOV r0,r2 MOVS pc,lr END zip30/acorn/srcrename0100644000076400000060000001403707020663036012774 0ustar ediskp  N L 0T@TS\_fKہr`=6蹣3Ҝ;Լۻȥ|ݫ")<0 PњpPNzM_4fK̟μ6~*1? el Iw _f4̼}(y2;#:=6!3>~vK_.MmdŚiҚªYSqlКeVՑ 𩡼㪡Iwb}ܪ4Q$ Pњ_f4{('% _f 4LOV8#f nqk5aje}r9J7=ϔ۹繼0ۻ20rۻS1z1cwyr}3yyɄɦ.x? 6jJhF;d)Ϋe*/ybQ _4fKPu?»|6vVݥVu8zqQɚ_f 4PK:ZtQɻr(>UIrz{y0۪@8on=qܨU˧rm=6p7N]n˳Iwۯy{ۻ/sGU9RA_f 4iHl:UFGz̸|2­:v@k]+jƚhFAI~sۯy{ۻ-͑ɯP6ѯ“6tiaj¹ۻp,<=g56 h}rܩϛ!sfrOk~(rs>TKeͯ޹T{'wc9۝dUܝM௛ol)ij|ɻ ljɁϼ\|]櫙ۈSXuͪ Zt皬 _g4h˷|̯Ź6a[^FF6bFr}|B56]pR9o*>43Ġ=`_6ۯ֬_4ghg ̆n+hz+Z&'fRˊŧ\6˩[W{6VFF6[Frq|B4m6UpR8o*K=HYX6ۯ.rXۼbی5%2"&̂2"#2!3  DC_f 4M0q/˜4.TͻZbrZ{sar6@7L-l-@A̅H*˼)ɾǼd˯~wtZP}$o9<=rxּ̳c# տؼ5ɹ|}S˿V&޼:|r}"7*}Sʹ9|oI;nۓּ̳gv;6:ʼ_4f^E ݿ` T|xTΪfj fTfFUNMnrOB c_4f8``v:u܂7S_f4B[^ +˫-,96I8 _4f`̏pGD87?=BGl86+Cd̛XYY۷O5LH@G п*0 b ,`/ k7mBiblC t ߰ `/_T    &2\=c!Ogx/okPkkGnHٚ~tap p_`KT     +\~D4  f\`9]\'.Ts ĖFq Of^$2`_fI\ jIdaP_ ]] bٺi8xȺ3ֻE;N ۺk% hE B!<qC5 Eɻ#"/DTI#. 'ga\? R P V A  _f E°8]Fd Ua] f ^ GS ^ 󴸺OͿT]]E a ] ̰Dh? `dIaS k   PEd\TDǻ@Lj-(h/_ b:b)T^4\S\\X1\\v'AQ 6}g\ӠO_ @0|l ?`@ k k kkk  k a=^c kl`\?kY\` \tk k ll\{k{:ؿ: _p/{/\xj k    k( Р5&4 6'D\gd '"j\ 2_h: kk|kll7@\|lнT]|\X] ]p\^TeD_$*\^^*]\am`dPc_Pa,_^\_\a]kkp]dl$x-ol`|\xkt\\kk\pk.k{|*kkl{ \hklklkl _\lkkZk\x{\l{k*lkkl k䟛kkk`o_@BBkL"&>.kll4kl\k|\|kVkXk"T|hl߰o.kkklkllAl|k|ol{_po?@_ _)J_y *J_ͺ@   iI\u!\(N3\^(\d^pQJD&% &&-;:>&% 4&-\Y\B## ,! '?)  !: D\m'(G`\D\ ! 7\_ /%V } ?,O? @ JoV` q P@ 0[) QQ T 00K00Q\Q00Q00\Q00T  @PMo@U H Z5`z0 SzASzzD@ zzzzL&2 SzQ0(SzzT0(P0( zzzz\0(] `I ]ʽ|Hrcc 5.00 zip30/acorn/swiven.h0100644000076400000060000000344107011110234012536 0ustar edisk/* Copyright (c) 1990-1999 Info-ZIP. All rights reserved. See the accompanying file LICENSE, version 1999-Oct-05 or later (the contents of which are also included in zip.h) for terms of use. If, for some reason, both of these files are missing, the Info-ZIP license also may be found at: ftp://ftp.cdrom.com/pub/infozip/license.html */ /* swiven.h */ #ifndef __swiven_h #define __swiven_h os_error *SWI_OS_FSControl_26(char *source, char *dest, int actionmask); /* copy */ os_error *SWI_OS_FSControl_27(char *filename, int actionmask); /* wipe */ os_error *SWI_OS_GBPB_9(char *dirname, void *buf, int *number, int *offset, int size, char *match); /* read dir */ os_error *SWI_OS_File_1(char *filename, unsigned int loadaddr, unsigned int execaddr, int attrib); /* write file attributes */ os_error *SWI_OS_File_5(char *filename, int *objtype, unsigned int *loadaddr, unsigned int *execaddr, int *length, int *attrib); /* read file info */ os_error *SWI_OS_File_6(char *filename); /* delete */ os_error *SWI_OS_File_7(char *filename, int loadaddr, int execaddr, int size); /* create an empty file */ os_error *SWI_OS_CLI(char *cmd); /* execute a command */ int SWI_OS_ReadC(void); /* get a key from the keyboard buffer */ os_error *SWI_OS_ReadVarVal(char *var, char *buf, int len, int *bytesused); /* reads an OS varibale */ os_error *SWI_OS_FSControl_54(char *buffer, int dir, char *fsname, int *size); /* reads the path of a specified directory */ os_error *SWI_OS_FSControl_37(char *pathname, char *buffer, int *size); /* canonicalise path */ os_error *SWI_DDEUtils_Prefix(char *dir); /* sets the 'prefix' directory */ int SWI_Read_Timezone(void); /* returns the timezone offset (centiseconds) */ #endif /* !__swiven_h */ zip30/acorn/swiven.s0100644000076400000060000001460407011110254012556 0ustar edisk;=========================================================================== ; Copyright (c) 1990-1999 Info-ZIP. All rights reserved. ; ; See the accompanying file LICENSE, version 1999-Oct-05 or later ; (the contents of which are also included in zip.h) for terms of use. ; If, for some reason, both of these files are missing, the Info-ZIP license ; also may be found at: ftp://ftp.cdrom.com/pub/infozip/license.html ;=========================================================================== ; SWI veneers used by Zip/Unzip ; r0 RN 0 r1 RN 1 r2 RN 2 r3 RN 3 r4 RN 4 r5 RN 5 r6 RN 6 r7 RN 7 r8 RN 8 r9 RN 9 r10 RN 10 r11 RN 11 r12 RN 12 sp RN 13 lr RN 14 pc RN 15 sl RN 10 fp RN 11 ip RN 12 XOS_Bit EQU &020000 OS_GBPB EQU &00000C OS_File EQU &000008 OS_FSControl EQU &000029 OS_CLI EQU &000005 OS_ReadC EQU &000004 OS_ReadVarVal EQU &000023 DDEUtils_Prefix EQU &042580 Territory_ReadCurrentTimeZone EQU &043048 MACRO STARTCODE $name EXPORT $name $name MEND AREA |C$$code|, CODE, READONLY ; os_error *SWI_OS_FSControl_26(char *source, char *dest, int actionmask); STARTCODE SWI_OS_FSControl_26 MOV ip, lr MOV r3, r2 MOV r2, r1 MOV r1, r0 MOV r0, #26 SWI OS_FSControl + XOS_Bit MOVVC r0, #0 MOVS pc, ip ; os_error *SWI_OS_FSControl_27(char *filename, int actionmask); STARTCODE SWI_OS_FSControl_27 MOV ip, lr MOV r3, r1 MOV r1, r0 MOV r0, #27 SWI OS_FSControl + XOS_Bit MOVVC r0, #0 MOVS pc, ip ; os_error *SWI_OS_GBPB_9(char *dirname, void *buf, int *number, ; int *offset, int size, char *match); STARTCODE SWI_OS_GBPB_9 MOV ip, sp STMFD sp!, {r2-r6,lr} LDMIA ip, {r5,r6} LDR r4, [r3] LDR r3, [r2] MOV r2, r1 MOV r1, r0 MOV r0, #9 SWI OS_GBPB + XOS_Bit LDMVSFD sp!, {r2-r6,pc}^ MOV r0, #0 LDMFD sp, {r5,r6} STR r3, [r5] STR r4, [r6] LDMFD sp!, {r2-r6,pc}^ ; os_error *SWI_OS_File_1(char *filename, int loadaddr, int execaddr, int attrib); STARTCODE SWI_OS_File_1 STMFD sp!, {r5,lr} MOV r5, r3 MOV r3, r2 MOV r2, r1 MOV r1, r0 MOV r0, #1 SWI OS_File + XOS_Bit MOVVC r0, #0 LDMFD sp!, {r5,pc}^ ; os_error *SWI_OS_File_5(char *filename, int *objtype, int *loadaddr, ; int *execaddr, int *length, int *attrib); STARTCODE SWI_OS_File_5 STMFD sp!, {r1-r5,lr} MOV r1, r0 MOV r0, #5 SWI OS_File + XOS_Bit LDMVSFD sp!, {r1-r5,pc}^ LDR lr, [sp] TEQ lr, #0 STRNE r0, [lr] LDR lr, [sp, #4] TEQ lr ,#0 STRNE r2, [lr] LDR lr, [sp, #8] TEQ lr, #0 STRNE r3, [lr] LDR lr, [sp ,#24] TEQ lr, #0 STRNE r4, [lr] LDR lr, [sp ,#28] TEQ lr, #0 STRNE r5, [lr] MOV r0, #0 LDMFD sp!, {r1-r5,pc}^ ; os_error *SWI_OS_File_6(char *filename); STARTCODE SWI_OS_File_6 STMFD sp!, {r4-r5,lr} MOV r1, r0 MOV r0, #6 SWI OS_File + XOS_Bit MOVVC r0, #0 LDMFD sp!, {r4-r5,pc}^ ; os_error *SWI_OS_File_7(char *filename, int loadaddr, int execaddr, int size); STARTCODE SWI_OS_File_7 STMFD sp!, {r4-r5,lr} MOV r5, r3 MOV r4, #0 MOV r3, r2 MOV r2, r1 MOV r1, r0 MOV r0, #7 SWI OS_File + XOS_Bit MOVVC r0, #0 LDMFD sp!, {r4-r5,pc}^ ; os_error *SWI_OS_CLI(char *cmd); STARTCODE SWI_OS_CLI MOV ip, lr SWI OS_CLI + XOS_Bit MOVVC r0, #0 MOVS pc, ip ; int SWI_OS_ReadC(void); STARTCODE SWI_OS_ReadC MOV ip, lr SWI OS_ReadC + XOS_Bit MOVS pc, ip ; os_error *SWI_OS_ReadVarVal(char *var, char *buf, int len, int *bytesused); STARTCODE SWI_OS_ReadVarVal STMFD sp!, {r4,lr} MOV ip, r3 MOV r3, #0 MOV r4, #0 SWI OS_ReadVarVal + XOS_Bit LDMVSFD sp!, {r4,pc}^ TEQ ip, #0 STRNE r2, [ip] MOV r0, #0 LDMFD sp!, {r4,pc}^ ; os_error *SWI_OS_FSControl_54(char *buffer, int dir, char *fsname, int *size); STARTCODE SWI_OS_FSControl_54 STMFD sp!, {r3-r6,lr} LDR r5, [r3] MOV r3, r2 MOV r2, r1 MOV r1, r0 MOV r0, #54 SWI OS_FSControl + XOS_Bit LDMVSFD sp!, {r3-r6,pc}^ MOV r0, #0 LDMFD sp!, {r3} STR r5, [r3] LDMFD sp!, {r4-r6,pc}^ ; os_error *SWI_OS_FSControl_37(char *pathname, char *buffer, int *size); STARTCODE SWI_OS_FSControl_37 STMFD sp!, {r2,r3-r5,lr} LDR r5, [r2] MOV r3, #0 MOV r4, #0 MOV r2, r1 MOV r1, r0 MOV r0, #37 SWI OS_FSControl + XOS_Bit LDMVSFD sp!, {r2,r3-r5,pc}^ MOV r0, #0 LDMFD sp!, {r2} STR r5, [r2] LDMFD sp!, {r3-r5,pc}^ ; os_error *SWI_DDEUtils_Prefix(char *dir); STARTCODE SWI_DDEUtils_Prefix MOV ip, lr SWI DDEUtils_Prefix + XOS_Bit MOVVC r0, #0 MOVS pc, ip ; int SWI_Read_Timezone(void); STARTCODE SWI_Read_Timezone MOV ip, lr SWI Territory_ReadCurrentTimeZone + XOS_Bit MOVVC r0, r1 MOVVS r0, #0 MOVS pc, ip END zip30/acorn/zipsfx0100644000076400000060000000053407077214620012340 0ustar edisk| zipsfx 0.1 | Written by Darren Salt | Assumes that unzipsfx is on Run$Path (eg. in !Boot.Library) | Assumes that IfThere is available as either *command or utility If "%1" = "" Then Error 220 Syntax: zipsfx | | If "%0" = "" Then Error 220 Syntax: zipsfx | | Copy Run:unzipsfx %1 A~C~D~F~L~N~R~S~T~V Print %0 { >> %1 }zip30/acorn/zipup.h0100644000076400000060000000106607011110264012376 0ustar edisk/* Copyright (c) 1990-1999 Info-ZIP. All rights reserved. See the accompanying file LICENSE, version 1999-Oct-05 or later (the contents of which are also included in zip.h) for terms of use. If, for some reason, both of these files are missing, the Info-ZIP license also may be found at: ftp://ftp.cdrom.com/pub/infozip/license.html */ #define fhow "r" #define fbad (NULL) typedef FILE *ftype; #define zopen(n,p) fopen(n,p) #define zread(f,b,n) fread((b),1,(n),(FILE*)(f)) #define zclose(f) fclose(f) #define zerr(f) (k==(extent)(-1L)) #define zstdin 0 zip30/amiga/0040755000076400000060000000000011033727770011051 5ustar ediskzip30/amiga/amiga.c0100644000076400000060000001013210272630542012257 0ustar edisk/* Copyright (c) 1990-2005 Info-ZIP. All rights reserved. See the accompanying file LICENSE, version 2005-Feb-10 or later (the contents of which are also included in zip.h) for terms of use. If, for some reason, all these files are missing, the Info-ZIP license also may be found at: ftp://ftp.info-zip.org/pub/infozip/license.html */ /* OS specific routines for AMIGA platform. * * John Bush BIX: jbush * Paul Kienitz * * History: * * Date DoBee Comments * ------- -------- ----------------------------------------------- * 21Jan93 JBush Original coding. * Incorporated filedate.c (existing routine). * * 31Jan93 JBush Made filedate.c include unconditional. * * 18Jul93 PaulK Moved Aztec _abort() here from stat.c because we * can't share the same one between Zip and UnZip. * Added close_leftover_open_dirs() call to it. * * 17Apr95 PaulK Added Amiga internal version string so that * installer programs can compare the version being * installed to see if the copy the user already has * is older or newer. Added Prestart_Hook to support * debug tracing in deflate.a. * * 6May95 PaulK Added GetComment() for filenote support. * * 12Nov95 PaulK Added #define ZIP in front of filedate.c, for * new options in there; removed declare of set_con() * since echon() no longer expands to it (or anything). * * 12Feb96 PaulK Removed call of echon() entirely. * * 12Jul97 PaulK Made both Aztec and SAS define USE_TIME_LIB for filedate.c * * 26Aug97 PaulK Added ClearIOErr_exit() * * 2Jan98 HWalt Adapted for SAS/C using stat.c replacement functions * * 6Jun00 PaulK Removed references to time_lib, since new filedate.c * supercedes it */ #include #ifdef AZTEC_C # include # include # include # include # include # include #else # include # include #endif #include #include "ziperr.h" void ziperr(int c, const char *h); #define ZIP #if !defined(UTIL) # define NO_MKTIME #endif #ifdef AZTEC_C /* ============================================================= */ /* filedate.c is an external file, since it's shared with UnZip. */ /* Aztec includes it here, but SAS/C now compiles it separately. */ # include "amiga/filedate.c" /* the same applies to stat.c */ # include "amiga/stat.c" # define setenv BOGUS_INCOMPATIBLE_setenv # include # undef setenv # ifdef DEBUG # define PRESTART_HOOK # endif #endif extern void close_leftover_open_dirs(void); /* the following handles cleanup when a ^C interrupt happens: */ void _abort(void) /* called when ^C is pressed */ { close_leftover_open_dirs(); ziperr(ZE_ABORT, "^C"); } void ClearIOErr_exit(int e) /* EXIT is defined as this */ { if (!e) ((struct Process *) FindTask(NULL))->pr_Result2 = 0; /* we clear IoErr() since we are successful, in a 1.x-compatible way */ exit(e); } /* Make sure the version number here matches the number in revision.h */ /* as closely as possible in strict decimal "#.#" form: */ const char version_id[] = "\0$VER: Zip 2.3 (" # include "env:VersionDate" ")\r\n"; /* call this with an arg of NULL to free storage: */ char *GetComment(char *filename) { BPTR lk; static struct FileInfoBlock *fib = NULL; if (!filename) { if (fib) FreeMem(fib, sizeof(*fib)); fib = NULL; return NULL; } if (!fib) { if (!(fib = AllocMem(sizeof(*fib), MEMF_PUBLIC))) ziperr(ZE_MEM, "was checking filenotes"); } if (!(lk = Lock(filename, ACCESS_READ))) return NULL; if (!Examine(lk, fib)) fib->fib_Comment[0] = '\0'; UnLock(lk); return fib->fib_Comment[0] ? &fib->fib_Comment[0] : NULL; } zip30/amiga/amiga.h0100644000076400000060000000271707011110320012256 0ustar edisk/* Copyright (c) 1990-1999 Info-ZIP. All rights reserved. See the accompanying file LICENSE, version 1999-Oct-05 or later (the contents of which are also included in zip.h) for terms of use. If, for some reason, both of these files are missing, the Info-ZIP license also may be found at: ftp://ftp.cdrom.com/pub/infozip/license.html */ #ifndef __amiga_amiga_h #define __amiga_amiga_h /* amiga.h * * Globular definitions that affect all of AmigaDom. * * Originally included in unzip.h, extracted for simplicity and eeze of * maintenance by John Bush. * * This version is for use with Zip. It is not globally included, but used * only by functions in amiga/amigazip.c. Much material that was needed for * UnZip is absent here. * */ #include /* O_BINARY for open() w/o CR/LF translation */ #include "amiga/z-stat.h" /* substitute for and */ #define direct dirent #ifndef MODERN # define MODERN #endif #ifdef AZTEC_C /* Manx Aztec C, 5.0 or newer only */ # include # include /* do inline dos.library calls */ # define O_BINARY 0 #endif /* AZTEC_C */ #ifdef __SASC # include # include # define disk_not_mounted 0 # if ( (!defined(O_BINARY)) && defined(O_RAW)) # define O_BINARY O_RAW # endif #endif /* SASC */ /* Funkshine Prough Toe Taipes */ LONG FileDate (char *, time_t[]); #endif /* __amiga_amiga_h */ zip30/amiga/amigazip.c0100644000076400000060000003431710154331630013010 0ustar edisk/* Copyright (c) 1990-1999 Info-ZIP. All rights reserved. See the accompanying file LICENSE, version 1999-Oct-05 or later (the contents of which are also included in zip.h) for terms of use. If, for some reason, both of these files are missing, the Info-ZIP license also may be found at: ftp://ftp.cdrom.com/pub/infozip/license.html */ #include "zip.h" #include "amiga/amiga.h" #ifndef UTIL /* the companion #endif is a bit of ways down ... */ #define utime FileDate #define PAD 0 #define PATH_END '/' /* Local globals (kinda like "military intelligence" or "broadcast quality") */ extern char *label; /* still declared in fileio.c */ local ulg label_time = 0; local ulg label_mode = 0; local time_t label_utim = 0; /* Local functions */ local char *readd OF((DIR *)); local int wild_recurse OF((char *, char *)); local char *readd(d) DIR *d; /* directory stream to read from */ /* Return a pointer to the next name in the directory stream d, or NULL if no more entries or an error occurs. */ { struct dirent *e = readdir(d); return e == NULL ? (char *) NULL : e->d_name; } /* What we have here is a mostly-generic routine using opendir()/readd() and */ /* isshexp()/MATCH() to find all the files matching a multi-part filespec */ /* using the portable pattern syntax. It shouldn't take too much fiddling */ /* to make it usable for any other platform that has directory hierarchies */ /* but no shell-level pattern matching. It works for patterns throughout */ /* the pathname, such as "foo:*.?/source/x*.[ch]". */ #define ONENAMELEN 30 /* the length of one filename component on the Amiga */ /* whole is a pathname with wildcards, wildtail points somewhere in the */ /* middle of it. All wildcards to be expanded must come AFTER wildtail. */ local int wild_recurse(whole, wildtail) char *whole; char *wildtail; { DIR *dir; char *subwild, *name, *newwhole = NULL, *glue = NULL, plug = 0, plug2; ush newlen, amatch = 0; BPTR lok; int e = ZE_MISS; if (!isshexp(wildtail)) if (lok = Lock(whole, ACCESS_READ)) { /* p exists? */ UnLock(lok); return procname(whole, 0); } else return ZE_MISS; /* woops, no wildcards! */ /* back up thru path components till existing dir found */ do { name = wildtail + strlen(wildtail) - 1; for (;;) if (name-- <= wildtail || *name == PATH_END) { subwild = name + 1; plug2 = *subwild; *subwild = 0; break; } if (glue) *glue = plug; glue = subwild; plug = plug2; dir = opendir(whole); } while (!dir && !disk_not_mounted && subwild > wildtail); wildtail = subwild; /* skip past non-wild components */ if ((subwild = strchr(wildtail + 1, PATH_END)) != NULL) { /* this "+ 1" dodges the ^^^ hole left by *glue == 0 */ *(subwild++) = 0; /* wildtail = one component pattern */ newlen = strlen(whole) + strlen(subwild) + (ONENAMELEN + 2); } else newlen = strlen(whole) + (ONENAMELEN + 1); if (!dir || !(newwhole = malloc(newlen))) { if (glue) *glue = plug; e = dir ? ZE_MEM : ZE_MISS; goto ohforgetit; } strcpy(newwhole, whole); newlen = strlen(newwhole); if (glue) *glue = plug; /* repair damage to whole */ if (!isshexp(wildtail)) { e = ZE_MISS; /* non-wild name not found */ goto ohforgetit; } while (name = readd(dir)) { if (MATCH(wildtail, name, 0)) { strcpy(newwhole + newlen, name); if (subwild) { name = newwhole + strlen(newwhole); *(name++) = PATH_END; strcpy(name, subwild); e = wild_recurse(newwhole, name); } else e = procname(newwhole, 0); newwhole[newlen] = 0; if (e == ZE_OK) amatch = 1; else if (e != ZE_MISS) break; } } ohforgetit: if (dir) closedir(dir); if (subwild) *--subwild = PATH_END; if (newwhole) free(newwhole); if (e == ZE_MISS && amatch) e = ZE_OK; return e; } int wild(p) char *p; { char *use; /* special handling of stdin request */ if (strcmp(p, "-") == 0) /* if compressing stdin */ return newname(p, 0, 0); /* wild_recurse() can't handle colons in wildcard part: */ if (use = strchr(p, ':')) { if (strchr(++use, ':')) return ZE_PARMS; } else use = p; return wild_recurse(p, use); } int procname(n, caseflag) char *n; /* name to process */ int caseflag; /* true to force case-sensitive match */ /* Process a name or sh expression to operate on (or exclude). Return an error code in the ZE_ class. */ { char *a; /* path and name for recursion */ DIR *d; /* directory stream from opendir() */ char *e; /* pointer to name from readd() */ int m; /* matched flag */ char *p; /* path for recursion */ struct stat s; /* result of stat() */ struct zlist far *z; /* steps through zfiles list */ if (strcmp(n, "-") == 0) /* if compressing stdin */ return newname(n, 0, caseflag); else if (LSSTAT(n, &s)) { /* Not a file or directory--search for shell expression in zip file */ p = ex2in(n, 0, (int *)NULL); /* shouldn't affect matching chars */ m = 1; for (z = zfiles; z != NULL; z = z->nxt) { if (MATCH(p, z->iname, caseflag)) { z->mark = pcount ? filter(z->zname, caseflag) : 1; if (verbose) fprintf(mesg, "zip diagnostic: %scluding %s\n", z->mark ? "in" : "ex", z->name); m = 0; } } free((zvoid *)p); return m ? ZE_MISS : ZE_OK; } /* Live name--use if file, recurse if directory */ if ((s.st_mode & S_IFDIR) == 0) { /* add or remove name of file */ if ((m = newname(n, 0, caseflag)) != ZE_OK) return m; } else { /* Add trailing / to the directory name */ if ((p = malloc(strlen(n)+2)) == NULL) return ZE_MEM; strcpy(p, n); a = p + strlen(p); if (*p && a[-1] != '/' && a[-1] != ':') strcpy(a, "/"); if (dirnames && (m = newname(p, 1, caseflag)) != ZE_OK) { free((zvoid *)p); return m; } /* recurse into directory */ if (recurse && (d = opendir(n)) != NULL) { while ((e = readd(d)) != NULL) { if ((a = malloc(strlen(p) + strlen(e) + 1)) == NULL) { closedir(d); free((zvoid *)p); return ZE_MEM; } strcat(strcpy(a, p), e); if ((m = procname(a, caseflag)) != ZE_OK) /* recurse on name */ { if (m == ZE_MISS) zipwarn("name not matched: ", a); else ziperr(m, a); } free((zvoid *)a); } closedir(d); } free((zvoid *)p); } /* (s.st_mode & S_IFDIR) == 0) */ return ZE_OK; } char *ex2in(x, isdir, pdosflag) char *x; /* external file name */ int isdir; /* input: x is a directory */ int *pdosflag; /* output: force MSDOS file attributes? */ /* Convert the external file name to a zip file name, returning the malloc'ed string or NULL if not enough memory. */ { char *n; /* internal file name (malloc'ed) */ char *t; /* shortened name */ int dosflag; dosflag = dosify; /* default for non-DOS and non-OS/2 */ /* Find starting point in name before doing malloc */ if ((t = strrchr(x, ':')) != NULL) /* reject ":" */ t++; else t = x; { /* reject "//" */ char *tt = t; while (tt = strchr(tt, '/')) while (*++tt == '/') t = tt; } while (*t == '/') /* reject leading "/" on what's left */ t++; if (!pathput) t = last(t, PATH_END); /* Malloc space for internal name and copy it */ if ((n = malloc(strlen(t) + 1)) == NULL) return NULL; strcpy(n, t); if (dosify) msname(n); /* Returned malloc'ed name */ if (pdosflag) *pdosflag = dosflag; return n; } char *in2ex(n) char *n; /* internal file name */ /* Convert the zip file name to an external file name, returning the malloc'ed string or NULL if not enough memory. */ { char *x; /* external file name */ if ((x = malloc(strlen(n) + 1 + PAD)) == NULL) return NULL; strcpy(x, n); return x; } void stamp(f, d) char *f; /* name of file to change */ ulg d; /* dos-style time to change it to */ /* Set last updated and accessed time of file f to the DOS time d. */ { time_t u[2]; /* argument for utime() */ /* Convert DOS time to time_t format in u */ u[0] = u[1] = dos2unixtime(d); /* Set updated and accessed times of f */ utime(f, u); } ulg filetime(f, a, n, t) char *f; /* name of file to get info on */ ulg *a; /* return value: file attributes */ long *n; /* return value: file size */ iztimes *t; /* return value: access, modific. and creation times */ /* If file *f does not exist, return 0. Else, return the file's last modified date and time as an MSDOS date and time. The date and time is returned in a long with the date most significant to allow unsigned integer comparison of absolute times. Also, if a is not a NULL pointer, store the file attributes there, with the high two bytes being the Unix attributes, and the low byte being a mapping of that to DOS attributes. If n is not NULL, store the file size there. If t is not NULL, the file's access, modification and creation times are stored there as UNIX time_t values. If f is "-", use standard input as the file. If f is a device, return a file size of -1 */ { struct stat s; /* results of stat() */ /* convert FNMAX to malloc - 11/8/04 EG */ char *name; int len = strlen(f); if (f == label) { if (a != NULL) *a = label_mode; if (n != NULL) *n = -2L; /* convention for a label name */ if (t != NULL) t->atime = t->mtime = t->ctime = label_utim; return label_time; } if ((name = malloc(len + 1)) == NULL) { ZIPERR(ZE_MEM, "filetime"); } strcpy(name, f); if (name[len - 1] == '/') name[len - 1] = '\0'; /* not all systems allow stat'ing a file with / appended */ if (strcmp(f, "-") == 0) { if (fstat(fileno(stdin), &s) != 0) error("fstat(stdin)"); } else if (SSTAT(name, &s) != 0) { /* Accept about any file kind including directories * (stored with trailing / with -r option) */ free(name); return 0; } free(name); if (a != NULL) { *a = ((ulg)s.st_mode << 16) | !(s.st_mode & S_IWRITE); if ((s.st_mode & S_IFDIR) != 0) { *a |= MSDOS_DIR_ATTR; } } if (n != NULL) *n = (s.st_mode & S_IFMT) == S_IFREG ? s.st_size : -1L; if (t != NULL) { t->atime = s.st_atime; t->mtime = s.st_mtime; t->ctime = s.st_ctime; } return unix2dostime(&s.st_mtime); } int set_extra_field(z, z_utim) struct zlist far *z; iztimes *z_utim; /* create extra field and change z->att if desired */ { #ifdef USE_EF_UT_TIME #ifdef IZ_CHECK_TZ if (!zp_tz_is_valid) return ZE_OK; /* skip silently if no valid TZ info */ #endif if ((z->extra = (char *)malloc(EB_HEADSIZE+EB_UT_LEN(1))) == NULL) return ZE_MEM; z->extra[0] = 'U'; z->extra[1] = 'T'; z->extra[2] = EB_UT_LEN(1); /* length of data part of e.f. */ z->extra[3] = 0; z->extra[4] = EB_UT_FL_MTIME; z->extra[5] = (char)(z_utim->mtime); z->extra[6] = (char)(z_utim->mtime >> 8); z->extra[7] = (char)(z_utim->mtime >> 16); z->extra[8] = (char)(z_utim->mtime >> 24); z->cextra = z->extra; z->cext = z->ext = (EB_HEADSIZE+EB_UT_LEN(1)); return ZE_OK; #else /* !USE_EF_UT_TIME */ return (int)(z-z); #endif /* ?USE_EF_UT_TIME */ } int deletedir(d) char *d; /* directory to delete */ /* Delete the directory *d if it is empty, do nothing otherwise. Return the result of rmdir(), delete(), or system(). For VMS, d must be in format [x.y]z.dir;1 (not [x.y.z]). */ { return rmdir(d); } #endif /* !UTIL */ /******************************/ /* Function version_local() */ /******************************/ /* NOTE: the following include depends upon the environment * variable $Workbench to be set correctly. (Set by * default, by Version command in Startup-sequence.) */ int WBversion = (int) #include "ENV:Workbench" ; void version_local() { static ZCONST char CompiledWith[] = "Compiled with %s%s under %s%s%s%s.\n\n"; /* Define buffers. */ char buf1[16]; /* compiler name */ char buf2[16]; /* revstamp */ char buf3[16]; /* OS */ char buf4[16]; /* Date */ /* char buf5[16]; /* Time */ /* format "with" name strings */ #ifdef AMIGA # ifdef __SASC strcpy(buf1,"SAS/C "); # else # ifdef LATTICE strcpy(buf1,"Lattice C "); # else # ifdef AZTEC_C strcpy(buf1,"Manx Aztec C "); # else strcpy(buf1,"UNKNOWN "); # endif # endif # endif /* "under" */ sprintf(buf3,"AmigaDOS v%d",WBversion); #else strcpy(buf1,"Unknown compiler "); strcpy(buf3,"Unknown OS"); #endif /* Define revision, date, and time strings. * NOTE: Do not calculate run time, be sure to use time compiled. * Pass these strings via your makefile if undefined. */ #if defined(__VERSION__) && defined(__REVISION__) sprintf(buf2,"version %d.%d",__VERSION__,__REVISION__); #else # ifdef __VERSION__ sprintf(buf2,"version %d",__VERSION__); # else sprintf(buf2,"unknown version"); # endif #endif #ifdef __DATE__ sprintf(buf4," on %s",__DATE__); #else strcpy(buf4," unknown date"); #endif /****** #ifdef __TIME__ sprintf(buf5," at %s",__TIME__); #else strcpy(buf5," unknown time"); #endif ******/ /* Print strings using "CompiledWith" mask defined above. * ("Compiled with %s%s under %s%s%s%s.") */ printf(CompiledWith, buf1, buf2, buf3, buf4, /* buf5, */ "", "" ); /* buf6 not used */ } /* end function version_local() */ zip30/amiga/crc_68.a0100644000076400000060000001027607076030442012275 0ustar edisk;=========================================================================== ; Copyright (c) 1990-2000 Info-ZIP. All rights reserved. ; ; See the accompanying file LICENSE, version 2000-Apr-09 or later ; (the contents of which are also included in zip.h) for terms of use. ; If, for some reason, all these files are missing, the Info-ZIP license ; also may be found at: ftp://ftp.info-zip.org/pub/infozip/license.html ;=========================================================================== ; crc_68 created by Paul Kienitz, last modified 04 Jan 96. ; ; Return an updated 32 bit CRC value, given the old value and a block of data. ; The CRC table used to compute the value is gotten by calling get_crc_table(). ; This replaces the older updcrc() function used in Zip and fUnZip. The ; prototype of the function is: ; ; ulg crc32(ulg crcval, uch *text, extent textlen); ; ; On the Amiga, type extent is always unsigned long, not unsigned int, because ; int can be short or long at whim, but size_t is long. ; ; If using this source on a non-Amiga 680x0 system, note that we treat ; a0/a1/d0/d1 as scratch registers not preserved across function calls. ; We do not bother to support registerized arguments for crc32() -- the ; textlen parm is usually large enough so that savings outside the loop ; are pointless. ; ; Define NO_UNROLLED_LOOPS to use a simple short loop which might be more ; efficient on certain machines with dinky instruction caches ('020?), or for ; processing short strings. If loops are unrolled, the textlen parm must be ; less than 512K; if not unrolled, it must be less than 64K. xdef _crc32 ; (ulg val, uch *buf, extent bufsize) DO_CRC0 MACRO moveq #0,ltemp move.b (textbuf)+,ltemp eor.b crcval,ltemp lsl.w #2,ltemp move.l (crc_table,ltemp.w),ltemp lsr.l #8,crcval eor.l ltemp,crcval ENDM machine mc68020 DO_CRC2 MACRO move.b (textbuf)+,btemp eor.b crcval,btemp lsr.l #8,crcval move.l (crc_table,btemp.w*4),ltemp eor.l ltemp,crcval ENDM crc_table equr a0 array of unsigned long crcval equr d0 unsigned long initial value textbuf equr a1 array of unsigned char textbufsize equr d1 unsigned long (count of bytes in textbuf) btemp equr d2 ltemp equr d3 xref _get_crc_table ; ulg *get_crc_table(void) NOLIST INCLUDE 'exec/execbase.i' LIST xref _SysBase ; struct ExecBase * _crc32: move.l 8(sp),d0 bne.s valid moveq #0,d0 rts valid: movem.l btemp/ltemp,-(sp) jsr _get_crc_table move.l d0,ltemp move.l 12(sp),crcval move.l 16(sp),textbuf move.l 20(sp),textbufsize not.l crcval move.l _SysBase,crc_table move.w AttnFlags(crc_table),btemp move.l ltemp,crc_table btst #AFB_68020,btemp bne twenty IFD NO_UNROLLED_LOOPS bra.s decr loop: DO_CRC0 decr: dbra textbufsize,loop bra.s done twenty: moveq #0,btemp bra.s decr2 loop2: DO_CRC2 decr2: dbra textbufsize,loop2 ELSE ; !NO_UNROLLED_LOOPS move.l textbufsize,btemp lsr.l #3,textbufsize bra decr8 loop8: DO_CRC0 DO_CRC0 DO_CRC0 DO_CRC0 DO_CRC0 DO_CRC0 DO_CRC0 DO_CRC0 decr8: dbra textbufsize,loop8 and.w #7,btemp bra.s decr1 loop1: DO_CRC0 decr1: dbra btemp,loop1 bra done twenty: moveq #0,btemp move.l textbufsize,-(sp) lsr.l #3,textbufsize bra decr82 loop82: DO_CRC2 DO_CRC2 DO_CRC2 DO_CRC2 DO_CRC2 DO_CRC2 DO_CRC2 DO_CRC2 decr82: dbra textbufsize,loop82 move.l (sp)+,textbufsize and.w #7,textbufsize bra.s decr12 loop12: DO_CRC2 decr12: dbra textbufsize,loop12 ENDC ; ?NO_UNROLLED_LOOPS done: movem.l (sp)+,btemp/ltemp not.l crcval ;;;;; move.l crcval,d0 ; crcval already is d0 rts zip30/amiga/deflate.a0100644000076400000060000010524107011110352012576 0ustar edisk;=========================================================================== ; Copyright (c) 1990-1999 Info-ZIP. All rights reserved. ; ; See the accompanying file LICENSE, version 1999-Oct-05 or later ; (the contents of which are also included in zip.h) for terms of use. ; If, for some reason, both of these files are missing, the Info-ZIP license ; also may be found at: ftp://ftp.cdrom.com/pub/infozip/license.html ;=========================================================================== ; This is a 680x0 assembly language translation of the Info-ZIP source file ; deflate.c, by Paul Kienitz. The function longest_match is based in part ; on match.a by Carsten Steger, which in turn is partly based on match.s ; for 386 by Jean-loup Gailly and Kai Uwe Rommel. Mostly, however, this ; material is based on deflate.c, by Gailly, Rommel, and Igor Mandrichenko. ; This code is not commented very much; see deflate.c for comments that explain ; what the functions are doing. ; ; The symbols that can be used to select different versions are as follows: ; ; CPU020 if defined, use 68020 instructions always. ; ; CPUTEST if defined, check at runtime for CPU type. Another symbol ; specifying the platform-specific test must be used with this. ; If neither of these is defined, use 68000 instructions only. ; Runtime test is nonportable; it is different for each OS. ; ; AMIGA use Amiga-specific test for 68020, if CPUTEST defined. Also ; tells it that registers d0/a0/d1/a1 are not preserved by ; function calls. At present, if AMIGA is not defined, it ; causes functions to preserve all registers. ALL OF THIS CODE ; CURRENTLY ASSUMES THAT REGISTERS D2-D7/A2-A6 WILL BE PRESERVED ; BY ANY FUNCTIONS THAT IT CALLS. ; ; DYN_ALLOC should be defined here if it is defined for C source; tells us ; that big arrays are allocated instead of static. ; ; WSIZE must be defined as the same number used for WSIZE in the C ; source, and must be a power of two <= 32768. As elsewhere, ; the default value is 32768. ; ; INT16 define this if ints are 16 bits; otherwise 32 bit ints assumed. ; ; SMALL_MEM define this if it is defined in the C source; otherwise it uses ; the MEDIUM_MEM model. BIG_MEM and MMAP are *not* supported. ; The FULL_SEARCH option in deflate.c is also not supported. ; ; DEBUG activates some tracing output, as in the C source. ; ; QUADLONG this selects a different version of the innermost longest_match ; loop code for 68020 operations, comparing bytes four at a time ; instead of two at a time. It seems to be a tiny bit faster on ; average, but it's slower often enough that one can't generalize. ; ; This code currently assumes that function results are returned in D0 for ; all platforms. It assumes that args to functions are pushed onto the stack, ; last arg first. It also currently assumes that all C symbols have an ; underscore prepended when referenced from assembly. IFND CPU020 IFND CPUTEST CPU000 equ 1 ENDC ENDC ; Use these macros for accessing variables of type int: IFD INT16 MOVINT MACRO move.w \1,\2 ENDM CLRINT MACRO clr.w \1 ENDM INTSIZE equ 2 ELSE ; !INT16 MOVINT MACRO move.l \1,\2 ENDM CLRINT MACRO clr.l \1 ENDM INTSIZE equ 4 ENDC IFD DYN_ALLOC BASEPTR MACRO move.l \1,\2 ENDM ELSE BASEPTR MACRO lea \1,\2 ENDM ENDC ; constants we use, many of them adjustable: MAX_MATCH equ 258 MIN_MATCH equ 3 TOO_FAR equ 4096 IFND WSIZE WSIZE equ 32768 ENDC WMASK equ WSIZE-1 MAX_DIST equ WSIZE-MAX_MATCH-MIN_MATCH-1 MIN_LOOKAHEAD equ MAX_MATCH+MIN_MATCH+1 ; IFD BIG_MEM ; NOT supported -- type Pos needs to be 32 bits ;HASH_BITS equ 15 ; ELSE IFD SMALL_MEM HASH_BITS equ 13 ELSE HASH_BITS equ 14 ; default -- MEDIUM_MEM ENDC ; ENDC ; BIG_MEM HASH_SIZE equ 1< MOVINT Strst,_strstart ; ct_tally reads this variable moveq #0,d0 move.b -1(Window,Strst.l),d0 MOVINT d0,-(sp) CLRINT -(sp) jsr _ct_tally addq #2*INTSIZE,sp tst.w d0 beq.s skipliteral FLUSH_B #0 move.l Strst,_block_start skipliteral: addq.w #1,Strst subq.w #1,Look refill: cmp.w #MIN_LOOKAHEAD,Look bhs look_loop bsr fill_window bra look_loop last_tally: tst.w Avail beq last_flush MOVINT Strst,_strstart ; ct_tally reads this variable moveq #0,d0 move.b -1(Window,Strst.l),d0 MOVINT d0,-(sp) CLRINT -(sp) jsr _ct_tally addq #2*INTSIZE,sp last_flush: FLUSH_B #1 bra deflate_exit ; ================== This is another version used for low compression levels: deflate_fast: moveq #0,MatchL moveq #MIN_MATCH-1,PrevL flook_loop: tst.w Look beq flast_flush IN_STR a0,d0 tst.w Head beq.s fno_new_match move.w Strst,d0 sub.w Head,d0 cmp.w #MAX_DIST,d0 bhi.s fno_new_match move.w PrevL,prev_length ; longest_match reads these variables MOVINT Strst,_strstart MOVINT Head,d0 ; parm for longest_match bsr longest_match ; sets match_start cmp.w Look,d0 ; does length exceed valid data? bls.s fstml move.w Look,d0 fstml: move.w d0,MatchL ; valid length of match fno_new_match: cmp.w #MIN_MATCH,MatchL blo fliteral ; CHECK_MATCH Strst,match_start,MatchL MOVINT Strst,_strstart ; ct_tally reads this variable move.l MatchL,d0 subq.w #MIN_MATCH,d0 MOVINT d0,-(sp) move.l Strst,d0 sub.w match_start,d0 MOVINT d0,-(sp) jsr _ct_tally ; sets d0 true if we have to flush addq #2*INTSIZE,sp sub.w MatchL,Look cmp.w max_lazy_match,MatchL bhi ftoolong subq.w #2,MatchL finsertmatch: addq.w #1,Strst IN_STR a0,d1 ; preserve d0 dbra MatchL,finsertmatch moveq #0,MatchL ; not needed? addq.w #1,Strst bra.s flushfill ftoolong: add.w MatchL,Strst moveq #0,MatchL moveq #0,d1 ; preserve d0 move.b (Window,Strst.l),d1 move.w d1,ins_h ; My assembler objects to passing <1(Window,Strst.l)> directly to UP_HASH... move.b 1(Window,Strst.l),Avail ; Avail is not used in deflate_fast UP_HASH d1,Avail ; preserve d0 IFNE MIN_MATCH-3 FAIL needs to UP_HASH another MIN_MATCH-3 times, but with what arg? ENDC bra.s flushfill fliteral: TRACE_C <(Window,Strst.l)> MOVINT Strst,_strstart ; ct_tally reads this variable moveq #0,d0 move.b (Window,Strst.l),d0 MOVINT d0,-(sp) CLRINT -(sp) jsr _ct_tally ; d0 set if we need to flush addq #2*INTSIZE,sp addq.w #1,Strst subq.w #1,Look flushfill: tst.w d0 beq.s frefill FLUSH_B #0 move.l Strst,_block_start frefill: cmp.w #MIN_LOOKAHEAD,Look bhs flook_loop bsr fill_window bra flook_loop flast_flush: FLUSH_B #1 ; sets our return value deflate_exit: MOVINT Strst,_strstart ; save back cached values move.w PrevL,prev_length move.w Look,lookahead movem.l (sp)+,DEFREGS rts ; ========================================================================= ; void fill_window(void) calls the input function to refill the sliding ; window that we use to find substring matches in. More equr Head ; local variable in fill_window WindTop equr Prev ; local variable used for sliding SlidIx equr PrevL ; local variable used for sliding IFD AMIGA FWREGS reg d2-d5/a2-a6 ; does NOT include Look and Strst ELSE FWREGS reg d1-d5/a0-a6 ; likewise ENDC ; all registers available to be clobbered by the sliding operation: ; we exclude More, WindTop, SlidIx, Look, Strst, Window, a4 and a7. SPAREGS reg d0-d3/a0-a1/a5-a6 SPCOUNT equ 8 ; number of registers in SPAREGS _fill_window: ; C-callable entry point movem.l Strst/Look,-(sp) IFD INT16 moveq #0,Strst ; Strst must be valid as a long ENDC MOVINT _strstart,Strst move.w lookahead,Look BASEPTR _window,Window bsr.s fill_window MOVINT Strst,_strstart move.w Look,lookahead movem.l (sp)+,Strst/Look rts ; strstart, lookahead, and window must be cached in Strst, Look, and Window: fill_window: ; asm-callable entry point movem.l FWREGS,-(sp) tst.w eofile ; we put this up here for speed bne fwdone and.l #$FFFF,Look ; make sure Look is valid as long fw_refill: move.l _window_size,More ; <= 64K sub.l Look,More sub.l Strst,More ; Strst is already valid as long cmp.w #EOF,More bne.s notboundary subq.w #1,More bra checkend notboundary: tst.w sliding beq checkend cmp.w #WSIZE+MAX_DIST,Strst blo checkend IFGT 32768-WSIZE lea WSIZE(Window),WindTop ; WindTop is aligned when Window is ELSE move.l Window,WindTop add.l #WSIZE,WindTop ENDC move.l Window,d0 and.w #3,d0 beq.s isaligned subq.w #1,d0 align: move.b (WindTop)+,(Window)+ ; copy up to a longword boundary dbra d0,align isaligned: ; This is faster than a simple move.l (WindTop)+,(Window)+ / dbra loop: move.w #(WSIZE-1)/(4*SPCOUNT),SlidIx slide: movem.l (WindTop)+,SPAREGS ; copy, 32 bytes at a time! movem.l SPAREGS,(Window) ; a slight overshoot doesn't matter. lea 4*SPCOUNT(Window),Window ; can't use (aN)+ as movem.l dest dbra SlidIx,slide BASEPTR _window,Window ; restore cached value sub.w #WSIZE,match_start sub.w #WSIZE,Strst sub.l #WSIZE,_block_start add.w #WSIZE,More BASEPTR _head,a0 move.w #HASH_SIZE-1,d0 fixhead: move.w (a0),d1 sub.w #WSIZE,d1 bpl.s headok moveq #0,d1 headok: move.w d1,(a0)+ dbra d0,fixhead BASEPTR _prev,a0 move.w #WSIZE-1,d0 fixprev: move.w (a0),d1 sub.w #WSIZE,d1 bpl.s prevok moveq #0,d1 prevok: move.w d1,(a0)+ dbra d0,fixprev TRACE_C #'.' checkend: ; assert eofile is false MOVINT More,-(sp) ; assert More's upper word is zero move.l Strst,d0 add.w Look,d0 add.l Window,d0 move.l d0,-(sp) move.l _read_buf,a0 jsr (a0) ; refill the upper part of the window addq #4+INTSIZE,sp tst.w d0 beq.s iseof cmp.w #EOF,d0 beq.s iseof add.w d0,Look cmp.w #MIN_LOOKAHEAD,Look blo fw_refill ; eofile is still false bra.s fwdone iseof: move.w #1,eofile fwdone: movem.l (sp)+,FWREGS rts ; ========================================================================= ; void lm_free(void) frees dynamic arrays in the DYN_ALLOC version. xdef _lm_free ; the entry point _lm_free: IFD DYN_ALLOC move.l _window,d0 beq.s lf_no_window move.l d0,-(sp) jsr _free addq #4,sp clr.l _window lf_no_window: move.l _prev,d0 beq.s lf_no_prev move.l d0,-(sp) jsr _free move.l _head,(sp) ; reuse the same stack arg slot jsr _free addq #4,sp clr.l _prev clr.l _head lf_no_prev: ENDC rts ; ============================================================================ ; void lm_init(int pack_level, unsigned short *flags) allocates dynamic arrays ; if any, and initializes all variables so that deflate() is ready to go. xdef _lm_init ; the entry point Level equr d2 ;Window equr a2 ; as in deflate() IFD AMIGA INIREGS reg d2/a2 ELSE INIREGS reg d0-d2/a0-a1 ENDC _lm_init: MOVINT 4(sp),d0 move.l 4+INTSIZE(sp),a0 movem.l INIREGS,-(sp) move.w d0,Level cmp.w #1,Level blt.s levelerr bgt.s try9 bset.b #B_FAST,1(a0) try9: cmp.w #9,Level bgt.s levelerr blt.s levelok bset.b #B_SLOW,1(a0) bra.s levelok levelerr: pea level_message jsr _error ; never returns levelok: clr.w sliding tst.l _window_size bne.s gotawindowsize move.w #1,sliding move.l #2*WSIZE,_window_size gotawindowsize: BASEPTR _window,Window IFD DYN_ALLOC move.l Window,d0 ; fake tst.l bne.s gotsomewind CAL_SH WSIZE move.l d0,Window move.l d0,_window bne.s gotsomewind pea window_message MOVINT #ZE_MEM,-(sp) jsr _ziperr ; never returns gotsomewind: tst.l _prev bne.s gotsomehead CAL_SH WSIZE move.l d0,_prev beq.s nohead CAL_SH HASH_SIZE move.l d0,_head bne.s gotfreshhead ; newly calloc'd memory is zeroed nohead: pea hash_message MOVINT #ZE_MEM,-(sp) jsr _ziperr ; never returns gotsomehead: ENDC ; DYN_ALLOC move.w #(HASH_SIZE/2)-1,d0 ; two shortwords per loop BASEPTR _head,a0 wipeh: clr.l (a0)+ dbra d0,wipeh gotfreshhead: move.l Level,d0 IFEQ Sizeof_config-8 asl.l #3,d0 ELSE mulu #Sizeof_config,d0 ENDC lea config_table,a0 add.l d0,a0 move.w Max_lazy(a0),max_lazy_match move.w Good_length(a0),good_match move.w Nice_length(a0),nice_match move.w Max_chain(a0),max_chain_len CLRINT _strstart clr.l _block_start bsr match_init clr.w eofile MOVINT #WSIZE,-(sp) ; We read only 32K because lookahead is short move.l Window,-(sp) ; even when int size is long, as if deflate.c move.l _read_buf,a0 ; were compiled with MAXSEG_64K defined. jsr (a0) addq #4+INTSIZE,sp move.w d0,lookahead beq.s noread cmp.w #EOF,d0 bne.s irefill noread: move.w #1,eofile clr.w lookahead bra.s init_done irefill: move.w lookahead,d0 cmp.w #MIN_LOOKAHEAD,d0 bhs.s hashify bsr _fill_window ; use the C-callable version hashify: clr.w ins_h moveq #MIN_MATCH-2,d0 hash1: move.b (Window)+,d1 UP_HASH Level,d1 dbra d0,hash1 init_done: movem.l (sp)+,INIREGS rts ; strings for error messages: hash_message dc.b 'hash table allocation',0 window_message dc.b 'window allocation',0 level_message dc.b 'bad pack level',0 end zip30/amiga/filedate.c0100644000076400000060000005461510154331630012767 0ustar edisk/* Copyright (c) 1990-2002 Info-ZIP. All rights reserved. See the accompanying file LICENSE, version 2000-Apr-09 or later (the contents of which are also included in zip.h) for terms of use. If, for some reason, all these files are missing, the Info-ZIP license also may be found at: ftp://ftp.info-zip.org/pub/infozip/license.html */ /* Low-level Amiga routines shared between Zip and UnZip. * * Contains: FileDate() * getenv() [replaces inadequate standard library version] * setenv() [SAS/C only, replaces standard library version] * set_TZ() [SAS/C only] * GetPlatformLocalTimezone() [callback from timezone.c tzset()] * time() * sendpkt() * Agetch() * * The first five are used by most Info-ZIP programs except fUnZip. * The last two are used by all except the non-CRYPT version of fUnZip. * Probably some of the stuff in here is unused by ZipNote and ZipSplit too... * sendpkt() is used by Agetch() and FileDate(), and by screensize() in * amiga/amiga.c (UnZip); time() is used only by Zip. */ /* HISTORY/CHANGES * 2 Sep 92, Greg Roelofs, Original coding. * 6 Sep 92, John Bush, Incorporated into UnZip 5.1 * 6 Sep 92, John Bush, Interlude "FileDate()" defined, which calls or * redefines SetFileDate() depending upon AMIGADOS2 definition. * 11 Oct 92, John Bush, Eliminated AMIGADOS2 switch by determining * revision via OpenLibrary() call. Now only one version of * the program runs on both platforms (1.3.x vs. 2.x) * 11 Oct 92, John Bush, Merged with Zip version and changed arg passing * to take time_t input instead of struct DateStamp. * Arg passing made to conform with utime(). * 22 Nov 92, Paul Kienitz, fixed includes for Aztec and cleaned up some * lint-ish errors; simplified test for AmigaDOS version. * 11 Nov 95, Paul Kienitz, added Agetch() for crypt password input and * UnZip's "More" prompt -- simplifies crypt.h and avoids * use of library code redundant with sendpkt(). Made it * available to fUnZip, which does not use FileDate(). * 22 Nov 95, Paul Kienitz, created a new tzset() that gets the current * timezone from the Locale preferences. These exist only under * AmigaDOS 2.1 and up, but it is probably correctly set on more * Amigas than the TZ environment variable is. We check that * only if TZ is not validly set. We do not parse daylight * savings syntax except to check for presence vs. absence of a * DST part; United States rules are assumed. This is better * than the tzset()s in the Amiga compilers' libraries do. * 15 Jan 96, Chr. Spieler, corrected the logic when to select low level * sendpkt() (when FileDate(), Agetch() or windowheight() is used), * and AMIGA's Agetch() (CRYPT, and UnZip(SFX)'s UzpMorePause()). * 10 Feb 96, Paul Kienitz, re-fiddled that selection logic again, moved * stuff around for clarity. * 16 Mar 96, Paul Kienitz, created a replacement localtime() to go with the * new tzset(), because Aztec's is hopelessly broken. Also * gmtime(), which localtime() calls. * 12 Apr 96, Paul Kienitz, daylight savings was being handled incorrectly. * 21 Apr 96, Paul Kienitz, had to replace time() as well, Aztec's returns * local time instead of GMT. That's why their localtime() was bad, * because it assumed time_t was already local, and gmtime() was * the one that checked TZ. * 23 Apr 96, Chr. Spieler, deactivated time() replacement for UnZip stuff. * Currently, the UnZip sources do not make use of time() (and do * not supply the working mktime() replacement, either!). * 29 Apr 96, Paul Kienitz, created a replacement getenv() out of code that * was previously embedded in tzset(), for reliable global test * of whether TZ is set or not. * 19 Jun 96, Haidinger Walter, re-adapted for current SAS/C compiler. * 7 Jul 96, Paul Kienitz, smoothed together compiler-related changes. * 4 Feb 97, Haidinger Walter, added set_TZ() for SAS/C. * 23 Apr 97, Paul Kienitz, corrected Unix->Amiga DST error by adding * mkgmtime() so localtime() could be used. * 28 Apr 97, Christian Spieler, deactivated mkgmtime() definition for ZIP; * the Zip sources supply this function as part of util.c. * 24 May 97, Haidinger Walter, added time_lib support for SAS/C and moved * set_TZ() to time_lib.c. * 12 Jul 97, Paul Kienitz, adapted time_lib stuff for Aztec. * 26 Jul 97, Chr. Spieler, old mkgmtime() fixed (ydays[] def, sign vs unsign). * 30 Dec 97, Haidinger Walter, adaptation for SAS/C using z-stat.h functions. * 19 Feb 98, Haidinger Walter, removed alloc_remember, more SAS.C fixes. * 23 Apr 98, Chr. Spieler, removed mkgmtime(), changed FileDate to convert to * Amiga file-time directly. * 24 Apr 98, Paul Kienitz, clip Unix dates earlier than 1978 in FileDate(). * 02 Sep 98, Paul Kienitz, C. Spieler, always include zip.h to get a defined * header inclusion sequence that resolves all header dependencies. * 06 Jun 00, Paul Kienitz, removed time_lib.c due to its incompatible license, * moved set_TZ() back here, replaced minimal tzset() and localtime() * with new versions derived from GNU glibc source. Gave locale_TZ() * reasonable European defaults for daylight savings. * 17 Jun 00, Paul Kienitz, threw out GNU code because of objections to the GPL * virus, replaced with similar functions based on the public domain * timezone code at ftp://elsie.nci.nih.gov/pub. As with the GNU * stuff, support for timezone files and leap seconds was removed. * 23 Aug 00, Paul Kienitz, moved timezone code out from here into separate * platform-independent module 'timezone.c'. * 31 Dec 00, Christian Spieler, moved system-specific timezone help funcions * back in here, from 'timezone.c'. * 07 Jan 01, Paul Kienitz, Chr. Spieler, added missing #include "timezone.h" * and "symbolic" preprocessor constants for time calculations. * 15 Jan 02, Paul Kienitz, excluded all time handling code from compilation * for Zip utilities (when "defined(UTIL)") */ #ifndef __amiga_filedate_c #define __amiga_filedate_c #include "zip.h" #include #include #include #include #include #include #ifdef AZTEC_C # include # include # include # include # include # include # include # include # define ESRCH ENOENT # define EOSERR EIO #endif #ifdef __SASC # include # if (defined(_M68020) && (!defined(__USE_SYSBASE))) /* on 68020 or higher processors it is faster */ # define __USE_SYSBASE /* to use the pragma libcall instead of syscall */ # endif /* to access functions of the exec.library */ # include /* see SAS/C manual:part 2,chapter 2,pages 6-7 */ # include # include # ifdef DEBUG # include # endif # ifdef MWDEBUG # include /* include both before memwatch.h again just */ # include /* to be safe */ # include "memwatch.h" # endif /* MWDEBUG */ #endif /* __SASC */ #include "crypt.h" /* just so we can tell if CRYPT is supported */ #if (!defined(FUNZIP) && !defined(UTIL)) #include "timezone.h" /* for AMIGA-specific timezone callbacks */ #ifndef SUCCESS # define SUCCESS (-1L) # define FAILURE 0L #endif #define ReqVers 36L /* required library version for SetFileDate() */ #define ENVSIZE 100 /* max space allowed for an environment var */ extern struct ExecBase *SysBase; #ifndef min # define min(a, b) ((a) < (b) ? (a) : (b)) # define max(a, b) ((a) < (b) ? (b) : (a)) #endif #if defined(ZIP) || defined(HAVE_MKTIME) static const unsigned short ydays[] = { 0, 31, 59, 90, 120, 151, 181, 212, 243, 273, 304, 334, 365 }; #else extern const unsigned short ydays[]; /* in unzip's fileio.c */ #endif #define LEAP(y) (((y) % 4 == 0 && (y) % 100 != 0) || (y) % 400 == 0) #define YDAYS(m, y) (ydays[m] + (m > 1 && LEAP(y))) /* Number of leap years from 1978 to `y' (not including `y' itself). */ #define ANLEAP(y) (((y) - 1977) / 4 - ((y) - 1901) / 100 + ((y) - 1601) / 400) #define SECSPERMIN 60 #define MINSPERHOUR 60 #define SECSPERHOUR (SECSPERMIN * MINSPERHOUR) #define SECSPERDAY 86400L /* prototypes */ char *getenv(const char *var); #ifdef __SASC /* XXX !! We have really got to find a way to operate without these. */ int setenv(const char *var, const char *value, int overwrite); void set_TZ(long time_zone, int day_light); #endif LONG FileDate(char *filename, time_t u[]); LONG sendpkt(struct MsgPort *pid, LONG action, LONG *args, LONG nargs); int Agetch(void); /* =============================================================== */ /***********************/ /* Function filedate() */ /***********************/ /* FileDate() (originally utime.c), by Paul Wells. Modified by John Bush * and others (see also sendpkt() comments, below); NewtWare SetFileDate() * clone cheaply ripped off from utime(). */ /* DESCRIPTION * This routine chooses between 2 methods to set the file date on AMIGA. * Since AmigaDOS 2.x came out, SetFileDate() was available in ROM (v.36 * and higher). Under AmigaDOS 1.3.x (less than v.36 ROM), SetFileDate() * must be accomplished by constructing a message packet and sending it * to the file system handler of the file to be stamped. * * The system's ROM version is extracted from the external system Library * base. * * NOTE: although argument passing conforms with utime(), note the * following differences: * - Return value is boolean success/failure. * - If a structure or array is passed, only the first value * is used, which *may* correspond to date accessed and not * date modified. */ LONG FileDate(filename, u) char *filename; time_t u[]; { LONG SetFileDate(UBYTE *filename, struct DateStamp *pDate); LONG sendpkt(struct MsgPort *pid, LONG action, LONG *args, LONG nargs); struct MsgPort *taskport; BPTR dirlock, lock; struct FileInfoBlock *fib; LONG pktargs[4]; UBYTE *ptr; long ret; struct DateStamp pDate; struct tm *ltm; int years; tzset(); /* Amiga file date is based on 01-Jan-1978 00:00:00 (local time): * 8 years and 2 leapdays difference from Unix time. */ ltm = localtime(&u[0]); years = ltm->tm_year + 1900; if (years < 1978) pDate.ds_Days = pDate.ds_Minute = pDate.ds_Tick = 0; else { pDate.ds_Days = (years - 1978) * 365L + (ANLEAP(years)) + YDAYS(ltm->tm_mon, years) + (ltm->tm_mday - 1); pDate.ds_Minute = ltm->tm_hour * 60 + ltm->tm_min; pDate.ds_Tick = ltm->tm_sec * TICKS_PER_SECOND; } if (SysBase->LibNode.lib_Version >= ReqVers) { return (SetFileDate(filename,&pDate)); /* native routine at 2.0+ */ } else /* !(SysBase->lib_Version >=ReqVers) */ { if( !(taskport = (struct MsgPort *)DeviceProc(filename)) ) { errno = ESRCH; /* no such process */ return FAILURE; } if( !(lock = Lock(filename,SHARED_LOCK)) ) { errno = ENOENT; /* no such file */ return FAILURE; } if( !(fib = (struct FileInfoBlock *)AllocMem( (long)sizeof(struct FileInfoBlock),MEMF_PUBLIC|MEMF_CLEAR)) ) { errno = ENOMEM; /* insufficient memory */ UnLock(lock); return FAILURE; } if( Examine(lock,fib)==FAILURE ) { errno = EOSERR; /* operating system error */ UnLock(lock); FreeMem(fib,(long)sizeof(*fib)); return FAILURE; } dirlock = ParentDir(lock); ptr = (UBYTE *)AllocMem(64L,MEMF_PUBLIC); strcpy((ptr+1),fib->fib_FileName); *ptr = strlen(fib->fib_FileName); FreeMem(fib,(long)sizeof(*fib)); UnLock(lock); /* now fill in argument array */ pktargs[0] = 0; pktargs[1] = (LONG)dirlock; pktargs[2] = (LONG)&ptr[0] >> 2; pktargs[3] = (LONG)&pDate; errno = ret = sendpkt(taskport,ACTION_SET_DATE,pktargs,4L); FreeMem(ptr,64L); UnLock(dirlock); return SUCCESS; } /* ?(SysBase->lib_Version >= ReqVers) */ } /* FileDate() */ char *getenv(const char *var) /* not reentrant! */ { static char space[ENVSIZE]; struct Process *me = (void *) FindTask(NULL); void *old_window = me->pr_WindowPtr; char *ret = NULL; me->pr_WindowPtr = (void *) -1; /* suppress any "Please insert" popups */ if (SysBase->LibNode.lib_Version >= ReqVers) { if (GetVar((char *) var, space, ENVSIZE - 1, /*GVF_GLOBAL_ONLY*/ 0) > 0) ret = space; } else { /* early AmigaDOS, get env var the crude way */ BPTR hand, foot, spine; int z = 0; if (foot = Lock("ENV:", ACCESS_READ)) { spine = CurrentDir(foot); if (hand = Open((char *) var, MODE_OLDFILE)) { z = Read(hand, space, ENVSIZE - 1); Close(hand); } UnLock(CurrentDir(spine)); } if (z > 0) { space[z] = '\0'; ret = space; } } me->pr_WindowPtr = old_window; return ret; } #ifdef __SASC int setenv(const char *var, const char *value, int overwrite) { struct Process *me = (void *) FindTask(NULL); void *old_window = me->pr_WindowPtr; int ret = -1; me->pr_WindowPtr = (void *) -1; /* suppress any "Please insert" popups */ if (SysBase->LibNode.lib_Version >= ReqVers) ret = !SetVar((char *)var, (char *)value, -1, GVF_GLOBAL_ONLY | LV_VAR); else { BPTR hand, foot, spine; long len = value ? strlen(value) : 0; if (foot = Lock("ENV:", ACCESS_READ)) { spine = CurrentDir(foot); if (len) { if (hand = Open((char *) var, MODE_NEWFILE)) { ret = Write(hand, (char *) value, len + 1) >= len; Close(hand); } } else ret = DeleteFile((char *) var); UnLock(CurrentDir(spine)); } } me->pr_WindowPtr = old_window; return ret; } /* Stores data from timezone and daylight to ENV:TZ. */ /* ENV:TZ is required to exist by some other SAS/C library functions, */ /* like stat() or fstat(). */ void set_TZ(long time_zone, int day_light) { char put_tz[MAXTIMEZONELEN]; /* string for putenv: "TZ=aaabbb:bb:bbccc" */ int offset; void *exists; /* dummy ptr to see if global envvar TZ already exists */ exists = (void *)getenv(TZ_ENVVAR); /* see if there is already an envvar TZ_ENVVAR. If not, create it */ if (exists == NULL) { /* create TZ string by pieces: */ sprintf(put_tz, "GMT%+ld", time_zone / 3600L); if (time_zone % 3600L) { offset = (int) labs(time_zone % 3600L); sprintf(put_tz + strlen(put_tz), ":%02d", offset / 60); if (offset % 60) sprintf(put_tz + strlen(put_tz), ":%02d", offset % 60); } if (day_light) strcat(put_tz,"DST"); setenv(TZ_ENVVAR, put_tz, 1); } } #endif /* __SASC */ /* set state as well as possible from settings found in locale.library */ int GetPlatformLocalTimezone(sp, fill_tzstate_from_rules) register struct state * ZCONST sp; void (*fill_tzstate_from_rules)(struct state * ZCONST sp_res, ZCONST struct rule * ZCONST start, ZCONST struct rule * ZCONST end); { struct Library *LocaleBase; struct Locale *ll; struct Process *me = (void *) FindTask(NULL); void *old_window = me->pr_WindowPtr; BPTR eh; int z, valid = FALSE; /* read timezone from locale.library if TZ envvar missing */ me->pr_WindowPtr = (void *) -1; /* suppress any "Please insert" popups */ if (LocaleBase = OpenLibrary("locale.library", 0)) { if (ll = OpenLocale(NULL)) { z = ll->loc_GMTOffset; /* in minutes */ if (z == -300) { if (eh = Lock("ENV:sys/locale.prefs", ACCESS_READ)) { UnLock(eh); valid = TRUE; } else z = 300; /* bug: locale not initialized, default bogus! */ } else valid = TRUE; if (valid) { struct rule startrule, stoprule; sp->timecnt = 0; sp->typecnt = 1; sp->charcnt = 2; sp->chars[0] = sp->chars[1] = '\0'; sp->ttis[0].tt_abbrind = 0; sp->ttis[1].tt_abbrind = 1; sp->ttis[0].tt_gmtoff = -z * MINSPERHOUR; sp->ttis[1].tt_gmtoff = -z * MINSPERHOUR + SECSPERHOUR; sp->ttis[0].tt_isdst = 0; sp->ttis[1].tt_isdst = 1; stoprule.r_type = MONTH_NTH_DAY_OF_WEEK; stoprule.r_day = 0; stoprule.r_week = 5; stoprule.r_mon = 10; stoprule.r_time = 2 * SECSPERHOUR; startrule = stoprule; startrule.r_mon = 4; startrule.r_week = 1; if (z >= -180 && z < 150) { /* At this point we make a really gratuitous assumption: */ /* if the time zone could be Europe, we use the European */ /* Union rules without checking what country we're in. */ /* The AmigaDOS locale country codes do not, at least in */ /* 2.x versions of the OS, recognize very many countries */ /* outside of Europe and North America. */ sp->typecnt = 2; startrule.r_mon = 3; /* one week earlier than US DST */ startrule.r_week = 5; } else if (z >= 150 && z <= 480 && /* no DST in alaska, hawaii */ (ll->loc_CountryCode == 0x55534100 /*"USA"*/ || ll->loc_CountryCode == 0x43414E00 /*"CAN"*/)) sp->typecnt = 2; /* We check the country code for U.S. or Canada because */ /* most of Latin America has no DST. Even in these two */ /* countries there are some exceptions... */ /* else if... Feel free to add more cases here! */ if (sp->typecnt > 1) (*fill_tzstate_from_rules)(sp, &startrule, &stoprule); } CloseLocale(ll); } CloseLibrary(LocaleBase); } me->pr_WindowPtr = old_window; return valid; } #ifdef ZIP time_t time(time_t *tp) { time_t t; struct DateStamp ds; DateStamp(&ds); t = ds.ds_Tick / TICKS_PER_SECOND + ds.ds_Minute * 60 + (ds.ds_Days + 2922) * SECSPERDAY; t = mktime(gmtime(&t)); /* gmtime leaves ds in the local timezone, mktime converts it to GMT */ if (tp) *tp = t; return t; } #endif /* ZIP */ #endif /* !FUNZIP && !UTIL */ #if CRYPT || !defined(FUNZIP) /* sendpkt.c * by A. Finkel, P. Lindsay, C. Sheppner * returns Res1 of the reply packet */ /* #include #include #include #include #include #include */ LONG sendpkt(struct MsgPort *pid, LONG action, LONG *args, LONG nargs); LONG sendpkt(pid,action,args,nargs) struct MsgPort *pid; /* process identifier (handler message port) */ LONG action, /* packet type (desired action) */ *args, /* a pointer to argument list */ nargs; /* number of arguments in list */ { struct MsgPort *replyport, *CreatePort(UBYTE *, long); void DeletePort(struct MsgPort *); struct StandardPacket *packet; LONG count, *pargs, res1; replyport = CreatePort(NULL,0L); if( !replyport ) return(0); packet = (struct StandardPacket *)AllocMem( (long)sizeof(struct StandardPacket),MEMF_PUBLIC|MEMF_CLEAR); if( !packet ) { DeletePort(replyport); return(0); } packet->sp_Msg.mn_Node.ln_Name = (char *)&(packet->sp_Pkt); packet->sp_Pkt.dp_Link = &(packet->sp_Msg); packet->sp_Pkt.dp_Port = replyport; packet->sp_Pkt.dp_Type = action; /* copy the args into the packet */ pargs = &(packet->sp_Pkt.dp_Arg1); /* address of 1st argument */ for( count=0; countsp_Pkt.dp_Res1; FreeMem((char *)packet,(long)sizeof(*packet)); DeletePort(replyport); return(res1); } /* sendpkt() */ #endif /* CRYPT || !FUNZIP */ #if CRYPT || (defined(UNZIP) && !defined(FUNZIP)) /* Agetch() reads one raw keystroke -- uses sendpkt() */ int Agetch(void) { LONG sendpkt(struct MsgPort *pid, LONG action, LONG *args, LONG nargs); struct Task *me = FindTask(NULL); struct CommandLineInterface *cli = BADDR(((struct Process *) me)->pr_CLI); BPTR fh = cli->cli_StandardInput; /* this is immune to < redirection */ void *conp = ((struct FileHandle *) BADDR(fh))->fh_Type; char longspace[8]; long *flag = (long *) ((ULONG) &longspace[4] & ~3); /* LONGWORD ALIGNED! */ UBYTE c; *flag = 1; sendpkt(conp, ACTION_SCREEN_MODE, flag, 1); /* assume success */ Read(fh, &c, 1); *flag = 0; sendpkt(conp, ACTION_SCREEN_MODE, flag, 1); if (c == 3) /* ^C in input */ Signal(me, SIGBREAKF_CTRL_C); return c; } #endif /* CRYPT || (UNZIP && !FUNZIP) */ #endif /* __amiga_filedate_c*/ zip30/amiga/LMKfile0100644000076400000060000000665010550044466012260 0ustar edisk# Makefile for Zip, ZipNote, ZipCloak and ZipSplit, Amiga SAS/C 5.10b # See the master Makefile under the top level Zip/Unzip source directory # for more information on compiler macros and flags for this version. # Last update: Jan 07, 2007 # -John Bush, , ####################### # MACROBE DEFINITIONS # ####################### # Compiler and loader debug flags. Omit comments as req'd. # Do not set when building production version. # CDBG = -d3 # LDBG = ADDSYM DEFINES = -DNO_MKTEMP CC = lc OPT = -O CFLAGS = $(OPT) $(DEFINES) $(CDBG) -v -mat -cuisf -b0 -j85i86i87i100i LD = blink LDSTART = LIB:c.o LDFLAGS = LIB LIB:lc.lib+LIB:amiga.lib TMPFILE = ram:MakeZip.tmp ############################################### # BASIC COMPILE INSTRUCTIONS AND DEPENDENCIES # ############################################### # default C rules .c.o: $(CC) $(CFLAGS) -o$@ $*.c # Alternate rules for routines containing entries needed by utilities .c.oo: $(CC) $(CFLAGS) -DUTIL -o$*.oo $*.c # object file macrough lists HFILES = zip.h ziperr.h tailor.h revision.h crc32.h crypt.h ttyio.h \ amiga/amiga.h amiga/zipup.h amiga/osdep.h OBJA = zipfile.o zipup.o fileio.o util.o globals.o crc32.o crypt.o \ timezone.o ttyio.o amiga.o amigazip.o filedate.o OBJI = deflate.o trees.o OBJU = zipfile.oo fileio.oo util.oo globals.o timezone.o \ amiga.o amigazip.oo filedate.o OBJZ = zip.o $(OBJA) $(OBJI) OBJN = zipnote.o $(OBJU) OBJC = zipcloak.o $(OBJU) crc32.oo crypt.oo ttyio.o OBJS = zipsplit.o $(OBJU) ZIPS = zip zipnote zipcloak zipsplit all: Message $(ZIPS) Message: -echo " " -echo "WARNING: Lattice 5.x HAS NOT BEEN TESTED WITH THIS ZIP VERSION" -echo "Report problems to " -echo " " zip: $(OBJZ) $(HFILES) -echo "$(OBJZ)" > $(TMPFILE) $(LD) TO Zip FROM $(LDSTART) WITH $(TMPFILE) $(LDFLAGS) $(LDBG) -delete $(TMPFILE) Zip.info zipnote: $(OBJN) $(HFILES) -echo "$(OBJN)" > $(TMPFILE) $(LD) TO ZipNote FROM $(LDSTART) WITH $(TMPFILE) $(LDFLAGS) $(LDBG) -delete $(TMPFILE) ZipNote.info zipcloak: $(OBJC) $(HFILES) -echo "$(OBJC)" > $(TMPFILE) $(LD) TO ZipCloak FROM $(LDSTART) WITH $(TMPFILE) $(LDFLAGS) $(LDBG) -delete $(TMPFILE) ZipCloak.info zipsplit: $(OBJS) $(HFILES) -echo "$(OBJS)" > $(TMPFILE) $(LD) TO ZipSplit FROM $(LDSTART) WITH $(TMPFILE) $(LDFLAGS) $(LDBG) -delete $(TMPFILE) ZipSplit.info clean: -delete $(OBJZ) all quiet force >nil: -delete $(OBJU) all quiet force >nil: -delete $(OBJA) all quiet force >nil: -delete $(OBJI) all quiet force >nil: -delete $(OBJN) all quiet force >nil: -delete $(OBJC) all quiet force >nil: -delete $(OBJS) all quiet force >nil: zip.o: zip.c $(HFILES) zipnote.o: zipnote.c $(HFILES) zipcloak.o: zipcloak.c $(HFILES) crypt.o: crypt.c $(HFILES) ttyio.o: ttyio.c $(HFILES) zipsplit.o: zipsplit.c $(HFILES) deflate.o: deflate.c $(HFILES) trees.o: trees.c $(HFILES) zipfile.o: zipfile.c $(HFILES) zipup.o: zipup.c $(HFILES) fileio.o: fileio.c $(HFILES) util.o: util.c $(HFILES) timezone.o: timezone.c $(HFILES) timezone.h crc32.o: crc32.c $(HFILES) crctab.o: crctab.c $(HFILES) globals.o: globals.c $(HFILES) # Amiga specific objects amiga.o: amiga/amiga.c $(HFILES) amigazip.o: amiga/amigazip.c $(HFILES) # end of Makefile zip30/amiga/makefile.azt0100644000076400000060000002133710550050502013332 0ustar edisk# Makefile for Zip, ZipNote, ZipCloak, ZipSplit for Aztec C 5.2 # Also ZipLM, a version of Zip that needs much less free memory # -- Paul Kienitz, last updated 07 Jan 2007 # Make sure platform is defined correctly, and select memory usage options: DEFINES = -d AMIGA -d DYN_ALLOC -d ASM_CRC CC = cc AS = as LD = ln LDLIBS = -lc16 # -------- RELEASE VERSION: CFLAGS = -psb0e -sabfmnpu -wcr0u $(DEFINES) # -pbs means unsigned chars and short ints, -sabfmnpu is various small # optimizations, -wcr0u adjusts type checking strictness ASOPTS = -n -eAMIGA -eDYN_ALLOC -eCPUTEST -eINT16 LDFLAGS = -m +q # -------- DEBUG VERSION: CFLAGD = -bs -psb0e -s0f0n -wcr0u $(DEFINES) # -bs is include source debugging info, -s0f0n is avoid hard-to-debug # optimizations LDFLAGD = -m +q -g -w # -------- MINIMUM MEMORY USAGE RELEASE VERSION: WSIZ = WSIZE=4096 LOWFLAGS = $(CFLAGS) -d $(WSIZ) -d SMALL_MEM LOWASOPTS = $(ASOPTS) -e$(WSIZ) -eSMALL_MEM # Options used for assembling amiga/deflate.a; must generally match the # settings in DEFINES. # -------- MINIMUM MEMORY USAGE DEBUG VERSION: LOWFLAGD = $(CFLAGD) -d $(WSIZ) -d SMALL_MEM # the directory where we stick all the object files: O = obA/ # default C rules .c.o : $(CC) $(CFLAGS) -o $@ $*.c # rules for routines containing entries needed by utilities .c.oo : $(CC) $(CFLAGS) -d UTIL -o $@ $*.c # rules for the low-memory version: .c.ol : $(CC) $(LOWFLAGS) -o $@ $*.c # default C rules for debugging .c.od : $(CC) $(CFLAGD) -o $@ $*.c # debugging rules for routines containing entries needed by utilities .c.dd : $(CC) $(CFLAGD) -d UTIL -o $@ $*.c # rules for the debugging low-memory version: .c.dl : $(CC) $(LOWFLAGD) -o $@ $*.c # object file lists ZIP_H = zip.h ziperr.h tailor.h amiga/osdep.h amiga/z-stat.h OBJZ = $(O)zip.o $(O)deflate.o \ $(O)trees.o $(O)zipfile.o $(O)zipup.o $(O)util.o $(O)timezone.o \ $(O)fileio.o $(O)globals.o $(O)crc32.o $(O)crypt.o $(O)ttyio.o \ $(O)amiga.o $(O)amigazip.o $(O)crc_68.o OBJL = $(O)zip.ol $(O)deflate.ol \ $(O)trees.ol $(O)zipfile.ol $(O)zipup.ol $(O)util.ol $(O)timezone.ol \ $(O)fileio.ol $(O)globals.ol $(O)crc32.ol $(O)crypt.ol $(O)ttyio.ol \ $(O)amiga.ol $(O)amigazip.ol $(O)crc_68.o OBJU = $(O)zipfile.oo $(O)fileio.oo \ $(O)util.oo $(O)globals.o $(O)amiga.oo $(O)amigazip.oo OBJN = $(O)zipnote.o $(OBJU) OBJC = $(O)zipcloak.o $(OBJU) $(O)crc32.oo \ $(O)crypt.oo $(O)ttyio.o OBJS = $(O)zipsplit.o $(OBJU) # These are the debuggable versions: DBJZ = $(O)zip.od $(O)deflate.od \ $(O)trees.od $(O)zipfile.od $(O)zipup.od $(O)util.od $(O)timezone.od \ $(O)fileio.od $(O)globals.od $(O)crc32.od $(O)crypt.od $(O)ttyio.od \ $(O)amiga.od $(O)amigazip.od $(O)crc_68.o DBJL = $(O)zip.dl $(O)deflate.dl \ $(O)trees.dl $(O)zipfile.dl $(O)zipup.dl $(O)util.dl $(O)timezone.dl \ $(O)fileio.dl $(O)globals.dl $(O)crc32.dl $(O)crypt.dl $(O)ttyio.dl \ $(O)amiga.dl $(O)amigazip.dl $(O)crc_68.o DBJU = $(O)zipfile.dd $(O)fileio.dd \ $(O)util.dd $(O)globals.od $(O)amiga.dd $(O)amigazip.dd DBJN = $(O)zipnote.od $(DBJU) DBJC = $(O)zipcloak.od $(DBJU) $(O)crc32.dd \ $(O)crypt.dd $(O)ttyio.od DBJS = $(O)zipsplit.od $(DBJU) # HERE WE GO: all : Zip ZipNote ZipSplit ZipCloak ZipLM z : Zip n : ZipNote s : ZipSplit c : ZipCloak l : ZipLM # Debug versions: dall : Zip.dbg ZipNote.dbg ZipSplit.dbg ZipCloak.dbg ZipLM.dbg dz : Zip.dbg dn : ZipNote.dbg ds : ZipSplit.dbg dc : ZipCloak.dbg dl : ZipLM.dbg Zip : $(OBJZ) $(ZIP_H) $(LD) $(LDFLAGS) -o $@ $(OBJZ) $(LDLIBS) -@delete Zip.dbg ZipNote : $(OBJN) $(ZIP_H) $(LD) $(LDFLAGS) -o $@ $(OBJN) $(LDLIBS) -@delete ZipNote.dbg ZipSplit : $(OBJS) $(ZIP_H) $(LD) $(LDFLAGS) -o $@ $(OBJS) $(LDLIBS) -@delete ZipSplit.dbg ZipCloak : $(OBJC) $(ZIP_H) $(LD) $(LDFLAGS) -o $@ $(OBJC) $(LDLIBS) -@delete ZipCloak.dbg ZipLM : $(OBJL) $(ZIP_H) $(LD) $(LDFLAGS) -o $@ $(OBJL) $(LDLIBS) -@delete ZipLM.dbg Zip.dbg : $(DBJZ) $(ZIP_H) $(LD) $(LDFLAGD) -o Zip $(DBJZ) $(LDLIBS) ZipNote.dbg : $(DBJN) $(ZIP_H) $(LD) $(LDFLAGD) -o ZipNote $(DBJN) $(LDLIBS) ZipSplit.dbg : $(DBJS) $(ZIP_H) $(LD) $(LDFLAGD) -o ZipSplit $(DBJS) $(LDLIBS) ZipCloak.dbg : $(DBJC) $(ZIP_H) $(LD) $(LDFLAGD) -o ZipCloak $(DBJC) $(LDLIBS) ZipLM.dbg : $(DBJL) $(ZIP_H) $(LD) $(LDFLAGD) -o ZipLM $(DBJL) $(LDLIBS) clean : bugclean -delete quiet $(OBJZ) -delete quiet $(OBJL) -delete quiet $(O)zipnote.o $(O)zipcloak.o $(O)zipsplit.o \ $(O)crypt.oo $(OBJU) bugclean : -delete quiet $(DBJZ) -delete quiet $(DBJL) -delete quiet $(O)zipnote.od $(O)zipcloak.od $(O)zipsplit.od \ $(O)crypt.dd $(DBJU) cleaner : clean -delete quiet Zip ZipNote ZipSplit ZipCloak ZipLM -delete quiet Zip.dbg ZipNote.dbg ZipSplit.dbg ZipCloak.dbg ZipLM.dbg # header dependencies: $(O)zip.o $(O)zipnote.o $(O)zipcloak.o $(O)zipsplit.o $(O)crypt.o $(O)ttyio.o \ $(O)deflate.o $(O)trees.o $(O)zipfile.o $(O)zipup.o $(O)fileio.o $(O)util.o \ $(O)timezone.o $(O)crc32.o $(O)globals.o $(O)amiga.o : $(ZIP_H) $(O)zip.ol $(O)zipnote.ol $(O)zipcloak.ol $(O)zipsplit.ol $(O)crypt.ol \ $(O)ttyio.ol $(O)deflate.ol $(O)trees.ol $(O)zipfile.ol $(O)zipup.ol \ $(O)fileio.ol $(O)util.ol $(O)timezone.ol $(O)crc32.ol $(O)globals.ol \ $(O)amiga.ol : $(ZIP_H) $(O)crc32.oo $(O)crypt.oo $(O)zipfile.oo $(O)fileio.oo $(O)util.oo : $(ZIP_H) $(O)amigazip.o $(O)amigazip.ol $(O)amigazip.oo : amiga/amiga.h $(ZIP_H) $(O)zip.o $(O)zipnote.o $(O)zipcloak.o $(O)zipsplit.o $(O)zipup.o \ $(O)zip.ol $(O)zipnote.ol $(O)zipcloak.ol $(O)zipsplit.ol \ $(O)zipup.ol : revision.h $(O)amiga.o $(O)amiga.ol : crypt.h $(O)crc32.o $(O)crc32.oo $(O)crc32.ol $(O)crypt.o $(O)crypt.oo $(O)crypt.ol \ $(O)zipcloak.o $(O)zipcloak.ol $(O)zip.o $(O)zip.ol \ $(O)zipup.o $(O)zipup.ol \ $(O)zipfile.o $(O)zipfile.oo $(O)zipfile.ol \ $(O)fileio.o $(O)fileio.oo $(O)fileio.ol : crc32.h $(O)crypt.o $(O)crypt.oo $(O)crypt.ol $(O)ttyio.o $(O)ttyio.ol \ $(O)zipcloak.o $(O)zipcloak.ol $(O)zip.o $(O)zip.ol \ $(O)zipup.o $(O)zipup.ol : crypt.h ttyio.h $(O)timezone.o $(O)timezone.ol $(O)timezone.od $(O)timezone.dl \ $(O)amiga.o $(O)amiga.ol $(O)amiga.oo : timezone.h $(O)zipup.o $(O)zipup.ol : amiga/zipup.h # SPECIAL CASES: # -mr changes expression parsing; avoids a bogus "expression too complex" error: $(O)trees.o : trees.c $(CC) $(CFLAGS) -mr -o $@ trees.c $(O)trees.ol : trees.c $(CC) $(LOWFLAGS) -mr -o $@ trees.c $(O)trees.od : trees.c $(CC) $(CFLAGD) -mr -o $@ trees.c $(O)trees.ld : trees.c $(CC) $(LOWFLAGD) -mr -o $@ trees.c # Substitute the assembly version of deflate.c: (but not in debug version) $(O)deflate.o : amiga/deflate.a $(AS) $(ASOPTS) -o $@ amiga/deflate.a $(O)deflate.ol : amiga/deflate.a $(AS) $(LOWASOPTS) -o $@ amiga/deflate.a # The assembly CRC function: $(O)crc_68.o : amiga/crc_68.a $(AS) -n -o $@ amiga/crc_68.a # Put the Amiga internal version data with today's date into amiga.c: $(O)amiga.o : amiga/amiga.c amiga/filedate.c amiga/stat.c rx > env:VersionDate "say '""'translate(date('E'), '.', '/')'""'" $(CC) $(CFLAGS) -o $@ amiga/amiga.c delete env:VersionDate $(O)amiga.ol : amiga/amiga.c amiga/filedate.c amiga/stat.c rx > env:VersionDate "say '""'translate(date('E'), '.', '/')'""'" $(CC) $(LOWFLAGS) -o $@ amiga/amiga.c delete env:VersionDate $(O)amiga.od : amiga/amiga.c amiga/filedate.c amiga/stat.c rx > env:VersionDate "say '""'translate(date('E'), '.', '/')'""'" $(CC) $(CFLAGD) -o $@ amiga/amiga.c delete env:VersionDate $(O)amiga.ld : amiga/amiga.c amiga/filedate.c amiga/stat.c rx > env:VersionDate "say '""'translate(date('E'), '.', '/')'""'" $(CC) $(LOWFLAGD) -o $@ amiga/amiga.c delete env:VersionDate $(O)amiga.oo : amiga/amiga.c amiga/filedate.c amiga/stat.c rx > env:VersionDate "say '""'translate(date('E'), '.', '/')'""'" $(CC) $(CFLAGS) -d UTIL -o $@ amiga/amiga.c delete env:VersionDate $(O)amiga.dd : amiga/amiga.c amiga/filedate.c amiga/stat.c rx > env:VersionDate "say '""'translate(date('E'), '.', '/')'""'" $(CC) $(CFLAGD) -d UTIL -o $@ amiga/amiga.c delete env:VersionDate # Put the compiler version number into amigazip.c: $(O)amigazip.o : amiga/amigazip.c $(CC) $(CFLAGS) -o $@ -d __VERSION__=5 -d __REVISION__=2 amiga/amigazip.c $(O)amigazip.ol : amiga/amigazip.c $(CC) $(LOWFLAGS) -o $@ -d __VERSION__=5 -d __REVISION__=2 amiga/amigazip.c $(O)amigazip.od : amiga/amigazip.c $(CC) $(CFLAGD) -o $@ -d __VERSION__=5 -d __REVISION__=2 amiga/amigazip.c $(O)amigazip.ld : amiga/amigazip.c $(CC) $(LOWFLAGD) -o $@ -d __VERSION__=5 -d __REVISION__=2 amiga/amigazip.c $(O)amigazip.oo : amiga/amigazip.c $(CC) $(CFLAGS) -d UTIL -o $@ -d __VERSION__=5 -d __REVISION__=2 amiga/amigazip.c $(O)amigazip.dd : amiga/amigazip.c $(CC) $(CFLAGD) -d UTIL -o $@ -d __VERSION__=5 -d __REVISION__=2 amiga/amigazip.c zip30/amiga/match.a0100644000076400000060000001171507011110370012270 0ustar edisk;=========================================================================== ; Copyright (c) 1990-1999 Info-ZIP. All rights reserved. ; ; See the accompanying file LICENSE, version 1999-Oct-05 or later ; (the contents of which are also included in zip.h) for terms of use. ; If, for some reason, both of these files are missing, the Info-ZIP license ; also may be found at: ftp://ftp.cdrom.com/pub/infozip/license.html ;=========================================================================== ; match.a -- optional optimized asm version of longest match in deflate.c ; Written by Jean-loup Gailly ; Adapted for the Amiga by Carsten Steger ; using the code in match.S. ; The major change in this code consists of removing all unaligned ; word accesses, because they cause 68000-based Amigas to crash. ; For maximum speed, UNALIGNED_OK can be defined in Makefile.sasc. ; The program will then only run on 68020-based Amigas, though. ; If you have reduced WSIZE in zip.h, then make sure this is ; assembled with an equivalent -dWSIZE=. ; ; This code will run with registerized parameters too, unless SAS ; changes parameter passing conventions between new releases of SAS/C. Cur_Match reg d0 ; Must be in d0! Best_Len reg d1 Loop_Counter reg d2 Scan_Start reg d3 Scan_End reg d4 Limit reg d5 Chain_Length reg d6 Scan_Test reg d7 Scan reg a0 Match reg a1 Prev_Address reg a2 Scan_Ini reg a3 Match_Ini reg a4 MAX_MATCH equ 258 MIN_MATCH equ 3 ifnd WSIZE WSIZE equ 32768 endc MAX_DIST equ WSIZE-MAX_MATCH-MIN_MATCH-1 xref _max_chain_length xref _prev_length xref _prev xref _window xref _strstart xref _good_match xref _match_start xref _nice_match section match,code xdef _match_init xdef @match_init xdef _longest_match xdef @longest_match _match_init: @match_init: rts _longest_match: move.l 4(sp),Cur_Match @longest_match: ifd UNALIGNED_OK movem.l d2-d6/a2-a4,-(sp) else movem.l d2-d7/a2-a4,-(sp) endc move.l _max_chain_length,Chain_Length move.l _prev_length,Best_Len lea _prev,Prev_Address lea _window+MIN_MATCH,Match_Ini move.l _strstart,Limit move.l Match_Ini,Scan_Ini add.l Limit,Scan_Ini subi.w #MAX_DIST,Limit bhi.b limit_ok moveq #0,Limit limit_ok: cmp.l _good_match,Best_Len bcs.b length_ok lsr.l #2,Chain_Length length_ok: subq.l #1,Chain_Length ifd UNALIGNED_OK move.w -MIN_MATCH(Scan_Ini),Scan_Start move.w -MIN_MATCH-1(Scan_Ini,Best_Len.L),Scan_End else move.b -MIN_MATCH(Scan_Ini),Scan_Start lsl.w #8,Scan_Start move.b -MIN_MATCH+1(Scan_Ini),Scan_Start move.b -MIN_MATCH-1(Scan_Ini,Best_Len.L),Scan_End lsl.w #8,Scan_End move.b -MIN_MATCH(Scan_Ini,Best_Len.L),Scan_End endc bra.b do_scan long_loop: ifd UNALIGNED_OK move.w -MIN_MATCH-1(Scan_Ini,Best_Len.L),Scan_End else move.b -MIN_MATCH-1(Scan_Ini,Best_Len.L),Scan_End lsl.w #8,Scan_End move.b -MIN_MATCH(Scan_Ini,Best_Len.L),Scan_End endc short_loop: lsl.w #1,Cur_Match move.w 0(Prev_Address,Cur_Match.L),Cur_Match cmp.w Limit,Cur_Match dbls Chain_Length,do_scan bra.b return do_scan: move.l Match_Ini,Match add.l Cur_Match,Match ifd UNALIGNED_OK cmp.w -MIN_MATCH-1(Match,Best_Len.L),Scan_End bne.b short_loop cmp.w -MIN_MATCH(Match),Scan_Start bne.b short_loop else move.b -MIN_MATCH-1(Match,Best_Len.L),Scan_Test lsl.w #8,Scan_Test move.b -MIN_MATCH(Match,Best_Len.L),Scan_Test cmp.w Scan_Test,Scan_End bne.b short_loop move.b -MIN_MATCH(Match),Scan_Test lsl.w #8,Scan_Test move.b -MIN_MATCH+1(Match),Scan_Test cmp.w Scan_Test,Scan_Start bne.b short_loop endc move.w #(MAX_MATCH-MIN_MATCH),Loop_Counter move.l Scan_Ini,Scan scan_loop: cmpm.b (Match)+,(Scan)+ dbne Loop_Counter,scan_loop sub.l Scan_Ini,Scan addq.l #(MIN_MATCH-1),Scan cmp.l Best_Len,Scan bls.b short_loop move.l Scan,Best_Len move.l Cur_Match,_match_start cmp.l _nice_match,Best_Len bcs.b long_loop return: move.l Best_Len,d0 ifd UNALIGNED_OK movem.l (sp)+,d2-d6/a2-a4 else movem.l (sp)+,d2-d7/a2-a4 endc rts end zip30/amiga/match_68.a0100644000076400000060000002127107011110400012575 0ustar edisk;=========================================================================== ; Copyright (c) 1990-1999 Info-ZIP. All rights reserved. ; ; See the accompanying file LICENSE, version 1999-Oct-05 or later ; (the contents of which are also included in zip.h) for terms of use. ; If, for some reason, both of these files are missing, the Info-ZIP license ; also may be found at: ftp://ftp.cdrom.com/pub/infozip/license.html ;=========================================================================== ; This is a 68000 assembly language version of the Zip function ; longest_match(). It is written for any 680x0 based computer, but at this ; time the feature for runtime testing of CPU type is only supported for the ; Amiga. Hopefully a similar test for the Macintosh is possible, and for any ; other system that supports both 68000 and 68020+ CPUs. This is written by ; Paul Kienitz, partially derived from a simpler version by Carsten Steger, ; derived in turn from a 386 assembly function by Jean-loup Gailly and Kai Uwe ; Rommel... but also based directly on the C original. ; ; The main difference of this from other longest_match() implementations is ; that it includes both byte based and word based versions of the function, ; and various symbols can be defined to select whether to use one routine or ; the other, or to do a platform-specific test at runtime. The symbols that ; can be used to select behavior are as follows: ; ; CPU020 if defined, use 68020 instructions always ; CPUTEST if defined, check at runtime for CPU type. Another symbol ; specifying the platform-specific test must be used with this. ; If neither of these is defined, use 68000 instructions only. ; AMIGA use Amiga-specific test for 68020, if CPUTEST defined. Also ; tells it to let a0/a1/d1 be clobbered by functions. ; ATSIGN define entry symbols in @foo form as well as _foo, with ; @longest_match taking its parm in d0 instead of on the stack. ; WSIZE if defined, determines the sliding window size for deflate; ; the default is 32K. If you have reduced WSIZE for the C code, ; make sure that this module is assembled with an equivalent ; "-dWSIZE=" (or "-e...") switch. ; ; NOTE: no provision is made for 16 bit ints. All external int variables are ; treated as 32 bit values. This also assumes that longest_match's result is ; returned in D0. IFND CPU020 IFND CPUTEST CPU000 equ 1 ENDC ENDC ; global variables: xref _max_chain_length ; unsigned int xref _prev_length ; unsigned int xref _match_start ; unsigned int xref _strstart ; unsigned int xref _good_match ; signed int xref _nice_match ; signed int xref _window ; array of unsigned char xref _prev ; array of unsigned short ; our entry points: xdef _match_init ; void match_init(void); xdef _longest_match ; int longest_match(unsigned cur_match); IFD ATSIGN xdef @match_init ; for SAS assembler xdef @longest_match ; ditto ENDC ; flag variable for remembering CPU type: IFD CPUTEST section cpuflag,data is020: ds.w 1 ENDC section match,code _match_init: IFD ATSIGN @match_init: ENDC IFD CPUTEST ; now check for platform type IFD AMIGA ; Amiga specific test for '020 CPU: xref _SysBase NOLIST INCLUDE 'exec/execbase.i' LIST clr.w is020 ; default value is 68000 move.l _SysBase,a0 btst #AFB_68020,AttnFlags+1(a0) beq.s cheap move.w #1,is020 cheap: ELSE ; !AMIGA !! Write an '020-detector for your system here! ENDC ; AMIGA ENDC ; CPUTEST rts ; match_init consists only of rts if CPUTEST unset IFD AMIGA SAVEREGS reg d3-d7/a2/a3/a5 ; don't protect d0/d1/a0/a1 ELSE SAVEREGS reg d1/d3-d7/a0-a3/a5 ; protect all but d0 return val ENDC Cur_Match equr d0 ; Must be in d0! Best_Len equr d1 Scan_Start equr d3 Scan_End equr d4 Limit equr d5 Chain_Length equr d6 Scan_Test equr d7 Scan equr a0 Match equr a1 Prev_Address equr a2 Scan_Ini equr a3 Match_Ini equr a5 MAX_MATCH equ 258 MIN_MATCH equ 3 IFND WSIZE WSIZE equ 32768 ENDC MAX_DIST equ WSIZE-MAX_MATCH-MIN_MATCH-1 _longest_match: move.l 4(sp),Cur_Match ; stack arg to register IFD ATSIGN @longest_match: ENDC movem.l SAVEREGS,-(sp) ; setup steps common to byte and word versions: move.l _max_chain_length,Chain_Length move.l _prev_length,Best_Len lea _prev,Prev_Address lea _window,Match_Ini move.l _strstart,Limit move.l Match_Ini,Scan_Ini addq #MIN_MATCH,Match_Ini add.l Limit,Scan_Ini subi.w #MAX_DIST,Limit bhi.s limit_ok moveq #0,Limit limit_ok: cmp.l _good_match,Best_Len bcs.s length_ok lsr.l #2,Chain_Length length_ok: subq.l #1,Chain_Length IFD CPUTEST tst.w is020 ; can we use '020 stuff today? bne WORD_match ENDC IFND CPU020 ; for 68000 or 68010, use byte operations: moveq #0,Scan_Start ; clear 2nd and 4th bytes, use 1st & 3rd moveq #0,Scan_End moveq #0,Scan_Test move.b (Scan_Ini),Scan_Start swap Scan_Start move.b 1(Scan_Ini),Scan_Start move.b -1(Scan_Ini,Best_Len),Scan_End swap Scan_End move.b 0(Scan_Ini,Best_Len),Scan_End bra.s bdo_scan blong_loop: move.b -1(Scan_Ini,Best_Len),Scan_End swap Scan_End move.b 0(Scan_Ini,Best_Len),Scan_End bshort_loop: add.w Cur_Match,Cur_Match move.w 0(Prev_Address,Cur_Match.l),Cur_Match cmp.l Limit,Cur_Match dbls Chain_Length,bdo_scan bra return bdo_scan: move.l Match_Ini,Match add.l Cur_Match,Match move.b -MIN_MATCH-1(Match,Best_Len),Scan_Test swap Scan_Test move.b -MIN_MATCH(Match,Best_Len),Scan_Test cmp.l Scan_Test,Scan_End bne.s bshort_loop move.b -MIN_MATCH(Match),Scan_Test swap Scan_Test move.b -MIN_MATCH+1(Match),Scan_Test cmp.l Scan_Test,Scan_Start bne.s bshort_loop move.w #(MAX_MATCH-MIN_MATCH),Scan_Test lea MIN_MATCH(Scan_Ini),Scan bscan_loop: cmpm.b (Match)+,(Scan)+ dbne Scan_Test,bscan_loop subq #1,Scan sub.l Scan_Ini,Scan cmp.l Best_Len,Scan bls.s bshort_loop move.l Scan,Best_Len move.l Cur_Match,_match_start cmp.l _nice_match,Best_Len bcs.s blong_loop IFD CPUTEST bra return ENDC ENDC ; !CPU020 IFND CPU000 ; for 68020 or higher, use word operations even on odd addresses: WORD_match: move.w (Scan_Ini),Scan_Start move.w -1(Scan_Ini,Best_Len),Scan_End bra.s wdo_scan wlong_loop: move.w -1(Scan_Ini,Best_Len),Scan_End wshort_loop: add.w Cur_Match,Cur_Match move.w (Prev_Address,Cur_Match.l),Cur_Match cmp.l Limit,Cur_Match dbls Chain_Length,wdo_scan bra.s return wdo_scan: move.l Match_Ini,Match add.l Cur_Match,Match cmp.w -MIN_MATCH-1(Match,Best_Len),Scan_End bne.s wshort_loop cmp.w -MIN_MATCH(Match),Scan_Start bne.s wshort_loop moveq #((MAX_MATCH-MIN_MATCH)/2),Scan_Test ; value = 127 lea MIN_MATCH(Scan_Ini),Scan wscan_loop: cmpm.w (Match)+,(Scan)+ dbne Scan_Test,wscan_loop subq #2,Scan move.b -MIN_MATCH+1(Match),Scan_Test cmp.b (Scan),Scan_Test bne steven addq #1,Scan steven: sub.l Scan_Ini,Scan cmp.l Best_Len,Scan bls.s wshort_loop move.l Scan,Best_Len move.l Cur_Match,_match_start cmp.l _nice_match,Best_Len bcs.s wlong_loop ENDC ; !CPU000 return: move.l Best_Len,d0 ; function return value movem.l (sp)+,SAVEREGS rts end zip30/amiga/osdep.h0100644000076400000060000000771310272630512012330 0ustar edisk/* Copyright (c) 1990-2005 Info-ZIP. All rights reserved. See the accompanying file LICENSE, version 2005-Feb-10 or later (the contents of which are also included in zip.h) for terms of use. If, for some reason, all these files are missing, the Info-ZIP license also may be found at: ftp://ftp.info-zip.org/pub/infozip/license.html */ #ifndef __amiga_osdep_h #define __amiga_osdep_h /* default to MEDIUM_MEM, but allow makefile override */ #if ( (!defined(BIG_MEM)) && (!defined(SMALL_MEM))) # define MEDIUM_MEM #endif /* check that TZ environment variable is defined before using UTC times */ #if (!defined(NO_IZ_CHECK_TZ) && !defined(IZ_CHECK_TZ)) # define IZ_CHECK_TZ #endif #ifndef IZTZ_GETLOCALETZINFO # define IZTZ_GETLOCALETZINFO GetPlatformLocalTimezone #endif /* AmigaDOS can't even support disk partitions over 4GB, let alone files */ #define NO_LARGE_FILE_SUPPORT #ifdef LARGE_FILE_SUPPORT # undef LARGE_FILE_SUPPORT #endif #define USE_CASE_MAP #define USE_EF_UT_TIME #define HANDLE_AMIGA_SFX #define PROCNAME(n) (action == ADD || action == UPDATE ? wild(n) : \ procname(n, 1)) #define EXIT(e) ClearIOErr_exit(e) void ClearIOErr_exit(int e); #include "amiga/z-stat.h" #ifdef __SASC # include # include # if (defined(_M68020) && (!defined(__USE_SYSBASE))) /* on 68020 or higher processors it is faster */ # define __USE_SYSBASE /* to use the pragma libcall instead of syscall */ # endif /* to access functions of the exec.library */ # include /* see SAS/C manual:part 2,chapter 2,pages 6-7 */ # include # if (defined(_M68020) && !defined(UNALIGNED_OK)) # define UNALIGNED_OK # endif # ifndef REENTRANT # define REENTRANT # endif # if (defined(_NEAR_DATA) && !defined(DYN_ALLOC)) # define DYN_ALLOC # endif # ifdef DEBUG # include /* profiler header file */ # endif # ifndef IZTZ_SETLOCALTZINFO /* XXX !! We have really got to find a way to operate without these. */ # define IZTZ_SETLOCALTZINFO # endif /* A word on short-integers and SAS/C (a bug of [mc]alloc?) Using short integers (i.e. compiling with option SHORT-INTEGERS) is *not* recommended. To get maximum compression ratio the window size stored in WSIZE should be 32k (0x8000). However, since the size of the window[] array is 2*WSIZE, 65536 bytes must be allocated. The calloc function can only allocate UINT_MAX (defined in limits.h) bytes which is one byte short (65535) of the maximum window size if you are compiling with short-ints. You'll get an error message "Out of memory (window allocation)" whenever you try to deflate. Note that the compiler won't produce any warning. The maximum window size with short-integers is therefore 32768 bytes. The following is only implemented to allow the use of short-integers but it is once again not recommended because of a loss in compression ratio. */ # if (defined(_SHORTINT) && !defined(WSIZE)) # define WSIZE 0x4000 /* only half of maximum window size */ # endif /* possible with short-integers */ #endif /* __SASC */ /* With Aztec C, using short integers imposes no size limits and makes the program run faster, even with 32 bit CPUs, so it's recommended. */ #ifdef AZTEC_C # define NO_UNISTD_H # define NO_RMDIR # define BROKEN_FSEEK # ifndef IZTZ_DEFINESTDGLOBALS # define IZTZ_DEFINESTDGLOBALS # endif #endif extern int real_timezone_is_set; void tzset(void); #define VALID_TIMEZONE(tempvar) (tzset(), real_timezone_is_set) #ifdef ZCRYPT_INTERNAL # ifndef CLIB_EXEC_PROTOS_H void *FindTask(void *); # endif # define ZCR_SEED2 (unsigned)(ulg)FindTask(NULL) #endif int Agetch(void); /* getch() like function, in amiga/filedate.c */ char *GetComment(char *); #define FOPR "rb" #define FOPM "rb+" #define FOPW "wb" /* prototype for ctrl-C trap function */ void _abort(void); #endif /* !__amiga_osdep_h */ zip30/amiga/README0100644000076400000060000000006506254362760011732 0ustar ediskthe -A option currently does not work for the amiga. zip30/amiga/smakefile0100644000076400000060000005525510550050270012730 0ustar edisk#=========================================================================== # Makefile for Zip, ZipNote, ZipCloak, ZipSplit AMIGA SAS/C Version 6.58 # Version: 2.3 last revised: 07 Jan 2007 #=========================================================================== # -John Bush, # or: # updated for SAS/C Version 6.56+ and AmigaDOS 3.1 (V40) # by Haidinger Walter, # additional supplements and maintenance by Paul Kienitz # This makefile should work with at least AmigaDOS 2.04 (V37) (not tested) # and will probably not work with AmigaDOS 1.3 (V34) # If you have any improvements, critics or else please feel free to mail. # Any response is appreciated. Haidinger Walter # Available targets: # all builds all executeables below # zip builds zip executeable # zipsplit builds zipsplit executeable # zipcloak builds zipcloak executeable # zipnote builds zipnote executeable # ziplm builds low memory version of zip executable # clean remove all files created by the compilation # spotless like clean target but removes binaries too ########################## # USER MACRO DEFINITIONS # ########################## # *** NOTE *** # The assembly version is not implemented yet. # (Un)commenting the assembler macros has no effect unless the # file dependencies are changed too. # Most of the amiga/*.a files do not assmble with 68000 instructions. # Any help is appreciated, of course. # Set the processor to generate code for. # Compiler: ANY 68000 68010 68020 68030 68040 68060 # Assembler: 0 0 1 2 3 4 n/a # Defaults: ANY and 0 # CUSECPU = ANY AUSECPU = 0 # UNCOMMENT to use 68020 instructions in the assembly version of deflate.o # Only use if code is generated for 68020 or higher processors above. # Note: You could use CPUTEST too to enable runtime cpu detection. # However, it is not recommended since both 68000 and 68020 code will be # included which would be an unnecessary increase in size. # (see amiga/deflate.a for more information) # #AUSE020 = CPU020 # To disable the assembler replacements and use the standard C source, # you have to change the Zip and ZipLM dependencies. See below for details. # (remember that assembler use is *not* implemented yet) # Uncomment both CUTIL and LUTIL to make use of utility.library of OS 2.04+ # The utility.library is *not* used for UnZipSFX to ensure maximum portability # between the different Amiga systems (minimal config: 68000 and OS 1.2). # You can change this by adding the $(LUTIL) macro in the UnZipSFX linking # rules (See below: Final output targets, UnZipSFX:). # WARNINGS when using the utility library: # 1. All Executables will *only* work with AmigaDOS 2.04 (v37) or higher. # 2. You *need not* compile/link with short-integers using the # utility.library. It will crash your machine. See Libraries below. # # Default: commented (not used) # #CUTIL = UTILLIB DEFINE=_UTILLIB #LUTIL = WITH SC:LIB/utillib.with # include necessary linker defines # Choose one stack-handling method (default=faster) # StackExtend: Dynamic runtime stack extension. You won't notice stack overflows. # StackCheck: On a stack overflow a requester appears which allows you to exit. # Note that either stack watching will slow down your executable because of the # extra code run on each function entry. On the other hand, you won't crash # anymore due to stack overflows. However, you should not have *any* stack # problems with Info-ZIP programs if you raise your stack to 10000 (which I'd # recommend as a minimum default stack for all applications) or more using the # shell stack command. Type 'Stack 20000' or add it to your S:Shell-Startup. # BTW: Typing 'Stack' prints your current stack size. # CSTACK = NOSTACKCHECK STACKEXTEND # slow, but always works #CSTACK = STACKCHECK NOSTACKEXTEND # slow, requester & graceful exit #CSTACK = NOSTACKCHECK NOSTACKEXTEND # faster but relies on larger stack (>=10K) # # LIBRARIES # --------- # Choose one DATAOPTS , SASLIB , ASMOPTS and LSTARTUP # Always comment/uncomment all macros of a set. # Library to use with near data and 2-byte integers # Notes: o slower than 4-byte integers with 68000 cpu # o *not* recommended due to poor overall performance # o see comment in amiga/osdep.h #DATAOPTS = DATA=NEAR SHORTINTEGERS DEF=_NEAR_DATA #SASLIB = scs #ASMOPTS = -dINT16 #LSTARTUP = cres.o # Library to use with near data and 4-byte integers (DEFAULT) # *** use this with the utility.library *** DATAOPTS = DATA=NEAR DEF=_NEAR_DATA SASLIB = sc ASMOPTS = LSTARTUP = cres.o # Library to use with far data and 2-byte integers # use if DYN_ALLOC is not defined # old default - far data always works but is slower #DATAOPTS = DATA=FAR SHORTINTEGERS DEF=_FAR_DATA #SASLIB = scsnb #ASMOPTS = -dINT16 #LSTARTUP = c.o # Library to use with far data and 4-byte integers # if everything else fails: try this #DATAOPTS = DATA=FAR DEF=_FAR_DATA #SASLIB = scnb #ASMOPTS = #LSTARTUP = c.o # # DEBUGGING # --------- # Default: No debugging information added. # The three macros below will be overwritten if you choose to add # debug info, therefore no need to comment. CDBG = NODEBUG NOPROFILE NOCOVERAGE # default: no debug info ADBG = LDBG = STRIPDEBUG # default: no debug info # Compiler and loader debug flags. Uncomment as needed. Recomment when done. # Optimization disabled for faster compilation (by using NOOPT) #CDBG1 = DEF=DEBUG DEF=DEBUG_TIME # enables Info-Zip's debug output # Enable profiling and coverage when desired. Option COVERAGE commented # seperately because running coverage may corrupt your drive in case of a # system crash since a file 'cover.dat' is created in your working directory. # Note that the use of COVERAGE forces the use of the c.o startup module. #CDBG2 = PROFILE #CDBG3 = COVERAGE # must use c.o startup code: #LSTARTUP = c.o # Uncomment *only* when you use COVERAGE # *Uncomment* here macros CDBG, ADBG and LDBG to include debugging information #CDBG = $(CDBG1) $(CDBG2) $(CDBG3) ADDSYM DEBUG=FULLFLUSH STACKCHECK NOOPT #ADBG = DEBUG #LDBG = ADDSYM # Optional use of memwatch.library which can be found in your # sc:extras/memlib directory. Please read the short docs (memlib.doc). # Note that memwatch.library has a small bug: MWTerm() displays always # the first entry. # Get the latest version from aminet (dev/debug/memlib.lha) or # contact me to get the patch. Uncomment all macros to use. #CMEMLIB = DEFINE=MWDEBUG=1 # define to enable library #LMEMLIB = SC:LIB/memwatch.lib # path to library #LSTARTUP = c.o # must use c.o with memlib! # # MAPPING # ------- # Map filenames used when mapping (no need to comment) # MAPFZ = zip.map # Zip map filename MAPFN = zipnote.map # ZipNote map filename MAPFC = zipcloak.map # ZipCloak map filename MAPFS = zipsplit.map # ZipSplit map filename MAPFL = ziplm.map # Zip low memory version map filename # Map file output: Uncomment to highlight and bold headings. # #MAPFSTYLE = FANCY # Map flags for each EXECUTABLE. Uncomment to enable mapping. # For map options please refer to: # SAS/C v6 manual, volume 1: user's guide, chapter 8, page 136: map # Default: all options enabled: f,h,l,o,s,x # |-> options start here #LMAPZ = $(MAPFSTYLE) MAP $(MAPFZ) f,h,l,o,s,x # Zip maps #LMAPN = $(MAPFSTYLE) MAP $(MAPFN) f,h,l,o,s,x # ZipNote maps #LMAPC = $(MAPFSTYLE) MAP $(MAPFC) f,h,l,o,s,x # ZipCloak maps #LMAPS = $(MAPFSTYLE) MAP $(MAPFS) f,h,l,o,s,x # ZipSplit maps #LMAPL = $(MAPFSTYLE) MAP $(MAPFL) f,h,l,o,s,x # Zip lowmem maps # # LISTINGS # -------- # Listfile-extensions for each executable (enter *with* dot) # LISTEXTZ = .lst # extension for Zip listfiles LISTEXTU = .ulst # extension for utility listfiles (ZipNote,ZipCloak,ZipSplit) LISTEXTL = .llst # extension for Zip low memory listfiles # List files and cross references for each OBJECT. # Add/remove flags as needed. Not all listed by default. # Use LISTINCLUDES to determine the dependencies for smake # CLISTOPT = LISTHEADERS LISTMACROS # LISTSYSTEM LISTINCLUDES CXREFOPT = XHEAD XSYS # # Uncomment to enable listing (default: commented) # *** WARNING: List files require *lots* of disk space! # #CLIST = LIST $(CLISTOPT) #CXREF = XREF $(CXREFOPT) # # SUPPRESSED COMPILER WARNINGS # ---------------------------- # Compiler warnings to ignore # # Warning 105 : module does not define any externally-known symbols # Warning 304 : Dead assignment eliminated... # Note 306 : ...function inlined... # Warning 317 : possibly uninitialized variable... # Comment to enable. # CIGNORE = IGNORE=105,304,306,317 # # OBJECT EXTENSIONS # # Extensions used for objects of each executeable. # Transformation rules require unique extensions. # Enter *with* dot. # O = .o # extension for Zip objects OU = .uo # extension for utility objects (ZipNote, ZipSplit and ZipCloak) OL = .lo # extension for low memory Zip objects # Filename used to store converted options from environment variable # LOCAL_ZIP. Default: scoptions_local_zip # CWITHOPT = scoptions_local_zip # Filenames to store compiler options to prevent command line overflow # # Common options file for Zip and other executables CFILE = scoptions-zip # Temp filenames for object lists to load using linker "WITH" command. OBJLISTZ = zip_objlist.with # Zip object list OBJLISTN = zipnote_objlist.with # ZipNote object list OBJLISTC = zipcloak_objlist.with # ZipCloak object list OBJLISTS = zipsplit_objlist.with # ZipSplit object list OBJLISTL = ziplm_objlist.with # Zip low-mem object list # Filenames to store linker options # LWITHZ = zip.lnk # zip linker options LWITHN = zipnote.lnk # zipnote linker options LWITHC = zipcloak.lnk # zipcloak linker options LWITHS = zipsplit.lnk # zipsplit linker options LWITHL = ziplm.lnk # zip low-mem linker options # Define AMIGA_BETA to print "Beta Notice" up front. See tailor.h. # Undefine AMIGA_BETA when building a released version. #CDEFBETA = DEF=AMIGA_BETA ##################################### # NOTHING TO CHANGE BEYOND HERE ... # ##################################### # (except for C/asm dependencies) # Define MEDIUM_MEM for production release (per Paul Kienitz). # This reduces runtime memory requirement but not speed or compression. # Note: Do *not* use BIG_MEM or MMAP since it isn't yet supported by the assembler version of deflate.c : amiga/deflate.a CUSEMEM = DEF=MEDIUM_MEM AUSEMEM = -DMEDIUM_MEM # for asm deflate.o, must match above # Defines for building low-memory use version of Zip WSIZEL = WSIZE=4096 # deflate.c window size for low-mem version CLOWMEM = DEF=SMALL_MEM DEF=$(WSIZEL) ALOWMEM = -DSMALL_MEM -D$(WSIZEL) # for asm deflate.o, must match above # Compiler definitions # CC = sc # # Optimizer flags # OPTPASSES = 6 # set number of global optimizer passes # OPT1 = OPT OPTINL OPTINLOCAL OPTTIME OPTLOOP OPTSCHED OPT2 = OPTCOMP=$(OPTPASSES) OPTDEP=$(OPTPASSES) OPTRDEP=$(OPTPASSES) OPT = $(OPT1) $(OPT2) # Compiler flags # CDEFINES = $(CMEMLIB) $(CDEFBETA) DEF=AMIGA COPTIONS = $(DATAOPTS) CODE=NEAR CPU=$(CUSECPU) VERBOSE PARAMETERS=BOTH NOMINC COPTIONS = $(COPTIONS) ERRORREXX NOERRORCONSOLE MEMSIZE=HUGE $(CLIST) $(CXREF) COPTIONS = $(COPTIONS) $(CSTACK) $(CUTIL) STRICT UNSCHAR NOICONS STRINGMERGE CFLAGS = $(CDEFINES) $(COPTIONS) $(OPT) $(CDBG) $(CIGNORE) # Linker definitions # See SASLIB definition above # LD = slink # special linker flags for pure (i.e. resident) binary. LDFLAGSS = FROM SC:LIB/$(LSTARTUP) # common linker flags for all other executeables LDFLAGSC = FROM SC:LIB/c.o LDFLAGS2 = NOICONS $(LDBG) LIBFLAGS = LIB $(LMEMLIB) SC:LIB/$(SASLIB).lib SC:LIB/amiga.lib # Assembler definitions # ASM = asm # # Options used for assembling amiga/deflate.a # Must match defines in C-Source. # AFLAGS0 = -d__SASC -dSASC -dAMIGA AFLAGS1 = $(AUSE020) $(ASMOPTS) $(ADBG) AFLAGS2 = -m$(AUSECPU) -jm -iINCLUDE: AFLAGS = $(AFLAGS0) $(AFLAGS1) $(AFLAGS2) ASMOPTSZ = $(AFLAGS) $(AUSEMEM) -dDYN_ALLOC # Zip asm flags ASMOPTSL = $(AFLAGS) $(ALOWMEM) # Zip low-mem version asm flags ################## # TARGET OBJECTS # ################## # Zip objects OBJZ1 = zip$(O) zipfile$(O) zipup$(O) fileio$(O) util$(O) globals$(O) OBJZ2 = crc32$(O) crypt$(O) timezone$(O) ttyio$(O) OBJZI = deflate$(O) trees$(O) OBJZA = amiga$(O) amigazip$(O) stat$(O) filedate$(O) OBJZ = $(OBJZ1) $(OBJZ2) $(OBJZI) $(OBJZA) # Shared utility objects for ZipNote, ZipCloak and ZipSplit OBJU1 = globals$(O) OBJUU = zipfile$(OU) fileio$(OU) timezone$(O) util$(OU) OBJUA = amigazip$(OU) amiga$(O) stat$(O) filedate$(O) OBJU = $(OBJU1) $(OBJUU) $(OBJUA) # ZipNote objects OBJN1 = zipnote$(O) OBJN = $(OBJN1) $(OBJU) # ZipCloak objects OBJC1 = zipcloak$(O) OBJCU = $(OBJU) crypt$(OU) OBJCS = crc32$(OU) ttyio$(O) OBJC = $(OBJC1) $(OBJCU) $(OBJCS) #ZipSplit objects OBJS1 = zipsplit$(O) OBJS = $(OBJS1) $(OBJU) # ZipLM objects OBJL1 = zip$(OL) zipfile$(OL) zipup$(OL) fileio$(OL) util$(OL) globals$(OL) OBJL2 = crc32$(OL) crypt$(OL) timezone$(OL) ttyio$(OL) OBJLI = deflate$(OL) trees$(OL) OBJLA = amiga$(OL) amigazip$(OL) stat$(OL) filedate$(OL) OBJL = $(OBJL1) $(OBJL2) $(OBJLI) $(OBJLA) # Common header files ZIP_H1 = zip.h ziperr.h tailor.h ZIP_HA = amiga/osdep.h amiga/z-stat.h ZIP_H = $(ZIP_H1) $(ZIP_HA) # Output targets ZIPS = Zip ZipNote ZipCloak ZipSplit ZipLM # Temp filenames for object lists to load using linker "WITH" command. OBJLISTZ = zip_objlist.with # Zip object list OBJLISTN = zipnote_objlist.with # ZipNote object list OBJLISTC = zipcloak_objlist.with # ZipCloak object list OBJLISTS = zipsplit_objlist.with # ZipSplit object list OBJLISTL = ziplm_objlist.with # Zip low-mem object list ####################################### # DEFAULT TARGET AND PROCESSING RULES # ####################################### all: request flush $(ZIPS) # Zip transformation rules # .c$(O): $(CC) WITH=$(CFILE) $(CUSEMEM) LISTFILE=$>$(LISTEXTZ) OBJNAME=$@ $*.c # Zip low-memory version transformation rules # .c$(OL): $(CC) WITH=$(CFILE) $(CLOWMEM) LISTFILE=$>$(LISTEXTL) OBJNAME=$@ $*.c # Utilities (ZipNote, ZipCloak and ZipSplit) transformation rules # .c$(OU): $(CC) WITH=$(CFILE) $(CUSEMEM) DEF=UTIL LISTFILE=$>$(LISTEXTU) OBJNAME=$@ $*.c ######################### # Final output targets. # ######################### zip: local_zip CommonFlags $(OBJZ) @Echo "$(OBJZ)" > $(OBJLISTZ) Type $(OBJLISTZ) @Echo "$(LDFLAGSS) $(LUTIL) WITH $(OBJLISTZ) $(LIBFLAGS)" \ "$(LDFLAGS2) $(LMAPZ)" >$(LWITHZ) Type $(LWITHZ) $(LD) TO Zip WITH $(LWITHZ) zipnote: local_zip CommonFlags $(OBJN) @Echo "$(OBJN)" > $(OBJLISTN) Type $(OBJLISTN) @Echo "$(LDFLAGSS) $(LUTIL) WITH $(OBJLISTN) $(LIBFLAGS) " \ "$(LDFLAGS2) $(LMAPN)" >$(LWITHN) Type $(LWITHN) $(LD) TO ZipNote WITH $(LWITHN) zipcloak: local_zip CommonFlags $(OBJC) @Echo "$(OBJC)" > $(OBJLISTC) Type $(OBJLISTC) @Echo "$(LDFLAGSS) $(LUTIL) WITH $(OBJLISTC) $(LIBFLAGS) " \ "$(LDFLAGS2) $(LMAPC)" >$(LWITHC) Type $(LWITHC) $(LD) TO ZipCloak WITH $(LWITHC) zipsplit: local_zip CommonFlags $(OBJS) @Echo "$(OBJS)" > $(OBJLISTS) Type $(OBJLISTS) @Echo "$(LDFLAGSS) $(LUTIL) WITH $(OBJLISTS) $(LIBFLAGS) " \ "$(LDFLAGS2) $(LMAPS)" >$(LWITHS) Type $(LWITHS) $(LD) TO ZipSplit WITH $(LWITHS) ziplm: local_zip CommonFlags $(OBJL) @Echo "$(OBJL)" > $(OBJLISTL) Type $(OBJLISTL) @Echo "$(LDFLAGSS) $(LUTIL) WITH $(OBJLISTL) $(LIBFLAGS) " \ "$(LDFLAGS2) $(LMAPL)" >$(LWITHL) Type $(LWITHL) $(LD) TO ZipLM WITH $(LWITHL) clean: -Delete >nil: $(OBJZ) quiet -Delete >nil: $(OBJN) quiet -Delete >nil: $(OBJC) quiet -Delete >nil: $(OBJS) quiet -Delete >nil: $(OBJL) quiet -Delete >nil: $(OBJLISTZ) $(OBJLISTL) $(OBJLISTN) $(OBJLISTS) $(OBJLISTC) quiet -Delete >nil: $(MAPFZ) $(MAPFN) $(MAPFC) $(MAPFS) $(MAPFL) quiet -Delete >nil: \#?$(LISTEXTZ) \#?$(LISTEXTU) \#?$(LISTEXTL) quiet -Delete >nil: $(CWITHOPT) $(CFILE) quiet -Delete >nil: $(LWITHZ) $(LWITHN) $(LWITHC) $(LWITHS) $(LWITHL) quiet -Delete >nil: env:VersionDate quiet -Delete >nil: \#?.q.?? \#?.tmp \#?.cov quiet spotless: clean -Delete >nil: $(ZIPS) quiet ################ # DEPENDENCIES # ################ # To change between the assembler and C sources, you have to comment/uncomment # the approprite lines. C sources are marked by #C-src and assembler sources # #asm-src at the end. # Zip dependencies: # zip$(O): zip.c $(ZIP_H) revision.h crc32.h crypt.h ttyio.h zipup$(O): zipup.c $(ZIP_H) revision.h crc32.h crypt.h amiga/zipup.h zipfile$(O): zipfile.c $(ZIP_H) revision.h crc32.h crypt$(O): crypt.c $(ZIP_H) crypt.h crc32.h ttyio.h ttyio$(O): ttyio.c $(ZIP_H) crypt.h ttyio.h deflate$(O): deflate.c $(ZIP_H) #C-src trees$(O): trees.c $(ZIP_H) fileio$(O): fileio.c $(ZIP_H) crc32.h util$(O): util.c $(ZIP_H) crc32$(O): crc32.c $(ZIP_H) crc32.h globals$(O): globals.c $(ZIP_H) timezone$(O): timezone.c $(ZIP_H) timezone.h # Amiga specific objects stat$(O): amiga/stat.c amiga/z-stat.h filedate$(O): amiga/filedate.c crypt.h timezone.h amiga$(O): amiga/amiga.c ziperr.h amigazip$(O): amiga/amigazip.c $(ZIP_H) amiga/amiga.h env:Workbench # Substitute assembly version of deflate.c: #deflate$(O): amiga/deflate.a #asm-src # $(ASM) $(ASMOPTSZ) -o$@ $*.a #asm-src # Utility (ZipNote, ZipCloak, ZipSplit) dependencies: # zipnote$(O): zipnote.c $(ZIP_H) revision.h zipcloak$(O): zipcloak.c $(ZIP_H) revision.h crc32.h crypt.h ttyio.h zipsplit$(O): zipsplit.c $(ZIP_H) revision.h zipfile$(OU): zipfile.c $(ZIP_H) revision.h crc32.h fileio$(OU): fileio.c $(ZIP_H) crc32.h util$(OU): util.c $(ZIP_H) crc32$(OU): crc32.c $(ZIP_H) crc32.h crypt$(OU): crypt.c $(ZIP_H) crypt.h crc32.h ttyio.h # Amiga specific objects amigazip$(OU): amiga/amigazip.c $(ZIP_H) amiga/amiga.h env:Workbench # ZipLM dependencies: # zip$(OL): zip.c $(ZIP_H) revision.h crc32.h crypt.h ttyio.h zipup$(OL): zipup.c $(ZIP_H) revision.h crc32.h crypt.h amiga/zipup.h zipfile$(OL): zipfile.c $(ZIP_H) revision.h crc32.h crypt$(OL): crypt.c $(ZIP_H) crypt.h crc32.h ttyio.h ttyio$(OL): ttyio.c $(ZIP_H) crypt.h ttyio.h deflate$(OL): deflate.c $(ZIP_H) trees$(OL): trees.c $(ZIP_H) fileio$(OL): fileio.c $(ZIP_H) crc32.h util$(OL): util.c $(ZIP_H) crc32$(OL): crc32.c $(ZIP_H) globals$(OL): globals.c $(ZIP_H) timezone$(OL): timezone.c $(ZIP_H) timezone.h # Amiga specific objects stat$(OL): amiga/stat.c amiga/z-stat.h filedate$(OL): amiga/filedate.c crypt.h timezone.h amiga$(OL): amiga/amiga.c ziperr.h # Substitute assembly version of deflate.c: #deflate$(OL): amiga/deflate.a # $(ASM) $(ASMOPTSL) -o$@ $*.a ######################## # DEPENDECIES END HERE # ######################## # flush all libraries to provide more mem for compilation flush: @Avail flush >nil: # write common compiler flags to file and echo to user CommonFlags: @Echo "$(CFLAGS)" >$(CFILE) @Type "$(CWITHOPT)" >>$(CFILE) -Type $(CFILE) # special rules for adding Amiga internal version number to amiga/amiga.c amiga$(O): rx > env:VersionDate "say '""'translate(date('E'),'.','/')'""'" $(CC) WITH=$(CFILE) $(CUSEMEM) LISTFILE=$>$(LISTEXTZ) OBJNAME=$@ $*.c -Delete env:VersionDate amiga$(OL): rx > env:VersionDate "say '""'translate(date('E'),'.','/')'""'" $(CC) WITH=$(CFILE) $(CLOWMEM) LISTFILE=$>$(LISTEXTL) OBJNAME=$@ $*.c -Delete env:VersionDate # needed in amiga/amigazip.c # should be set in startup-sequence, but just in case: # (only works with OS 2.0 and above) env\:WorkBench: @Execute < < (Workbench_smk.tmp) FailAt 21 If not exists ENV:Workbench Version >nil: SetEnv Workbench $$Workbench Endif < # Read environment variable LOCAL_ZIP and convert options to SAS format # # e.g.: to define FOO_ONE and FOO_TWO enter: # # SetEnv LOCAL_ZIP "-DFOO_ONE -DFOO_TWO" # # Put the statement into your startup-sequence or (for AmigaDOS 2.0 or higher # only) make sure LOCAL_ZIP is stored in the ENVARC: directory # ( Copy ENV:LOCAL_ZIP ENVARC: ) # local_zip: @Execute < < (Local_Zip_smk.tmp) Failat 21 If exists ENV:LOCAL_ZIP Echo "Using environment variable LOCAL_ZIP !" Copy >NIL: ENV:LOCAL_ZIP SASCOPTS Else Echo "You could use envvar ZIP_OPT to set your special compilation options." Delete >nil: SASCOPTS quiet Endif ; Do not remove the lctosc command! If LOCAL_ZIP is unset, an ; empty file is created which needed by CommonFlags ! lctosc >$(CWITHOPT) < # Echo request to the user # request: @Echo "" @Echo " This makefile is for use with SAS/C version 6.58." @Echo " If you still have an older version, please upgrade!" @Echo " Patches are available on the Aminet under biz/patch/sc\#?." @Echo "" @Echo " Just a simple request..." @Echo " Please give me a mail that you compiled whether you encounter any errors" @Echo " or not. I'd just like to know how many Amiga users actually make use of" @Echo " this makefile." @Echo " If you mail me, I'll put you on my mailing-list and notify you whenever" @Echo " new versions of Info-Zip are released." @Echo " Have a look at the makefile for changes like CPU type, UtilLib, etc." @Echo " Feel free to mail comments, suggestions, etc." @Echo " Enjoy Info-Zip !" @Echo " Haidinger Walter, " @Echo "" # Echo help in case of an error # .ONERROR: @Echo "" @Echo "[sigh] An error running this makefile was detected." @Echo "This message may also appear if you interrupted smake by pressing CTRL-C." @Echo "Contact Info-Zip authors at Zip-Bugs@lists.wku.edu or me for help." @Echo "Haidinger Walter, " zip30/amiga/stat.c0100644000076400000060000002027510154331630012160 0ustar edisk/* Copyright (c) 1990-2000 Info-ZIP. All rights reserved. See the accompanying file LICENSE, version 2000-Apr-09 or later (the contents of which are also included in zip.h) for terms of use. If, for some reason, all these files are missing, the Info-ZIP license also may be found at: ftp://ftp.info-zip.org/pub/infozip/license.html */ /* Here we have a handmade stat() function because Aztec's c.lib stat() */ /* does not support an st_mode field, which we need... also a chmod(). */ /* This stat() is by Paul Wells, modified by Paul Kienitz. */ /* Originally for use with Aztec C >= 5.0 and Lattice C <= 4.01 */ /* Adapted for SAS/C 6.5x by Haidinger Walter */ /* POLICY DECISION: We will not attempt to remove global variables from */ /* this source file for Aztec C. These routines are essentially just */ /* augmentations of Aztec's c.lib, which is itself not reentrant. If */ /* we want to produce a fully reentrant UnZip, we will have to use a */ /* suitable startup module, such as purify.a for Aztec by Paul Kienitz. */ #ifndef __amiga_stat_c #define __amiga_stat_c #include #include #include "amiga/z-stat.h" /* fake version of stat.h */ #include #ifdef AZTEC_C # include # include # include # include # include # include #endif #ifdef __SASC # include /* SAS/C dir function prototypes */ # include # include # include #endif #ifndef SUCCESS # define SUCCESS (-1) # define FAILURE (0) #endif void close_leftover_open_dirs(void); /* prototype */ static DIR *dir_cleanup_list = NULL; /* for resource tracking */ /* CALL THIS WHEN HANDLING CTRL-C OR OTHER UNEXPECTED EXIT! */ void close_leftover_open_dirs(void) { while (dir_cleanup_list) closedir(dir_cleanup_list); } unsigned short disk_not_mounted; extern int stat(const char *file, struct stat *buf); stat(file,buf) const char *file; struct stat *buf; { struct FileInfoBlock *inf; BPTR lock; time_t ftime; struct tm local_tm; if( (lock = Lock((char *)file,SHARED_LOCK))==0 ) /* file not found */ return(-1); if( !(inf = (struct FileInfoBlock *)AllocMem( (long)sizeof(struct FileInfoBlock),MEMF_PUBLIC|MEMF_CLEAR)) ) { UnLock(lock); return(-1); } if( Examine(lock,inf)==FAILURE ) { FreeMem((char *)inf,(long)sizeof(*inf)); UnLock(lock); return(-1); } /* fill in buf */ buf->st_dev = buf->st_nlink = buf->st_uid = buf->st_gid = buf->st_rdev = 0; buf->st_ino = inf->fib_DiskKey; buf->st_blocks = inf->fib_NumBlocks; buf->st_size = inf->fib_Size; /* now the date. AmigaDOS has weird datestamps--- * ds_Days is the number of days since 1-1-1978; * however, as Unix wants date since 1-1-1970... */ ftime = (inf->fib_Date.ds_Days * 86400 ) + (inf->fib_Date.ds_Minute * 60 ) + (inf->fib_Date.ds_Tick / TICKS_PER_SECOND ) + (86400 * 8 * 365 ) + (86400 * 2 ); /* two leap years */ /* tzset(); */ /* this should be handled by mktime(), instead */ /* ftime += timezone; */ local_tm = *gmtime(&ftime); local_tm.tm_isdst = -1; ftime = mktime(&local_tm); buf->st_ctime = buf->st_atime = buf->st_mtime = ftime; buf->st_mode = (inf->fib_DirEntryType < 0 ? S_IFREG : S_IFDIR); /* lastly, throw in the protection bits */ buf->st_mode |= ((inf->fib_Protection ^ 0xF) & 0xFF); FreeMem((char *)inf, (long)sizeof(*inf)); UnLock((BPTR)lock); return(0); } int fstat(int handle, struct stat *buf) { /* fake some reasonable values for stdin */ buf->st_mode = (S_IREAD|S_IWRITE|S_IFREG); buf->st_size = -1; buf->st_mtime = time(&buf->st_mtime); return 0; } /* opendir(), readdir(), closedir(), rmdir(), and chmod() by Paul Kienitz. */ DIR *opendir(const char *path) { DIR *dd = AllocMem(sizeof(DIR), MEMF_PUBLIC); if (!dd) return NULL; if (!(dd->d_parentlock = Lock((char *)path, MODE_OLDFILE))) { disk_not_mounted = IoErr() == ERROR_DEVICE_NOT_MOUNTED; FreeMem(dd, sizeof(DIR)); return NULL; } else disk_not_mounted = 0; if (!Examine(dd->d_parentlock, &dd->d_fib) || dd->d_fib.fib_EntryType < 0) { UnLock(dd->d_parentlock); FreeMem(dd, sizeof(DIR)); return NULL; } dd->d_cleanuplink = dir_cleanup_list; /* track them resources */ if (dir_cleanup_list) dir_cleanup_list->d_cleanupparent = &dd->d_cleanuplink; dd->d_cleanupparent = &dir_cleanup_list; dir_cleanup_list = dd; return dd; } void closedir(DIR *dd) { if (dd) { if (dd->d_cleanuplink) dd->d_cleanuplink->d_cleanupparent = dd->d_cleanupparent; *(dd->d_cleanupparent) = dd->d_cleanuplink; if (dd->d_parentlock) UnLock(dd->d_parentlock); FreeMem(dd, sizeof(DIR)); } } struct dirent *readdir(DIR *dd) { return (ExNext(dd->d_parentlock, &dd->d_fib) ? (struct dirent *)dd : NULL); } #ifdef AZTEC_C int rmdir(const char *path) { return (DeleteFile((char *)path) ? 0 : IoErr()); } int chmod(const char *filename, int bits) /* bits are as for st_mode */ { long protmask = (bits & 0xFF) ^ 0xF; return !SetProtection((char *)filename, protmask); } /* This here removes unnecessary bulk from the executable with Aztec: */ void _wb_parse(void) { } /* fake a unix function that does not apply to amigados: */ int umask(void) { return 0; } # include /* C library signal() messes up debugging yet adds no actual usefulness */ typedef void (*__signal_return_type)(int); __signal_return_type signal() { return SIG_ERR; } /* The following replaces Aztec's argv-parsing function for compatibility with Unix-like syntax used on other platforms. It also fixes the problem the standard _cli_parse() has of accepting only lower-ascii characters. */ int _argc, _arg_len; char **_argv, *_arg_lin; void _cli_parse(struct Process *pp, long alen, register UBYTE *aptr) { register UBYTE *cp; register struct CommandLineInterface *cli; register short c; register short starred = 0; # ifdef PRESTART_HOOK void Prestart_Hook(void); # endif cli = (struct CommandLineInterface *) (pp->pr_CLI << 2); cp = (UBYTE *) (cli->cli_CommandName << 2); _arg_len = cp[0] + alen + 2; if (!(_arg_lin = AllocMem((long) _arg_len, 0L))) return; c = cp[0]; strncpy(_arg_lin, cp + 1, c); _arg_lin[c] = 0; for (cp = _arg_lin + c + 1; alen && (*aptr < '\n' || *aptr > '\r'); alen--) *cp++ = *aptr++; *cp = 0; aptr = cp = _arg_lin + c + 1; for (_argc = 1; ; _argc++) { while (*cp == ' ' || *cp == '\t') cp++; if (!*cp) break; if (*cp == '"') { cp++; while (c = *cp++) { if (c == '"' && !starred) { *aptr++ = 0; starred = 0; break; } else if (c == '\\' && !starred) starred = 1; else { *aptr++ = c; starred = 0; } } } else { while ((c = *cp++) && c != ' ' && c != '\t') *aptr++ = c; *aptr++ = 0; } if (c == 0) --cp; } *aptr = 0; if (!(_argv = AllocMem((_argc + 1) * sizeof(*_argv), 0L))) { _argc = 0; return; } for (c = 0, cp = _arg_lin; c < _argc; c++) { _argv[c] = cp; cp += strlen(cp) + 1; } _argv[c] = NULL; # ifdef PRESTART_HOOK Prestart_Hook(); # endif } #endif /* AZTEC_C */ #endif /* __amiga_stat_c */ zip30/amiga/z-stat.h0100644000076400000060000000621007130036246012432 0ustar edisk/* Copyright (c) 1990-2000 Info-ZIP. All rights reserved. See the accompanying file LICENSE, version 2000-Apr-09 or later (the contents of which are also included in zip.h) for terms of use. If, for some reason, all these files are missing, the Info-ZIP license also may be found at: ftp://ftp.info-zip.org/pub/infozip/license.html */ #ifndef __amiga_z_stat_h #define __amiga_z_stat_h /* Since older versions of the Lattice C compiler for Amiga, and all current */ /* versions of the Manx Aztec C compiler for Amiga, either provide no stat() */ /* function or provide one inadequate for unzip (Aztec's has no st_mode */ /* field), we provide our own stat() function in stat.c by Paul Wells, and */ /* this fake stat.h file by Paul Kienitz. Paul Wells originally used the */ /* Lattice stat.h but that does not work for Aztec and is not distributable */ /* with this package, so I made a separate one. This has to be pulled into */ /* unzip.h when compiling an Amiga version, as "amiga/z-stat.h". */ /* We also provide here a "struct dirent" for use with opendir() & readdir() */ /* functions included in amiga/stat.c. If you use amiga/stat.c, this must */ /* be included wherever you use either readdir() or stat(). */ #ifdef AZTEC_C # define __STAT_H #else /* __SASC */ /* do not include the following header, replacement definitions are here */ # define _STAT_H /* do not include SAS/C */ # define _DIRENT_H /* do not include SAS/C */ # define _SYS_DIR_H /* do not include SAS/C */ # define _COMMIFMT_H /* do not include SAS/C */ # include #endif #include #include struct stat { unsigned short st_mode; time_t st_ctime, st_atime, st_mtime; long st_size; long st_ino; long st_blocks; short st_attr, st_dev, st_nlink, st_uid, st_gid, st_rdev; }; #define S_IFDIR (1<<11) #define S_IFREG (1<<10) #if 0 /* these values here are totally random: */ # define S_IFLNK (1<<14) # define S_IFSOCK (1<<13) # define S_IFCHR (1<<8) # define S_IFIFO (1<<7) # define S_IFMT (S_IFDIR|S_IFREG|S_IFCHR|S_IFLNK) #else # define S_IFMT (S_IFDIR|S_IFREG) #endif #define S_IHIDDEN (1<<7) #define S_ISCRIPT (1<<6) #define S_IPURE (1<<5) #define S_IARCHIVE (1<<4) #define S_IREAD (1<<3) #define S_IWRITE (1<<2) #define S_IEXECUTE (1<<1) #define S_IDELETE (1<<0) int stat(const char *name, struct stat *buf); int fstat(int handle, struct stat *buf); /* returns dummy values */ typedef struct dirent { struct dirent *d_cleanuplink, **d_cleanupparent; BPTR d_parentlock; struct FileInfoBlock d_fib; } DIR; #define d_name d_fib.fib_FileName extern unsigned short disk_not_mounted; /* flag set by opendir() */ DIR *opendir(const char *); void closedir(DIR *); void close_leftover_open_dirs(void); /* call this if aborted in mid-run */ struct dirent *readdir(DIR *); int umask(void); #ifdef AZTEC_C int rmdir(const char *); int chmod(const char *filename, int bits); #endif #endif /* __amiga_z_stat_h */ zip30/amiga/zipup.h0100644000076400000060000000132607011110460012347 0ustar edisk/* Copyright (c) 1990-1999 Info-ZIP. All rights reserved. See the accompanying file LICENSE, version 1999-Oct-05 or later (the contents of which are also included in zip.h) for terms of use. If, for some reason, both of these files are missing, the Info-ZIP license also may be found at: ftp://ftp.cdrom.com/pub/infozip/license.html */ #ifndef __amiga_zipup_h #define __amiga_zipup_h #ifndef O_RAW # define O_RAW 0 #endif #define fhow (O_RDONLY | O_RAW) #define fbad (-1) typedef int ftype; #define zopen(n,p) open(n,p) #define zread(f,b,n) read(f,b,n) #define zclose(f) close(f) #define zerr(f) (k == (extent)(-1L)) #define zstdin 0 #endif /* __amiga_zipup_h */ zip30/aosvs/0040755000076400000060000000000011033727770011126 5ustar ediskzip30/aosvs/aosvs.c0100644000076400000060000005234710154331652012426 0ustar edisk/* Copyright (c) 1990-1999 Info-ZIP. All rights reserved. See the accompanying file LICENSE, version 1999-Oct-05 or later (the contents of which are also included in zip.h) for terms of use. If, for some reason, both of these files are missing, the Info-ZIP license also may be found at: ftp://ftp.cdrom.com/pub/infozip/license.html */ #include #include #include "zip.h" #include /* parameter definitions */ #include /* AOS/VS system call interface */ #include /* AOS/VS ?FSTAT packet defs */ #ifndef UTIL /* AOS/VS specific fileio code not needed for UTILs */ #define PAD 0 #define PATH_END ':' /* * could probably avoid the union - * all are same size & we're going to assume this */ typedef union zvsfstat_stru { P_FSTAT norm_fstat_packet; /* normal fstat packet */ P_FSTAT_DIR dir_fstat_packet; /* DIR/CPD fstat packet */ P_FSTAT_UNIT unit_fstat_packet; /* unit (device) fstat packet */ P_FSTAT_IPC ipc_fstat_packet; /* IPC file fstat packet */ } ZVSFSTAT_STRU; typedef struct zextrafld { char extra_header_id[2]; /* set to VS - in theory, an int */ char extra_data_size[2]; /* size of rest, in Intel little-endian order */ char extra_sentinel[4]; /* set to FCI w/ trailing null */ unsigned char extra_rev; /* set to 10 for rev 1.0 */ ZVSFSTAT_STRU fstat_packet; /* the fstat packet */ char aclbuf[$MXACL]; /* raw ACL, or link-resolution name */ } ZEXTRAFLD; #define ZEXTRA_HEADID "VS" #define ZEXTRA_SENTINEL "FCI" #define ZEXTRA_REV (unsigned char) 10 local ZEXTRAFLD zzextrafld; /* buffer for extra field containing ?FSTAT packet & ACL buffer */ local char zlinkres[$MXPL]; /* buf for link resolution contents */ local char znamebuf[$MXPL]; /* buf for AOS/VS filename */ static char vsnamebuf[$MXPL]; static char uxnamebuf[FNMAX]; static P_FSTAT vsfstatbuf; local ulg label_time = 0; local ulg label_mode = 0; local time_t label_utim = 0; /* Local functions */ local char *readd OF((DIR *)); char *readd(d) DIR *d; /* directory stream to read from */ /* Return a pointer to the next name in the directory stream d, or NULL if no more entries or an error occurs. */ { struct dirent *e; e = readdir(d); return e == NULL ? (char *) NULL : e->d_name; } int procname(n, caseflag) char *n; /* name to process */ int caseflag; /* true to force case-sensitive match */ /* Process a name or sh expression to operate on (or exclude). Return an error code in the ZE_ class. */ { char *a; /* path and name for recursion */ DIR *d; /* directory stream from opendir() */ char *e; /* pointer to name from readd() */ int m; /* matched flag */ char *p; /* path for recursion */ struct stat s; /* result of stat() */ struct zlist far *z; /* steps through zfiles list */ if (strcmp(n, "-") == 0) /* if compressing stdin */ return newname(n, 0, caseflag); else if (LSSTAT(n, &s)) { /* Not a file or directory--search for shell expression in zip file */ p = ex2in(n, 0, (int *)NULL); /* shouldn't affect matching chars */ m = 1; for (z = zfiles; z != NULL; z = z->nxt) { if (MATCH(p, z->iname, caseflag)) { z->mark = pcount ? filter(z->zname, caseflag) : 1; if (verbose) fprintf(mesg, "zip diagnostic: %scluding %s\n", z->mark ? "in" : "ex", z->name); m = 0; } } free((zvoid *)p); return m ? ZE_MISS : ZE_OK; } /* Live name--use if file, recurse if directory */ if ((s.st_mode & S_IFDIR) == 0) { /* add or remove name of file */ if ((m = newname(n, 0, caseflag)) != ZE_OK) return m; } else { /* Add trailing / to the directory name */ if ((p = malloc(strlen(n)+2)) == NULL) return ZE_MEM; if (strcmp(n, ".") == 0) { *p = '\0'; /* avoid "./" prefix and do not create zip entry */ } else { strcpy(p, n); a = p + strlen(p); if (a[-1] != '/') strcpy(a, "/"); if (dirnames && (m = newname(p, 1, caseflag)) != ZE_OK) { free((zvoid *)p); return m; } } /* recurse into directory */ if (recurse && (d = opendir(n)) != NULL) { while ((e = readd(d)) != NULL) { if (strcmp(e, ".") && strcmp(e, "..")) { if ((a = malloc(strlen(p) + strlen(e) + 1)) == NULL) { closedir(d); free((zvoid *)p); return ZE_MEM; } strcat(strcpy(a, p), e); if ((m = procname(a, caseflag)) != ZE_OK) /* recurse on name */ { if (m == ZE_MISS) zipwarn("name not matched: ", a); else ziperr(m, a); } free((zvoid *)a); } } closedir(d); } free((zvoid *)p); } /* (s.st_mode & S_IFDIR) == 0) */ return ZE_OK; } char *strlower(s) char *s; /* string to convert */ /* Convert all uppercase letters to lowercase in string s */ { char *p; /* scans string */ for (p = s; *p; p++) if (*p >= 'A' && *p <= 'Z') *p += 'a' - 'A'; return s; } char *strupper(s) char *s; /* string to convert */ /* Convert all lowercase letters to uppercase in string s */ { char *p; /* scans string */ for (p = s; *p; p++) if (*p >= 'a' && *p <= 'z') *p -= 'a' - 'A'; return s; } char *ex2in(x, isdir, pdosflag) char *x; /* external file name */ int isdir; /* input: x is a directory */ int *pdosflag; /* output: force MSDOS file attributes? */ /* Convert the external file name to a zip file name, returning the malloc'ed string or NULL if not enough memory. */ { char *n; /* internal file name (malloc'ed) */ char *t; /* shortened name */ int dosflag; dosflag = dosify; /* default for non-DOS and non-OS/2 */ /* Find starting point in name before doing malloc */ for (t = x; *t == '/'; t++) ; if (*t == '=') /* AOS/VS for ./ */ t++; else if (*t == ':') /* AOS/VS for / */ t++; if (!pathput) t = last(t, PATH_END); if (*t == '^') /* AOS/VS for ../ */ { if ((n = malloc(strlen(t) + 3)) == NULL) return NULL; strcpy(n, "../"); strcpy(n + 3, t + 1); } else if (*t == '@') /* AOS/VS for :PER:, kind of like /dev/ */ { if ((n = malloc(strlen(t) + 5)) == NULL) return NULL; strcpy(n, "/PER/"); strcpy(n + 5, t + 1); } else { if ((n = malloc(strlen(t) + 1)) == NULL) return NULL; strcpy(n, t); } /* now turn AOS/VS dir separators (colons) into slashes */ for (t = n; *t != '\0'; t++) if (*t == ':') *t = '/'; /* * Convert filename to uppercase (for correct matching). * (It may make more sense to patch the matching code, since * we may want those filenames in uppercase on the target system, * but this seems better at present. If we're converting, uppercase * also seems to make sense.) */ strupper(n); if (dosify) msname(n); /* Returned malloc'ed name */ if (pdosflag) *pdosflag = dosflag; return n; } char *in2ex(n) char *n; /* internal file name */ /* Convert the zip file name to an external file name, returning the malloc'ed string or NULL if not enough memory. */ { char *x; /* external file name */ if ((x = malloc(strlen(n) + 1 + PAD)) == NULL) return NULL; strcpy(x, n); return x; } void stamp(f, d) char *f; /* name of file to change */ ulg d; /* dos-style time to change it to */ /* Set last updated and accessed time of file f to the DOS time d. */ { time_t u[2]; /* argument for utime() */ /* Convert DOS time to time_t format in u */ u[0] = u[1] = dos2unixtime(d); utime(f, u); } ulg filetime(f, a, n, t) char *f; /* name of file to get info on */ ulg *a; /* return value: file attributes */ long *n; /* return value: file size */ iztimes *t; /* return value: access, modific. and creation times */ /* If file *f does not exist, return 0. Else, return the file's last modified date and time as an MSDOS date and time. The date and time is returned in a long with the date most significant to allow unsigned integer comparison of absolute times. Also, if a is not a NULL pointer, store the file attributes there, with the high two bytes being the Unix attributes, and the low byte being a mapping of that to DOS attributes. If n is not NULL, store the file size there. If t is not NULL, the file's access, modification and creation times are stored there as UNIX time_t values. If f is "-", use standard input as the file. If f is a device, return a file size of -1 */ { struct stat s; /* results of stat() */ /* convert FNMAX to malloc - 11/8/04 EG */ char *name; int len = strlen(f); if (f == label) { if (a != NULL) *a = label_mode; if (n != NULL) *n = -2L; /* convention for a label name */ if (t != NULL) t->atime = t->mtime = t->ctime = label_utim; return label_time; } if ((name = malloc(len + 1)) == NULL) { ZIPERR(ZE_MEM, "filetime"); } strcpy(name, f); if (name[len - 1] == '/') name[len - 1] = '\0'; /* not all systems allow stat'ing a file with / appended */ if (strcmp(f, "-") == 0) { if (fstat(fileno(stdin), &s) != 0) error("fstat(stdin)"); } else if (LSSTAT(name, &s) != 0) { /* Accept about any file kind including directories * (stored with trailing / with -r option) */ free(name); return 0; } free(name); if (a != NULL) { *a = ((ulg)s.st_mode << 16) | !(s.st_mode & S_IWRITE); if ((s.st_mode & S_IFDIR) != 0) { *a |= MSDOS_DIR_ATTR; } } if (n != NULL) *n = (s.st_mode & S_IFMT) == S_IFREG ? s.st_size : -1L; if (t != NULL) { t->atime = s.st_atime; t->mtime = s.st_mtime; t->ctime = s.st_ctime; } return unix2dostime(&s.st_ctime); } int deletedir(d) char *d; { return rmdir(d); } int set_extra_field(z, z_utim) struct zlist far *z; iztimes *z_utim; /* create extra field and change z->att if desired */ /* NOTE: this AOS/VS version assumes the pathname in z->name is an * AOS/VS pathname, not a unix-style one. Since you can zip up using * unix-style pathnames, this may create problems occasionally. * We COULD add code to parse back to AOS/VS format ... * (This might also fail for other reasons such as access denied, but * that should already have occurred.) * We set the central-dir extra fld pointer & length here to the same data. */ { int aclend = 0; /* * use this to simplify because different calls depending on * whether links are resolved */ unsigned short errc; z->ext = 0; /* init to no extra field */ /* get the ?FSTAT info & the acl - if no errors, get memory & store. * (first, we have to cut off the trailing slash that was added if * it's a dir, since AOS/VS doesn't accept that kind of thing) */ strncpy(znamebuf, z->name, $MXPL); znamebuf[$MXPL-1] = '\0'; if (znamebuf[strlen(znamebuf)-1] == '/') znamebuf[strlen(znamebuf)-1] = '\0'; if (linkput) errc = sys_fstat(znamebuf, BIT1, &(zzextrafld.fstat_packet)); else errc = sys_fstat(znamebuf, 0, &(zzextrafld.fstat_packet)); if (errc) { fprintf(stderr, "\n Warning: can't get ?FSTAT info & acl of %s - error %d\n ", znamebuf, errc); perror("sys_fstat()"); } else { /* store the ACL - or, if a link (no ACL!), store the resolution name */ if (zzextrafld.fstat_packet.norm_fstat_packet.styp_type != $FLNK) { if ((errc = sys_gacl(znamebuf, zzextrafld.aclbuf)) != 0) { fprintf(stderr, "\n Warning: can't get acl of %s - error %d\n ", z->name, errc); perror("sys_gacl()"); } else { /* find length of ACL - ends with double-null */ while (aclend++ < $MXACL && (zzextrafld.aclbuf[aclend - 1] != '\0' || zzextrafld.aclbuf[aclend] != '\0')) /* EMPTY LOOP */ ; if ((z->cextra = z->extra = malloc(sizeof(ZEXTRAFLD) - $MXACL + aclend + 4)) != NULL) { strncpy(zzextrafld.extra_header_id, ZEXTRA_HEADID, sizeof(zzextrafld.extra_header_id)); strncpy(zzextrafld.extra_sentinel, ZEXTRA_SENTINEL, sizeof(zzextrafld.extra_sentinel)); zzextrafld.extra_rev = ZEXTRA_REV; /* this is a char, no need to worry about byte order */ /* set size (Intel (little-endian)) 2-byte int, which we've set as array to make it easier */ errc = (unsigned short) (sizeof(ZEXTRAFLD) - $MXACL + aclend + 4 - sizeof(zzextrafld.extra_header_id) - sizeof(zzextrafld.extra_data_size)); zzextrafld.extra_data_size[0] = errc & 0xFF; /* low-order byte */ zzextrafld.extra_data_size[1] = errc >> 8; /* high-order byte */ memcpy((char *) z->extra, (char *) &zzextrafld, sizeof(ZEXTRAFLD) - $MXACL + aclend + 4); z->cext = z->ext = sizeof(ZEXTRAFLD) - $MXACL + aclend + 4; } } } else /* a link */ { if ((errc = sys_glink(z->name, zzextrafld.aclbuf)) != 0) { fprintf(stderr, "\n Warning: can't get link-resolution of %s - error %d\n ", z->name, errc); perror("sys_glink()"); } else { aclend = strlen(zzextrafld.aclbuf) + 1; if ((z->extra = malloc(sizeof(ZEXTRAFLD) - $MXACL + aclend + 4)) != NULL) { strncpy(zzextrafld.extra_header_id, ZEXTRA_HEADID, sizeof(zzextrafld.extra_header_id)); strncpy(zzextrafld.extra_sentinel, ZEXTRA_SENTINEL, sizeof(zzextrafld.extra_sentinel)); zzextrafld.extra_rev = ZEXTRA_REV; /* this is a char, no need to worry about byte order */ /* set size (Intel (little-endian)) 2-byte int, which we've set as array to make it easier */ errc = (unsigned short) (sizeof(ZEXTRAFLD) - $MXACL + aclend + 4 - sizeof(zzextrafld.extra_header_id) - sizeof(zzextrafld.extra_data_size)); zzextrafld.extra_data_size[0] = errc & 0xFF; /* low-order byte */ zzextrafld.extra_data_size[1] = errc >> 8; /* high-order byte */ memcpy((char *) z->extra, (char *) &zzextrafld, sizeof(ZEXTRAFLD) - $MXACL + aclend + 4); z->ext = sizeof(ZEXTRAFLD) - $MXACL + aclend + 4; } } } } return ZE_OK; } #endif /* !UTIL */ void version_local() { printf("Compiled with %s under %s.\n", "a C compiler", "AOS/VS" ); } /* * This file defines for AOS/VS two Unix functions relating to links; * the calling code should have the following defines: * * #define lstat(path,buf) zvs_lstat(path,buf) * #define readlink(path,buf,nbytes) zvs_readlink(path,buf,nbytes) * * For these functions, I'm going to define yet 2 MORE filename buffers * and also insert code to change pathnames to Unix & back. This is * easier than changing all the other places this kind of thing happens to * be efficient. This is a kludge. I'm also going to put the functions * here for my immediate convenience rather than somewhere else for * someone else's. * * WARNING: the use of static buffers means that you'd better get your * data out of these buffers before the next call to any of these functions! * */ /* ========================================================================= * ZVS_LSTAT() - get (or simulate) stat information WITHOUT following symlinks * This is intended to look to the outside like the unix lstat() * function. We do a quick-&-dirty filename conversion. * * If the file is NOT a symbolic link, we can just do a stat() on it and * that should be fine. But if it IS a link, we have to set the elements * of the stat struct ourselves, since AOS/VS doesn't have a built-in * lstat() function. * * RETURNS: 0 on success, or -1 otherwise * */ int zvs_lstat(char *path, struct stat *buf) { char *cp_vs = vsnamebuf; char *cp_ux = path; int mm, dd, yy; /* * Convert the Unix pathname to an AOS/VS pathname. * This is quick & dirty; it won't handle (for instance) pathnames with * ../ in the middle of them, and may choke on other Unixisms. We hope * they're unlikely. */ if (!strncmp(cp_ux, "../", 3)) { *cp_vs++ = '^'; /* AOS/VS for ../ */ cp_ux += 3; } else if (!strncmp(cp_ux, "./", 2)) { *cp_vs++ = '='; /* AOS/VS for ./ */ cp_ux += 2; } do { if (*cp_ux == '/') { *cp_vs++ = ':'; } else { *cp_vs++ = (char) toupper(*cp_ux); } } while (*cp_ux++ != '\0' && cp_vs - vsnamebuf < sizeof(vsnamebuf)); /* If Unix name was too long for our buffer, return an error return */ if (cp_vs - vsnamebuf >= sizeof(vsnamebuf) && *(cp_vs - 1) != '\0') return (-1); /* error */ /* Make AOS/VS ?FSTAT call that won't follow links & see if we find * anything. If not, we return error. */ if (sys_fstat(vsnamebuf, BIT1, /* BIT1 says to not resolve links */ &vsfstatbuf)) return (-1); /* error */ /* If we DID find the file but it's not a link, * call stat() and return its value. */ if (vsfstatbuf.styp_type != $FLNK) return (stat(path, buf)); /* call with Unix pathname ... */ /* Otherwise, we have to kludge up values for the stat structure */ memset((char *) buf, 0, sizeof(*buf)); /* init to nulls (0 values) */ buf->st_mode = S_IFLNK | 0777; /* link and rwxrwxrwx */ buf->st_uid = -1; /* this is what we get on AOS/VS anyway (maybe unless we set up a dummy password file?) */ buf->st_nlink = 1; /* The DG date we've got is days since 12/31/67 and seconds/2. So we * need to subtract 732 days (if that's not negative), convert to seconds, * and add adjusted seconds. */ if (vsfstatbuf.stch.short_time[0] < 732) buf->st_ctime = buf->st_mtime = buf->st_atime = 0L; else { buf->st_ctime = buf->st_mtime = buf->st_atime = ((long) vsfstatbuf.stch.short_time[0] - 732L) * 24L * 3600L + 2L * (long) vsfstatbuf.stch.short_time[1]; } /* And we need to get the filename linked to and use its length as * the file size. We'll use the Unix pathname buffer for this - hope * it's big enough. (We won't overwrite anything, but we could get a * truncated path.) If there's an error, here's our last chance to * say anything. */ if ((buf->st_size = zvs_readlink(vsnamebuf, uxnamebuf, FNMAX)) < 0) return (-1); else return (0); } /* end zvs_lstat() */ /* ========================================================================= * ZVS_READLINK() - get pathname pointed to by an AOS/VS link file * This is intended to look to the outside like the unix readlink() * function. We do a quick-&-dirty filename conversion. * * RETURNS: the length of the output path (in bytes), or -1 if an error * */ int zvs_readlink(char *path, char *buf, int nbytes) { char *cp_vs = vsnamebuf; char *cp_ux = buf; /* This is called with z->name, the filename the user gave, so we'll get * the link-resolution name on the assumption that it's a valid AOS/VS * name. We're also assuming a reasonable value (> 5) for nbytes. */ if (sys_glink(path, vsnamebuf)) return (-1); /* readlink() is supposed to return -1 on error */ /* Now, convert the AOS/VS pathname to a Unix pathname. * Note that sys_glink(), unlike readlink(), does add a null. */ if (*cp_vs == '^') /* AOS/VS for ../ */ { strncpy(cp_ux, "../", 3); cp_ux += 3; cp_vs++; } else if (*cp_vs == '@') /* AOS/VS for :PER:, kind of like /dev/ */ { strncpy(cp_ux, "/PER/", 5); cp_ux += 5; cp_vs++; } else if (*cp_vs == '=') /* AOS/VS for ./ */ { strncpy(cp_ux, "./", 2); cp_ux += 2; cp_vs++; } while (*cp_vs != '\0' && cp_ux - buf < nbytes) { if (*cp_vs == ':') { *cp_ux++ = '/'; } else { *cp_ux++ = (char) toupper(*cp_vs); } cp_vs++; } return (cp_ux - buf); /* # characters in Unix path (no trailing null) */ } /* end zvs_readlink() */ zip30/aosvs/make.cli0100644000076400000060000000027310550043046012521 0ustar ediskpush prompt pop sea :c_4.10 :c_4.10:lang_rt [!sea] cc%0/%/link/NOUNX AOS_VS/DEFINE NODIR/DEFINE .C pop zip30/api.c0100644000076400000060000005035410602141656010706 0ustar edisk/* api.c - Zip 3 Copyright (c) 1990-2007 Info-ZIP. All rights reserved. See the accompanying file LICENSE, version 2007-Mar-4 or later (the contents of which are also included in zip.h) for terms of use. If, for some reason, all these files are missing, the Info-ZIP license also may be found at: ftp://ftp.info-zip.org/pub/infozip/license.html */ /*--------------------------------------------------------------------------- api.c This module supplies a Zip dll engine for use directly from C/C++ programs. The entry points are: ZpVer *ZpVersion(void); int EXPENTRY ZpInit(LPZIPUSERFUNCTIONS lpZipUserFunc); int EXPENTRY ZpArchive(ZCL C, LPZPOPT Opts); This module is currently only used by the Windows dll, and is not used at all by any of the other platforms, although it should be easy enough to implement this on most platforms. ---------------------------------------------------------------------------*/ #define __API_C #include #ifdef WINDLL # include # include "windll/windll.h" #endif #ifdef OS2 # define INCL_DOSMEMMGR # include #endif #ifdef __BORLANDC__ #include #endif #include #include #include "api.h" /* this includes zip.h */ #include "crypt.h" #include "revision.h" #ifdef USE_ZLIB # include "zlib.h" #endif DLLPRNT *lpZipPrint; DLLPASSWORD *lpZipPassword; extern DLLCOMMENT *lpComment; ZIPUSERFUNCTIONS ZipUserFunctions, far * lpZipUserFunctions; int ZipRet; char szOrigDir[PATH_MAX]; BOOL fNo_int64 = FALSE; /* flag for DLLSERVICE_NO_INT64 */ /* Local forward declarations */ extern int zipmain OF((int, char **)); int AllocMemory(unsigned int, char *, char *, BOOL); int ParseString(LPSTR, unsigned int); void FreeArgVee(void); ZPOPT Options; char **argVee; unsigned int argCee; /*--------------------------------------------------------------------------- Local functions ---------------------------------------------------------------------------*/ char szRootDir[PATH_MAX], szExcludeList[PATH_MAX], szIncludeList[PATH_MAX], szTempDir[PATH_MAX]; int ParseString(LPSTR s, unsigned int ArgC) { unsigned int i; int root_flag, m, j; char *str1, *str2, *str3; size_t size; i = ArgC; str1 = (char *) malloc(lstrlen(s)+4); lstrcpy(str1, s); lstrcat(str1, " @"); if ((szRootDir != NULL) && (szRootDir[0] != '\0')) { root_flag = TRUE; if (szRootDir[lstrlen(szRootDir)-1] != '\\') lstrcat(szRootDir, "\\"); } else root_flag = FALSE; str2 = strchr(str1, '\"'); /* get first occurance of double quote */ while ((str3 = strchr(str1, '\t')) != NULL) { str3[0] = ' '; /* Change tabs into a single space */ } /* Note that if a quoted string contains multiple adjacent spaces, they will not be removed, because they could well point to a valid folder/file name. */ while ((str2 = strchr(str1, '\"')) != NULL) /* Found a double quote if not NULL */ { str3 = strchr(str2+1, '\"'); /* Get the second quote */ if (str3 == NULL) { free(str1); return ZE_PARMS; /* Something is screwy with the string, bail out */ } str3[0] = '\0'; /* terminate str2 with a NULL */ /* strip unwanted fully qualified path from entry */ if (root_flag) if ((_strnicmp(szRootDir, str2+1, lstrlen(szRootDir))) == 0) { m = 0; str2++; for (j = lstrlen(szRootDir); j < lstrlen(str2); j++) str2[m++] = str2[j]; str2[m] = '\0'; str2--; } size = _msize(argVee); if ((argVee = (char **)realloc(argVee, size + sizeof(char *))) == NULL) { fprintf(stdout, "Unable to allocate memory in zip dll\n"); return ZE_MEM; } /* argCee is incremented in AllocMemory */ if (AllocMemory(i, str2+1, "Creating file list from string", TRUE) != ZE_OK) { free(str1); return ZE_MEM; } i++; str3+=2; /* Point past the whitespace character */ str2[0] = '\0'; /* Terminate str1 */ lstrcat(str1, str3); } /* end while */ /* points to first occurance of a space */ str2 = strchr(str1, ' '); /* Go through the string character by character, looking for instances of two spaces together. Terminate when you find the trailing @ */ while ((str2[0] != '\0') && (str2[0] != '@')) { while ((str2[0] == ' ') && (str2[1] == ' ')) { str3 = &str2[1]; str2[0] = '\0'; lstrcat(str1, str3); } str2++; } /* Do we still have a leading space? */ if (str1[0] == ' ') { str3 = &str1[1]; lstrcpy(str1, str3); /* Dump the leading space */ } /* Okay, now we have gotten rid of any tabs and replaced them with spaces, and have replaced multiple spaces with a single space. We couldn't do this before because the folder names could have actually contained these characters. */ str2 = str3 = str1; while ((str2[0] != '\0') && (str3[0] != '@')) { str3 = strchr(str2+1, ' '); str3[0] = '\0'; /* strip unwanted fully qualified path from entry */ if (root_flag) if ((_strnicmp(szRootDir, str2, lstrlen(szRootDir))) == 0) { m = 0; for (j = lstrlen(Options.szRootDir); j < lstrlen(str2); j++) str2[m++] = str2[j]; str2[m] = '\0'; } size = _msize(argVee); if ((argVee = (char **)realloc(argVee, size + sizeof(char *))) == NULL) { fprintf(stdout, "Unable to allocate memory in zip dll\n"); return ZE_MEM; } if (AllocMemory(i, str2, "Creating file list from string", TRUE) != ZE_OK) { free(str1); return ZE_MEM; } i++; str3++; str2 = str3; } free(str1); return ZE_OK; } int AllocMemory(unsigned int i, char *cmd, char *str, BOOL IncrementArgCee) { if ((argVee[i] = (char *) malloc( sizeof(char) * strlen(cmd)+1 )) == NULL) { if (IncrementArgCee) argCee++; FreeArgVee(); fprintf(stdout, "Unable to allocate memory in zip library at %s\n", str); return ZE_MEM; } strcpy( argVee[i], cmd ); argCee++; return ZE_OK; } void FreeArgVee(void) { unsigned i; /* Free the arguments in the array */ for (i = 0; i < argCee; i++) { free (argVee[i]); argVee[i] = NULL; } /* Then free the array itself */ free(argVee); /* Restore the original working directory */ chdir(szOrigDir); #ifdef __BORLANDC__ setdisk(toupper(szOrigDir[0]) - 'A'); #endif } /*--------------------------------------------------------------------------- Documented API entry points ---------------------------------------------------------------------------*/ int EXPENTRY ZpInit(LPZIPUSERFUNCTIONS lpZipUserFunc) { ZipUserFunctions = *lpZipUserFunc; lpZipUserFunctions = &ZipUserFunctions; if (!lpZipUserFunctions->print || !lpZipUserFunctions->comment) return FALSE; return TRUE; } int EXPENTRY ZpArchive(ZCL C, LPZPOPT Opts) /* Add, update, freshen, or delete zip entries in a zip file. See the command help in help() zip.c */ { int k, j, m; size_t size; Options = *Opts; /* Save off options, and make them available locally */ szRootDir[0] = '\0'; szExcludeList[0] = '\0'; szIncludeList[0] = '\0'; szTempDir[0] = '\0'; if (Options.szRootDir) lstrcpy(szRootDir, Options.szRootDir); if (Options.szExcludeList) lstrcpy(szExcludeList, Options.szExcludeList); if (Options.szIncludeList) lstrcpy(szIncludeList, Options.szIncludeList); if (Options.szTempDir) lstrcpy(szTempDir, Options.szTempDir); getcwd(szOrigDir, PATH_MAX); /* Save current drive and directory */ if ((szRootDir != NULL) && (szRootDir[0] != '\0')) { /* Make sure there isn't a trailing slash */ if (szRootDir[lstrlen(szRootDir)-1] == '\\') szRootDir[lstrlen(szRootDir)-1] = '\0'; chdir(szRootDir); #ifdef __BORLANDC__ setdisk(toupper(szRootDir[0]) - 'A'); #endif } argCee = 0; /* malloc additional 40 to allow for additional command line arguments. Note that we are also adding in the count for the include lists as well as the exclude list. */ if ((argVee = (char **)malloc((C.argc+40)*sizeof(char *))) == NULL) { fprintf(stdout, "Unable to allocate memory in zip dll\n"); return ZE_MEM; } if ((argVee[argCee] = (char *) malloc( sizeof(char) * strlen("wiz.exe")+1 )) == NULL) { free(argVee); fprintf(stdout, "Unable to allocate memory in zip dll\n"); return ZE_MEM; } strcpy( argVee[argCee], "wiz.exe" ); argCee++; /* Set compression level efficacy -0...-9 */ if (AllocMemory(argCee, "-0", "Compression", FALSE) != ZE_OK) return ZE_MEM; /* Check to see if the compression level is set to a valid value. If not, then set it to the default. */ if ((Options.fLevel < '0') || (Options.fLevel > '9')) { Options.fLevel = '6'; if (!Options.fDeleteEntries) fprintf(stdout, "Compression level set to invalid value. Setting to default\n"); } argVee[argCee-1][1] = Options.fLevel; if (Options.fOffsets) /* Update offsets for SFX prefix */ { if (AllocMemory(argCee, "-A", "Offsets", FALSE) != ZE_OK) return ZE_MEM; } if (Options.fDeleteEntries) /* Delete files from zip file -d */ { if (AllocMemory(argCee, "-d", "Delete", FALSE) != ZE_OK) return ZE_MEM; } if (Options.fNoDirEntries) /* Do not add directory entries -D */ { if (AllocMemory(argCee, "-D", "No Dir Entries", FALSE) != ZE_OK) return ZE_MEM; } if (Options.fFreshen) /* Freshen zip file--overwrite only -f */ { if (AllocMemory(argCee, "-f", "Freshen", FALSE) != ZE_OK) return ZE_MEM; } if (Options.fRepair) /* Fix archive -F or -FF */ { if (Options.fRepair == 1) { if (AllocMemory(argCee, "-F", "Repair", FALSE) != ZE_OK) return ZE_MEM; } else { if (AllocMemory(argCee, "-FF", "Repair", FALSE) != ZE_OK) return ZE_MEM; } } if (Options.fGrow) /* Allow appending to a zip file -g */ { if (AllocMemory(argCee, "-g", "Appending", FALSE) != ZE_OK) return ZE_MEM; } if (Options.fJunkDir) /* Junk directory names -j */ { if (AllocMemory(argCee, "-j", "Junk Dir Names", FALSE) != ZE_OK) return ZE_MEM; } if (Options.fEncrypt) /* encrypt -e */ { if (AllocMemory(argCee, "-e", "Encrypt", FALSE) != ZE_OK) return ZE_MEM; } if (Options.fJunkSFX) /* Junk sfx prefix */ { if (AllocMemory(argCee, "-J", "Junk SFX", FALSE) != ZE_OK) return ZE_MEM; } if (Options.fForce) /* Make entries using DOS names (k for Katz) -k */ { if (AllocMemory(argCee, "-k", "Force DOS", FALSE) != ZE_OK) return ZE_MEM; } if (Options.fLF_CRLF) /* Translate LF_CRLF -l */ { if (AllocMemory(argCee, "-l", "LF-CRLF", FALSE) != ZE_OK) return ZE_MEM; } if (Options.fCRLF_LF) /* Translate CR/LF to LF -ll */ { if (AllocMemory(argCee, "-ll", "CRLF-LF", FALSE) != ZE_OK) return ZE_MEM; } if (Options.fMove) /* Delete files added to or updated in zip file -m */ { if (AllocMemory(argCee, "-m", "Move", FALSE) != ZE_OK) return ZE_MEM; } if (Options.fLatestTime) /* Set zip file time to time of latest file in it -o */ { if (AllocMemory(argCee, "-o", "Time", FALSE) != ZE_OK) return ZE_MEM; } if (Options.fComment) /* Add archive comment "-z" */ { if (AllocMemory(argCee, "-z", "Comment", FALSE) != ZE_OK) return ZE_MEM; } if (Options.fQuiet) /* quiet operation -q */ { if (AllocMemory(argCee, "-q", "Quiet", FALSE) != ZE_OK) return ZE_MEM; } if (Options.fRecurse == 1) /* recurse into subdirectories -r */ { if (AllocMemory(argCee, "-r", "Recurse -r", FALSE) != ZE_OK) return ZE_MEM; } else if (Options.fRecurse == 2) /* recurse into subdirectories -R */ { if (AllocMemory(argCee, "-R", "Recurse -R", FALSE) != ZE_OK) return ZE_MEM; } if (Options.fSystem) /* include system and hidden files -S */ { if (AllocMemory(argCee, "-S", "System", FALSE) != ZE_OK) return ZE_MEM; } if (Options.fExcludeDate) /* Exclude files newer than specified date -tt */ { if ((Options.Date != NULL) && (Options.Date[0] != '\0')) { if (AllocMemory(argCee, "-tt", "Date", FALSE) != ZE_OK) return ZE_MEM; if (AllocMemory(argCee, Options.Date, "Date", FALSE) != ZE_OK) return ZE_MEM; } } if (Options.fIncludeDate) /* include files newer than specified date -t */ { if ((Options.Date != NULL) && (Options.Date[0] != '\0')) { if (AllocMemory(argCee, "-t", "Date", FALSE) != ZE_OK) return ZE_MEM; if (AllocMemory(argCee, Options.Date, "Date", FALSE) != ZE_OK) return ZE_MEM; } } if (Options.fUpdate) /* Update zip file--overwrite only if newer -u */ { if (AllocMemory(argCee, "-u", "Update", FALSE) != ZE_OK) return ZE_MEM; } if (Options.fVerbose) /* Mention oddities in zip file structure -v */ { if (AllocMemory(argCee, "-v", "Verbose", FALSE) != ZE_OK) return ZE_MEM; } if (Options.fVolume) /* Include volume label -$ */ { if (AllocMemory(argCee, "-$", "Volume", FALSE) != ZE_OK) return ZE_MEM; } if (Options.szSplitSize != NULL) /* Turn on archive splitting */ { if (AllocMemory(argCee, "-s", "Splitting", FALSE) != ZE_OK) return ZE_MEM; if (AllocMemory(argCee, Options.szSplitSize, "Split size", FALSE) != ZE_OK) return ZE_MEM; } if (lpZipUserFunctions->split != NULL) /* Turn on archive split destinations select */ { if (AllocMemory(argCee, "-sp", "Split Pause Select Destination", FALSE) != ZE_OK) return ZE_MEM; } #ifdef WIN32 if (Options.fPrivilege) /* Use privileges -! */ { if (AllocMemory(argCee, "-!", "Privileges", FALSE) != ZE_OK) return ZE_MEM; } #endif if (Options.fExtra) /* Exclude extra attributes -X */ { if (AllocMemory(argCee, "-X", "Extra", FALSE) != ZE_OK) return ZE_MEM; } if (Options.IncludeList != NULL) /* Include file list -i */ { if (AllocMemory(argCee, "-i", "Include file list", FALSE) != ZE_OK) return ZE_MEM; k = 0; if (Options.IncludeListCount > 0) while ((Options.IncludeList[k] != NULL) && (Options.IncludeListCount != k+1)) { size = _msize(argVee); if ((argVee = (char **)realloc(argVee, size + sizeof(char *))) == NULL) { fprintf(stdout, "Unable to allocate memory in zip dll\n"); return ZE_MEM; } if (AllocMemory(argCee, Options.IncludeList[k], "Include file list array", TRUE) != ZE_OK) { return ZE_MEM; } k++; } else while (Options.IncludeList[k] != NULL) { size = _msize(argVee); if ((argVee = (char **)realloc(argVee, size + sizeof(char *))) == NULL) { FreeArgVee(); fprintf(stdout, "Unable to allocate memory in zip dll\n"); return ZE_MEM; } if (AllocMemory(argCee, Options.IncludeList[k], "Include file list array", TRUE) != ZE_OK) return ZE_MEM; k++; } if (AllocMemory(argCee, "@", "End of Include List", FALSE) != ZE_OK) return ZE_MEM; } if (Options.ExcludeList != NULL) /* Exclude file list -x */ { if (AllocMemory(argCee, "-x", "Exclude file list", FALSE) != ZE_OK) return ZE_MEM; k = 0; if (Options.ExcludeListCount > 0) while ((Options.ExcludeList[k] != NULL) && (Options.ExcludeListCount != k+1)) { size = _msize(argVee); if ((argVee = (char **)realloc(argVee, size + sizeof(char *))) == NULL) { fprintf(stdout, "Unable to allocate memory in zip dll\n"); return ZE_MEM; } if (AllocMemory(argCee, Options.ExcludeList[k], "Exclude file list array", TRUE) != ZE_OK) return ZE_MEM; k++; } else while (Options.ExcludeList[k] != NULL) { size = _msize(argVee); if ((argVee = (char **)realloc(argVee, size + sizeof(char *))) == NULL) { FreeArgVee(); fprintf(stdout, "Unable to allocate memory in zip dll\n"); return ZE_MEM; } if (AllocMemory(argCee, Options.ExcludeList[k], "Exclude file list array", TRUE) != ZE_OK) return ZE_MEM; k++; } if (AllocMemory(argCee, "@", "End of Exclude List", FALSE) != ZE_OK) return ZE_MEM; } if (szIncludeList != NULL && szIncludeList[0] != '\0') /* Include file list -i */ { if (AllocMemory(argCee, "-i", "Include file list", FALSE) != ZE_OK) return ZE_MEM; if ((k = ParseString(szIncludeList, argCee)) != ZE_OK) return k; /* Something was screwy with the parsed string bail out */ if (AllocMemory(argCee, "@", "End of Include List", FALSE) != ZE_OK) return ZE_MEM; } if (szExcludeList != NULL && szExcludeList[0] != '\0') /* Exclude file list -x */ { if (AllocMemory(argCee, "-x", "Exclude file list", FALSE) != ZE_OK) return ZE_MEM; if ((k = ParseString(szExcludeList, argCee)) != ZE_OK) return k; /* Something was screwy with the parsed string bail out */ if (AllocMemory(argCee, "@", "End of Exclude List", FALSE) != ZE_OK) return ZE_MEM; } if ((szTempDir != NULL) && (szTempDir[0] != '\0') && Options.fTemp) /* Use temporary directory -b */ { if (AllocMemory(argCee, "-b", "Temp dir switch command", FALSE) != ZE_OK) return ZE_MEM; if (AllocMemory(argCee, szTempDir, "Temporary directory", FALSE) != ZE_OK) return ZE_MEM; } if (AllocMemory(argCee, C.lpszZipFN, "Zip file name", FALSE) != ZE_OK) return ZE_MEM; if ((szRootDir != NULL) && (szRootDir[0] != '\0')) { if (szRootDir[lstrlen(szRootDir)-1] != '\\') lstrcat(szRootDir, "\\"); /* append trailing \\ */ if (C.FNV != NULL) { for (k = 0; k < C.argc; k++) { if (AllocMemory(argCee, C.FNV[k], "Making argv", FALSE) != ZE_OK) return ZE_MEM; if ((_strnicmp(szRootDir, C.FNV[k], lstrlen(szRootDir))) == 0) { m = 0; for (j = lstrlen(szRootDir); j < lstrlen(C.FNV[k]); j++) argVee[argCee-1][m++] = C.FNV[k][j]; argVee[argCee-1][m] = '\0'; } } } } else if (C.FNV != NULL) for (k = 0; k < C.argc; k++) { if (AllocMemory(argCee, C.FNV[k], "Making argv", FALSE) != ZE_OK) return ZE_MEM; } if (C.lpszAltFNL != NULL) { if ((k = ParseString(C.lpszAltFNL, argCee)) != ZE_OK) return k; /* Something was screwy with the parsed string bail out */ } argVee[argCee] = NULL; ZipRet = zipmain(argCee, argVee); /* Free the arguments in the array. Note this also restores the current directory */ FreeArgVee(); return ZipRet; } #if CRYPT int encr_passwd(int modeflag, char *pwbuf, int size, const char *zfn) { return (*lpZipUserFunctions->password)(pwbuf, size, ((modeflag == ZP_PW_VERIFY) ? "Verify password: " : "Enter password: "), (char *)zfn); } #endif /* CRYPT */ void EXPENTRY ZpVersion(ZpVer far * p) /* should be pointer to const struct */ { p->structlen = ZPVER_LEN; #ifdef BETA p->flag = 1; #else p->flag = 0; #endif #ifdef CRYPT p->fEncryption = TRUE; #else p->fEncryption = FALSE; #endif lstrcpy(p->betalevel, Z_BETALEVEL); lstrcpy(p->date, REVDATE); #ifdef ZLIB_VERSION lstrcpy(p->zlib_version, ZLIB_VERSION); p->flag |= 2; #else p->zlib_version[0] = '\0'; #endif #ifdef ZIP64_SUPPORT p->flag |= 4; /* Flag that ZIP64 was compiled in. */ #endif p->zip.major = Z_MAJORVER; p->zip.minor = Z_MINORVER; p->zip.patchlevel = Z_PATCHLEVEL; #ifdef OS2 p->os2dll.major = D2_MAJORVER; p->os2dll.minor = D2_MINORVER; p->os2dll.patchlevel = D2_PATCHLEVEL; #endif #ifdef WINDLL p->windll.major = DW_MAJORVER; p->windll.minor = DW_MINORVER; p->windll.patchlevel = DW_PATCHLEVEL; #endif } zip30/api.h0100644000076400000060000001564110626361650010717 0ustar edisk/* api.h - Zip 3 Copyright (c) 1990-2007 Info-ZIP. All rights reserved. See the accompanying file LICENSE, version 2007-Mar-4 or later (the contents of which are also included in zip.h) for terms of use. If, for some reason, all these files are missing, the Info-ZIP license also may be found at: ftp://ftp.info-zip.org/pub/infozip/license.html */ /* Only the Windows DLL is currently supported */ #ifndef _ZIPAPI_H #define _ZIPAPI_H #include "zip.h" #ifdef WIN32 # ifndef PATH_MAX # define PATH_MAX 260 # endif #else # ifndef PATH_MAX # define PATH_MAX 128 # endif #endif #if defined(WINDLL) || defined(API) #include /* Porting definations between Win 3.1x and Win32 */ #ifdef WIN32 # define far # define _far # define __far # define near # define _near # define __near #endif /*--------------------------------------------------------------------------- Prototypes for public Zip API (DLL) functions. ---------------------------------------------------------------------------*/ #define ZPVER_LEN sizeof(ZpVer) /* These defines are set to zero for now, until OS/2 comes out with a dll. */ #define D2_MAJORVER 0 #define D2_MINORVER 0 #define D2_PATCHLEVEL 0 /* intended to be a private struct: */ typedef struct _zip_ver { uch major; /* e.g., integer 5 */ uch minor; /* e.g., 2 */ uch patchlevel; /* e.g., 0 */ uch not_used; } _zip_version_type; typedef struct _ZpVer { ulg structlen; /* length of the struct being passed */ ulg flag; /* bit 0: is_beta bit 1: uses_zlib */ char betalevel[10]; /* e.g., "g BETA" or "" */ char date[20]; /* e.g., "4 Sep 95" (beta) or "4 September 1995" */ char zlib_version[10]; /* e.g., "0.95" or NULL */ BOOL fEncryption; /* TRUE if encryption enabled, FALSE otherwise */ _zip_version_type zip; _zip_version_type os2dll; _zip_version_type windll; } ZpVer; # ifndef EXPENTRY # define EXPENTRY WINAPI # endif #ifndef DEFINED_ONCE #define DEFINED_ONCE typedef int (WINAPI DLLPRNT) (LPSTR, unsigned long); typedef int (WINAPI DLLPASSWORD) (LPSTR, int, LPCSTR, LPCSTR); #endif #ifdef ZIP64_SUPPORT typedef int (WINAPI DLLSERVICE) (LPCSTR, unsigned __int64); typedef int (WINAPI DLLSERVICE_NO_INT64) (LPCSTR, unsigned long, unsigned long); #else typedef int (WINAPI DLLSERVICE) (LPCSTR, unsigned long); #endif typedef int (WINAPI DLLSPLIT) (LPSTR); typedef int (WINAPI DLLCOMMENT)(LPSTR); /* Structures */ typedef struct { /* zip options */ LPSTR Date; /* Date to include after */ LPSTR szRootDir; /* Directory to use as base for zipping */ LPSTR szTempDir; /* Temporary directory used during zipping */ BOOL fTemp; /* Use temporary directory '-b' during zipping */ BOOL fSuffix; /* include suffixes (not implemented) */ BOOL fEncrypt; /* encrypt files */ BOOL fSystem; /* include system and hidden files */ BOOL fVolume; /* Include volume label */ BOOL fExtra; /* Exclude extra attributes */ BOOL fNoDirEntries; /* Do not add directory entries */ BOOL fExcludeDate; /* Exclude files newer than specified date */ BOOL fIncludeDate; /* Include only files newer than specified date */ BOOL fVerbose; /* Mention oddities in zip file structure */ BOOL fQuiet; /* Quiet operation */ BOOL fCRLF_LF; /* Translate CR/LF to LF */ BOOL fLF_CRLF; /* Translate LF to CR/LF */ BOOL fJunkDir; /* Junk directory names */ BOOL fGrow; /* Allow appending to a zip file */ BOOL fForce; /* Make entries using DOS names (k for Katz) */ BOOL fMove; /* Delete files added or updated in zip file */ BOOL fDeleteEntries; /* Delete files from zip file */ BOOL fUpdate; /* Update zip file--overwrite only if newer */ BOOL fFreshen; /* Freshen zip file--overwrite only */ BOOL fJunkSFX; /* Junk SFX prefix */ BOOL fLatestTime; /* Set zip file time to time of latest file in it */ BOOL fComment; /* Put comment in zip file */ BOOL fOffsets; /* Update archive offsets for SFX files */ BOOL fPrivilege; /* Use privileges (WIN32 only) */ BOOL fEncryption; /* TRUE if encryption supported, else FALSE. this is a read only flag */ LPSTR szSplitSize; /* This string contains the size that you want to split the archive into. i.e. 100 for 100 bytes, 2K for 2 k bytes, where K is 1024, m for meg and g for gig. If this string is not NULL it will automatically be assumed that you wish to split an archive. */ LPSTR szIncludeList; /* Pointer to include file list string (for VB) */ long IncludeListCount; /* Count of file names in the include list array */ char **IncludeList; /* Pointer to include file list array. Note that the last entry in the array must be NULL */ LPSTR szExcludeList; /* Pointer to exclude file list (for VB) */ long ExcludeListCount; /* Count of file names in the include list array */ char **ExcludeList; /* Pointer to exclude file list array. Note that the last entry in the array must be NULL */ int fRecurse; /* Recurse into subdirectories. 1 => -r, 2 => -R */ int fRepair; /* Repair archive. 1 => -F, 2 => -FF */ char fLevel; /* Compression level (0 - 9) */ } ZPOPT, _far *LPZPOPT; typedef struct { int argc; /* Count of files to zip */ LPSTR lpszZipFN; /* name of archive to create/update */ char **FNV; /* array of file names to zip up */ LPSTR lpszAltFNL; /* pointer to a string containing a list of file names to zip up, separated by whitespace. Intended for use only by VB users, all others should set this to NULL. */ } ZCL, _far *LPZCL; typedef struct { DLLPRNT *print; DLLCOMMENT *comment; DLLPASSWORD *password; DLLSPLIT *split; /* This MUST be set to NULL unless you want to be queried for a destination for each split archive. */ #ifdef ZIP64_SUPPORT DLLSERVICE *ServiceApplication64; DLLSERVICE_NO_INT64 *ServiceApplication64_No_Int64; #else DLLSERVICE *ServiceApplication; #endif } ZIPUSERFUNCTIONS, far * LPZIPUSERFUNCTIONS; extern LPZIPUSERFUNCTIONS lpZipUserFunctions; void EXPENTRY ZpVersion(ZpVer far *); int EXPENTRY ZpInit(LPZIPUSERFUNCTIONS lpZipUserFunc); int EXPENTRY ZpArchive(ZCL C, LPZPOPT Opts); #if defined(ZIPLIB) || defined(COM_OBJECT) # define ydays zp_ydays #endif /* Functions not yet supported */ #if 0 int EXPENTRY ZpMain (int argc, char **argv); int EXPENTRY ZpAltMain (int argc, char **argv, ZpInit *init); #endif #endif /* WINDLL? || API? */ #endif /* _ZIPAPI_H */ zip30/atari/0040755000076400000060000000000011033727770011073 5ustar ediskzip30/atari/atari.c0100644000076400000060000004474410154331670012342 0ustar edisk/* Copyright (c) 1990-1999 Info-ZIP. All rights reserved. See the accompanying file LICENSE, version 1999-Oct-05 or later (the contents of which are also included in zip.h) for terms of use. If, for some reason, both of these files are missing, the Info-ZIP license also may be found at: ftp://ftp.cdrom.com/pub/infozip/license.html */ #include "zip.h" #ifndef UTIL /* the companion #endif is a bit of ways down ... */ #include #include #include #include #include #include #define PAD 0 #define PATH_END '/' extern char *label; /* defined in fileio.c */ local ulg label_time = 0; local ulg label_mode = 0; local time_t label_utim = 0; local char *readd(d) DIR *d; /* directory stream to read from */ /* Return a pointer to the next name in the directory stream d, or NULL if no more entries or an error occurs. */ { struct dirent *e; e = readdir(d); return e == NULL ? (char *) NULL : e->d_name; } local char *getVolumeLabel(drive, vtime, vmode, utim) int drive; /* drive name: 'A' .. 'Z' or '\0' for current drive */ ulg *vtime; /* volume label creation time (DOS format) */ ulg *vmode; /* volume label file mode */ time_t utim;/* volume label creation time (UNIX format) */ /* If a volume label exists for the given drive, return its name and set its time and mode. The returned name must be static data. */ { static char vol[14]; _DTA *dtaptr; if (drive) { vol[0] = (char)drive; strcpy(vol+1, ":/"); } else { strcpy(vol, "/"); } strcat(vol, "*.*"); if (Fsfirst(vol, FA_LABEL) == 0) { dtaptr = Fgetdta(); strncpy(vol, dtaptr->dta_name, sizeof(vol)-1); *vtime = ((ulg)dtaptr->dta_date << 16) | ((ulg)dtaptr->dta_time & 0xffff); *vmode = (ulg)dtaptr->dta_attribute; return vol; } return NULL; } char GetFileMode(char *name) { struct stat sb; sb.st_attr = 0; Fxattr(linkput ? 1 : 0, name, &sb); if (errno == EINVAL) { _DTA *dtaptr, *old; old = Fgetdta(); Fsfirst(name, FA_RDONLY+FA_HIDDEN+FA_SYSTEM+FA_DIR); dtaptr = Fgetdta(); sb.st_attr = dtaptr->dta_attribute; Fsetdta(old); } return sb.st_attr & 0x3f; } int wild2(w) char *w; /* path/pattern to match */ /* If not in exclude mode, expand the pattern based on the contents of the file system. Return an error code in the ZE_ class. */ { DIR *d; /* stream for reading directory */ char *e; /* name found in directory */ int r; /* temporary variable */ char *n; /* constructed name from directory */ int f; /* true if there was a match */ char *a; /* alloc'ed space for name */ char *p; /* path */ char *q; /* name */ char v[5]; /* space for device current directory */ if (volume_label == 1) { volume_label = 2; label = getVolumeLabel(w[1] == ':' ? to_up(w[0]) : '\0', &label_time, &label_mode, &label_utim); if (label != NULL) { newname(label, 0, 0); } if (w[1] == ':' && w[2] == '\0') return ZE_OK; /* "zip -$ foo a:" can be used to force drive name */ } /* special handling of stdin request */ if (strcmp(w, "-") == 0) /* if compressing stdin */ return newname(w, 0, 0); /* Allocate and copy pattern */ if ((p = a = malloc(strlen(w) + 1)) == NULL) return ZE_MEM; strcpy(p, w); /* Normalize path delimiter as '/'. */ for (q = p; *q; q++) /* use / consistently */ if (*q == '\\') *q = '/'; /* Only name can have special matching characters */ if ((q = isshexp(p)) != NULL && (strrchr(q, '/') != NULL || strrchr(q, ':') != NULL)) { free((zvoid *)a); return ZE_PARMS; } /* Separate path and name into p and q */ if ((q = strrchr(p, '/')) != NULL && (q == p || q[-1] != ':')) { *q++ = '\0'; /* path/name -> path, name */ if (*p == '\0') /* path is just / */ p = strcpy(v, "/."); } else if ((q = strrchr(p, ':')) != NULL) { /* has device and no or root path */ *q++ = '\0'; p = strcat(strcpy(v, p), ":"); /* copy device as path */ if (*q == '/') /* -> device:/., name */ { strcat(p, "/"); q++; } strcat(p, "."); } else if (recurse && (strcmp(p, ".") == 0 || strcmp(p, "..") == 0)) { /* current or parent directory */ /* I can't understand Mark's code so I am adding a hack here to get * "zip -r foo ." to work. Allow the dubious "zip -r foo .." but * reject "zip -rm foo ..". */ if (dispose && strcmp(p, "..") == 0) ziperr(ZE_PARMS, "cannot remove parent directory"); q = "*.*"; } else /* no path or device */ { q = p; p = strcpy(v, "."); } if (recurse && *q == '\0') { q = "*.*"; } /* Search that level for matching names */ if ((d = opendir(p)) == NULL) { free((zvoid *)a); return ZE_MISS; } if ((r = strlen(p)) > 1 && (strcmp(p + r - 2, ":.") == 0 || strcmp(p + r - 2, "/.") == 0)) *(p + r - 1) = '\0'; f = 0; while ((e = readd(d)) != NULL) { if (strcmp(e, ".") && strcmp(e, "..") && MATCH(q, e, 0)) { f = 1; if (strcmp(p, ".") == 0) { /* path is . */ r = procname(e, 0); /* name is name */ if (r) { f = 0; break; } } else { if ((n = malloc(strlen(p) + strlen(e) + 2)) == NULL) { free((zvoid *)a); closedir(d); return ZE_MEM; } n = strcpy(n, p); if (n[r = strlen(n) - 1] != '/' && n[r] != ':') strcat(n, "/"); r = procname(strcat(n, e), 0); /* name is path/name */ free((zvoid *)n); if (r) { f = 0; break; } } } } closedir(d); /* Done */ free((zvoid *)a); return f ? ZE_OK : ZE_MISS; } #include #include void regerror( char ZCONST *msg ) { perror( msg ); } static int ret; static regexp *regptr; static short is_w, ind_w; static char fullpath[FILENAME_MAX], file_arg[FILENAME_MAX]; #define FTW_F 0 #define FTW_D 1 #define FTW_DNR 2 #define FTW_NS 3 static int ftwfunc( struct stat *stats, int ftw_status ) { char *path = &fullpath[0]; if (strncmp(path, "./", 2) == 0) path += 2; switch (ftw_status) { case FTW_NS: zipwarn("can't stat file: ", path); ret = ZE_MISS; return 0; case FTW_F: if (!is_w || regexec(regptr, path, 1)) { #if 0 char fn[FILENAME_MAX]; int k; if (S_ISLNK(stats->st_mode) && (k = readlink(path, fn, FILENAME_MAX)) > 0) { int l = strlen(path); fn[k] = '\0'; strcat(strcat(path, " -> "), fn); ret = newname(path, 0, 0); /* procname(path, 0); */ path[l] = '\0'; } else #endif ret = newname(path, 0, 0); /* procname(path, 0); */ } return 0; case FTW_DNR: zipwarn("can't open directory: ", path); ret = ZE_MISS; return 0; case FTW_D: if (strcmp(path, ".") == 0) return 0; if (is_w && ind_w > 0 && strncmp(path, file_arg, ind_w) != 0) return 4; } return 0; } static int myftw( int depth ) { register DIR *dirp; struct dirent *entp; struct stat stats; register char *p,*q; register long i; if (LSSTAT(fullpath, &stats) < 0) return ftwfunc(&stats, FTW_NS); if (!S_ISDIR(stats.st_mode)) return ftwfunc(&stats, FTW_F); if ((dirp = opendir(fullpath)) == NULL) return ftwfunc(&stats, FTW_DNR); if (i = ftwfunc(&stats, FTW_D)) { closedir(dirp); return (i == 4 ? 0 : (int)i); } i = strlen(fullpath); p = &fullpath[i]; *p++ = '/'; *p = '\0'; if (dirnames && i > 1) { q = (strncmp(fullpath, "./", 2) == 0 ? &fullpath[2] : &fullpath[0]); ret = newname(q, 1, 0); } i = 0; while (depth > 0 && (entp = readdir(dirp)) != 0) if (strcmp(entp->d_name,".") != 0 && strcmp(entp->d_name,"..") != 0) { strcpy(p, entp->d_name); if (i = myftw(depth-1)) depth = 0; /* force User's finish */ } closedir(dirp); return (int)i; } int wild( char *p ) { char *d; ret = ZE_OK; if (p == NULL) p = "*"; if (strcmp(p, "-") == 0) /* if compressing stdin */ ret = newname(p, 0, 0); strcpy(fullpath, p); /* now turning UNIX-Wildcards into basic regular expressions */ for (is_w = ind_w = 0, d = &file_arg[0]; *p; d++, p++) switch (*p) { case '*': *d++ = '.'; *d = *p; is_w = 1; break; case '?': *d = '.'; is_w = 1; break; case '[': *d = *p; if (*(p+1) == '!') { *++d = '^'; p++; } is_w = 1; break; case '.': *d++ = '\\'; *d = *p; break; default : *d = *p; if (!is_w) ind_w++; } *++d = '\0'; if (is_w) { strcat( file_arg, "$" ); /* to get things like *.[ch] work */ if ((regptr = regcomp( file_arg )) == NULL) return ZE_MEM; strcpy( fullpath, "." ); myftw( recurse ? 99 : 1 ); free(regptr); } else if (recurse) { myftw( 99 ); } else myftw( 1 ); /* ret = procname( fullpath, 0 ); */ return ret; } int procname(n, caseflag) char *n; /* name to process */ int caseflag; /* true to force case-sensitive match */ /* Process a name or sh expression to operate on (or exclude). Return an error code in the ZE_ class. */ { char *a; /* path and name for recursion */ DIR *d; /* directory stream from opendir() */ char *e; /* pointer to name from readd() */ int m; /* matched flag */ char *p; /* path for recursion */ struct stat s; /* result of stat() */ struct zlist far *z; /* steps through zfiles list */ if (strcmp(n, "-") == 0) /* if compressing stdin */ return newname(n, 0, caseflag); else if (LSSTAT(n, &s)) { /* Not a file or directory--search for shell expression in zip file */ p = ex2in(n, 0, (int *)NULL); /* shouldn't affect matching chars */ m = 1; for (z = zfiles; z != NULL; z = z->nxt) { if (MATCH(p, z->iname, caseflag)) { z->mark = pcount ? filter(z->zname, caseflag) : 1; if (verbose) fprintf(mesg, "zip diagnostic: %scluding %s\n", z->mark ? "in" : "ex", z->name); m = 0; } } free((zvoid *)p); return m ? ZE_MISS : ZE_OK; } /* Live name--use if file, recurse if directory */ for (p = n; *p; p++) /* use / consistently */ if (*p == '\\') *p = '/'; if (!S_ISDIR(s.st_mode)) { /* add or remove name of file */ if ((m = newname(n, 0, caseflag)) != ZE_OK) return m; } else { /* Add trailing / to the directory name */ if ((p = malloc(strlen(n)+2)) == NULL) return ZE_MEM; if (strcmp(n, ".") == 0) { *p = '\0'; /* avoid "./" prefix and do not create zip entry */ } else { strcpy(p, n); a = p + strlen(p); if (a[-1] != '/') strcpy(a, "/"); if (dirnames && (m = newname(p, 1, caseflag)) != ZE_OK) { free((zvoid *)p); return m; } } /* recurse into directory */ if (recurse && (d = opendir(n)) != NULL) { while ((e = readd(d)) != NULL) { if (strcmp(e, ".") && strcmp(e, "..")) { if ((a = malloc(strlen(p) + strlen(e) + 1)) == NULL) { closedir(d); free((zvoid *)p); return ZE_MEM; } strcat(strcpy(a, p), e); if ((m = procname(a, caseflag)) != ZE_OK) /* recurse on name */ { if (m == ZE_MISS) zipwarn("name not matched: ", a); else ziperr(m, a); } free((zvoid *)a); } } closedir(d); } free((zvoid *)p); } /* (s.st_mode & S_IFDIR) == 0) */ return ZE_OK; } char *ex2in(x, isdir, pdosflag) char *x; /* external file name */ int isdir; /* input: x is a directory */ int *pdosflag; /* output: force MSDOS file attributes? */ /* Convert the external file name to a zip file name, returning the malloc'ed string or NULL if not enough memory. */ { char *n; /* internal file name (malloc'ed) */ char *t, *p; /* shortened name */ int dosflag; dosflag = 0; /* Find starting point in name before doing malloc */ t = *x && *(x + 1) == ':' ? x + 2 : x; while (*t == '/' || *t == '\\') t++; /* Make changes, if any, to the copied name (leave original intact) */ for (n = t; *n; n++) if (*n == '\\') *n = '/'; if (!pathput) t = last(t, PATH_END); /* Malloc space for internal name and copy it */ if ((n = malloc(strlen(t) + 1)) == NULL) return NULL; strcpy(n, t); #if 0 if (p = strstr(t, " -> ")) /* shorten "link -> data" to "link" */ *p = '\0'; #endif if (dosify) msname(n); /* Returned malloc'ed name */ if (pdosflag) *pdosflag = dosflag; return n; } char *in2ex(n) char *n; /* internal file name */ /* Convert the zip file name to an external file name, returning the malloc'ed string or NULL if not enough memory. */ { char *x; /* external file name */ if ((x = malloc(strlen(n) + 1 + PAD)) == NULL) return NULL; strcpy(x, n); return x; } void stamp(f, d) char *f; /* name of file to change */ ulg d; /* dos-style time to change it to */ /* Set last updated and accessed time of file f to the DOS time d. */ { struct utimbuf u; /* argument for utime() const ?? */ /* Convert DOS time to time_t format in u[0] and u[1] */ u.actime = u.modtime = dos2unixtime(d); /* Set updated and accessed times of f */ utime(f, &u); } ulg filetime(f, a, n, t) char *f; /* name of file to get info on */ ulg *a; /* return value: file attributes */ long *n; /* return value: file size */ iztimes *t; /* return value: access, modific. and creation times */ /* If file *f does not exist, return 0. Else, return the file's last modified date and time as an MSDOS date and time. The date and time is returned in a long with the date most significant to allow unsigned integer comparison of absolute times. Also, if a is not a NULL pointer, store the file attributes there, with the high two bytes being the Unix attributes, and the low byte being a mapping of that to DOS attributes. If n is not NULL, store the file size there. If t is not NULL, the file's access, modification and creation times are stored there as UNIX time_t values. If f is "-", use standard input as the file. If f is a device, return a file size of -1 */ { struct stat s; /* results of stat() */ /* convert FNMAX to malloc - 11/8/04 EG */ char *name; int len = strlen(f); if (f == label) { if (a != NULL) *a = label_mode; if (n != NULL) *n = -2L; /* convention for a label name */ if (t != NULL) t->atime = t->mtime = t->ctime = label_utim; return label_time; } if ((name = malloc(len + 1)) == NULL) { ZIPERR(ZE_MEM, "filetime"); } strcpy(name, f); if (name[len - 1] == '/') name[len - 1] = '\0'; /* not all systems allow stat'ing a file with / appended */ if (strcmp(f, "-") == 0) { if (fstat(fileno(stdin), &s) != 0) { free(name); error("fstat(stdin)"); } } else if (LSSTAT(name, &s) != 0) { /* Accept about any file kind including directories * (stored with trailing / with -r option) */ free(name); return 0; } if (a != NULL) { /* *a = ((ulg)s.st_mode << 16) | (ulg)GetFileMode(name); */ *a = ((ulg)s.st_mode << 16) | (ulg)s.st_attr; } free(name); if (n != NULL) *n = S_ISREG(s.st_mode) ? s.st_size : -1L; if (t != NULL) { t->atime = s.st_atime; t->mtime = s.st_mtime; t->ctime = s.st_ctime; } return unix2dostime(&s.st_mtime); } int set_extra_field(z, z_utim) struct zlist far *z; iztimes *z_utim; /* create extra field and change z->att if desired */ { #ifdef USE_EF_UT_TIME #ifdef IZ_CHECK_TZ if (!zp_tz_is_valid) return ZE_OK; /* skip silently if no valid TZ info */ #endif if ((z->extra = (char *)malloc(EB_HEADSIZE+EB_UT_LEN(2))) == NULL) return ZE_MEM; if ((z->cextra = (char *)malloc(EB_HEADSIZE+EB_UT_LEN(1))) == NULL) return ZE_MEM; z->extra[0] = 'U'; z->extra[1] = 'T'; z->extra[2] = EB_UT_LEN(2); /* length of data part of e.f. */ z->extra[3] = 0; z->extra[4] = EB_UT_FL_MTIME | EB_UT_FL_ATIME; z->extra[5] = (char)(z_utim->mtime); z->extra[6] = (char)(z_utim->mtime >> 8); z->extra[7] = (char)(z_utim->mtime >> 16); z->extra[8] = (char)(z_utim->mtime >> 24); z->extra[9] = (char)(z_utim->atime); z->extra[10] = (char)(z_utim->atime >> 8); z->extra[11] = (char)(z_utim->atime >> 16); z->extra[12] = (char)(z_utim->atime >> 24); z->ext = (EB_HEADSIZE+EB_UX_LEN(2)); memcpy(z->cextra, z->extra, (EB_HEADSIZE+EB_UT_LEN(1))); z->cextra[EB_LEN] = EB_UT_LEN(1); z->cext = (EB_HEADSIZE+EB_UX_LEN(1)); return ZE_OK; #else /* !USE_EF_UT_TIME */ return (int)(z-z); #endif /* ?USE_EF_UT_TIME */ } int deletedir(d) char *d; /* directory to delete */ /* Delete the directory *d if it is empty, do nothing otherwise. Return the result of rmdir(), delete(), or system(). For VMS, d must be in format [x.y]z.dir;1 (not [x.y.z]). */ { return rmdir(d); } #endif /* !UTIL */ /******************************/ /* Function version_local() */ /******************************/ void version_local() { static ZCONST char CompiledWith[] = "Compiled with %s%s for %s%s%s%s.\n\n"; #ifdef __TURBOC__ char buf[40]; #endif printf(CompiledWith, #ifdef __GNUC__ "gcc ", __VERSION__, #else # if 0 "cc ", (sprintf(buf, " version %d", _RELEASE), buf), # else # ifdef __TURBOC__ "Turbo C", (sprintf(buf, " (0x%04x = %d)", __TURBOC__, __TURBOC__), buf), # else "unknown compiler", "", # endif # endif #endif #ifdef __MINT__ "Atari TOS/MiNT", #else "Atari TOS", #endif " (Atari ST/TT/Falcon030)", #ifdef __DATE__ " on ", __DATE__ #else "", "" #endif ); } /* end function version_local() */ zip30/atari/Makefile0100644000076400000060000000533410550050534012523 0ustar edisk# Makefile for Zip, ZipNote, ZipCloak and ZipSplit MAKE = make SHELL = /bin/sh # (to use the Gnu compiler, change cc to gcc in CC and BIND) CC = cc BIND = $(CC) AS = $(CC) -c E = CPP = /lib/cpp # probably can change this to 'install' if you have it INSTALL = cp # target directories - where to install executables and man pages to BINDIR = /usr/local/bin manext=1 MANDIR = /usr/local/man/man$(manext) # flags # CFLAGS flags for C compile # LFLAGS1 flags after output file spec, before obj file list # LFLAGS2 flags after obj file list (libraries, etc) CFLAGS = -O LFLAGS1 = LFLAGS2 = -s # object file lists OBJZ = zip.o zipfile.o zipup.o fileio.o util.o crc32.o globals.o \ crypt.o ttyio.o atari.o OBJI = deflate.o trees.o OBJA = OBJU = zipfile_.o fileio_.o util_.o globals.o atari_.o OBJN = zipnote.o $(OBJU) OBJC = zipcloak.o $(OBJU) crc32_.o crypt_.o ttyio.o OBJS = zipsplit.o $(OBJU) ZIP_H = zip.h ziperr.h tailor.h atari/osdep.h # suffix rules .SUFFIXES: .SUFFIXES: _.o .o .c .doc .1 .c_.o: rm -f $*_.c; ln $< $*_.c $(CC) $(CFLAGS) -DUTIL -c $*_.c rm -f $*_.c .c.o: $(CC) $(CFLAGS) -c $< .1.doc: nroff -man $< | col -b | uniq > $@ # rules for zip, zipnote, zipcloak, zipsplit, and the Zip MANUAL. $(OBJZ): $(ZIP_H) $(OBJI): $(ZIP_H) $(OBJN): $(ZIP_H) $(OBJS): $(ZIP_H) $(OBJC): $(ZIP_H) zip.o crc32.o crypt.o fileio.o zipfile.o zipup.o: crc32.h zipcloak.o crc32_.o crypt_.o fileio_.o zipfile_.o: crc32.h zip.o zipup.o crypt.o ttyio.o zipcloak.o crypt_.o: crypt.h zip.o zipup.o zipnote.o zipcloak.o zipsplit.o: revision.h zip.o crypt.o ttyio.o zipcloak.o crypt_.o: ttyio.h zipup.o: atari/zipup.h match.o: match.s $(CPP) match.s > _match.s $(AS) _match.s mv _match.o match.o rm -f _match.s ZIPS = zip$E zipnote$E zipsplit$E zipcloak$E zips: $(ZIPS) zipsman: $(ZIPS) $(ZIPMANUAL) zip$E: $(OBJZ) $(OBJI) $(OBJA) $(BIND) -o zip$E $(LFLAGS1) $(OBJZ) $(OBJI) $(OBJA) $(LFLAGS2) zipnote$E: $(OBJN) $(BIND) -o zipnote$E $(LFLAGS1) $(OBJN) $(LFLAGS2) zipcloak$E: $(OBJC) $(BIND) -o zipcloak$E $(LFLAGS1) $(OBJC) $(LFLAGS2) zipsplit$E: $(OBJS) $(BIND) -o zipsplit$E $(LFLAGS1) $(OBJS) $(LFLAGS2) $(ZIPMANUAL): man/zip.1 nroff -man man/zip.1 | col -b | uniq > $(ZIPMANUAL) # install install: $(ZIPS) $(INSTALL) $(ZIPS) $(BINDIR) $(INSTALL) man/zip.1 $(MANDIR)/zip.$(manext) uninstall: -cd $(BINDIR); rm -f $(ZIPS) -cd $(MANDIR); rm -f zip.$(manext) dist: $(ZIPMANUAL) zip -u9T zip`sed -e '/VERSION/!d' -e 's/.*"\(.*\)".*/\1/' \ -e s/[.]//g -e q revision.h` \ `awk '/^Makefile/,/vms_zip.rnh/ {print $$1}' < contents` # ATARI version (gcc 2.5.8 and Mintlibs PL46) atari: $(MAKE) zips CFLAGS="-O -DATARI" OBJA=atari/atari.o CC=gcc E=.ttp # clean up after making stuff and installing it clean: rm -f *.o $(ZIPS) flags zip30/atari/make_all.mup0100644000076400000060000000073206254362762013367 0ustar ediskrm -f *.o *.sym *.ttp make370 SHELL=/bin/mupfel.ttp CC=gcc CFLAGS="-O -DATARI" E=.ttp OBJA=atari.o zips #make370 SHELL=/bin/mupfel.ttp CC=gcc CFLAGS="-g -D__NO_INLINE__ -DATARI" E=.ttp OBJA=atari.o zip.ttp #make370 SHELL=/bin/mupfel.ttp CC=gcc CFLAGS="-g -D__NO_INLINE__ -DATARI" E=.sym OBJA=atari.o zip.sym LFLAGS2="-B/bin/sym-" #make370 SHELL=/bin/mupfel.ttp CC=gcc CFLAGS="-O -DATARI" E=.ttp OBJA=atari.o -n zips > make_all.mup #fixstk 32K pgp.ttp prgflags 017 007 *.ttp zip30/atari/make_zip.mup0100644000076400000060000000073206254362762013421 0ustar edisk#rm -f *.o *.sym *.ttp #make370 SHELL=/bin/mupfel.ttp CC=gcc CFLAGS="-O -DATARI" E=.ttp OBJA=atari.o zips make370 SHELL=/bin/mupfel.ttp CC=gcc CFLAGS="-g -D__NO_INLINE__ -DATARI" E=.ttp OBJA=atari.o zip.ttp make370 SHELL=/bin/mupfel.ttp CC=gcc CFLAGS="-g -D__NO_INLINE__ -DATARI" E=.sym OBJA=atari.o zip.sym LFLAGS2="-B/bin/sym-" #make370 SHELL=/bin/mupfel.ttp CC=gcc CFLAGS="-O -DATARI" E=.ttp OBJA=atari.o -n zips > make_all.mup #fixstk 32K pgp.ttp prgflags 017 007 *.ttp zip30/atari/osdep.h0100644000076400000060000000114307011110536012335 0ustar edisk/* Copyright (c) 1990-1999 Info-ZIP. All rights reserved. See the accompanying file LICENSE, version 1999-Oct-05 or later (the contents of which are also included in zip.h) for terms of use. If, for some reason, both of these files are missing, the Info-ZIP license also may be found at: ftp://ftp.cdrom.com/pub/infozip/license.html */ #define FOPR "rb" #define FOPM "r+b" #define FOPW "wb" #define DIRENT #define NO_TERMIO #define USE_CASE_MAP #define PROCNAME(n) (action == ADD || action == UPDATE ? wild(n) : \ procname(n, 1)) #include #include zip30/atari/README0100644000076400000060000000027006254362762011754 0ustar ediskFrom: harry@hal.westfalen.de (Harald Denker) The old zip ATARI port is based on TurboC which is no more supported (for more than 3 years). I used the GNU gcc 2.5.8 and MiNTlibs PL46. zip30/atari/zipup.h0100644000076400000060000000112407011110546012372 0ustar edisk/* Copyright (c) 1990-1999 Info-ZIP. All rights reserved. See the accompanying file LICENSE, version 1999-Oct-05 or later (the contents of which are also included in zip.h) for terms of use. If, for some reason, both of these files are missing, the Info-ZIP license also may be found at: ftp://ftp.cdrom.com/pub/infozip/license.html */ #ifndef O_RDONLY # define O_RDONLY 0 #endif #define fhow O_RDONLY #define fbad (-1) typedef int ftype; #define zopen(n,p) open(n,p) #define zread(f,b,n) read(f,b,n) #define zclose(f) close(f) #define zerr(f) (k == (extent)(-1L)) #define zstdin 0 zip30/atheos/0040755000076400000060000000000011033727770011256 5ustar ediskzip30/atheos/atheos.c0100644000076400000060000006404010154331714012676 0ustar edisk/* Copyright (c) 1990-1999 Info-ZIP. All rights reserved. See the accompanying file LICENSE, version 1999-Oct-05 or later (the contents of which are also included in zip.h) for terms of use. If, for some reason, both of these files are missing, the Info-ZIP license also may be found at: ftp://ftp.cdrom.com/pub/infozip/license.html This AtheOS - specific file is based on unix.c and beos.c; changes by Ruslan Nickolaev (nruslan@hotbox.ru) */ #include "zip.h" #ifndef UTIL /* the companion #endif is a bit of ways down ... */ #include #include #include #include #include #include #include #include #include #include #define PAD 0 #define PATH_END '/' /* Library functions not in (most) header files */ #ifdef _POSIX_VERSION # include #else int utime OF((char *, time_t *)); #endif extern char *label; local ulg label_time = 0; local ulg label_mode = 0; local time_t label_utim = 0; /* Local functions */ local char *readd OF((DIR *)); local int get_attr_dir( const char *, char **, off_t * ); local int add_UT_ef( struct zlist far * ); local int add_Ux_ef( struct zlist far * ); local int add_At_ef( struct zlist far * ); local char *readd(d) DIR *d; /* directory stream to read from */ /* Return a pointer to the next name in the directory stream d, or NULL if no more entries or an error occurs. */ { struct dirent *e; e = readdir(d); return e == NULL ? (char *) NULL : e->d_name; } int procname(n, caseflag) char *n; /* name to process */ int caseflag; /* true to force case-sensitive match */ /* Process a name or sh expression to operate on (or exclude). Return an error code in the ZE_ class. */ { char *a; /* path and name for recursion */ DIR *d; /* directory stream from opendir() */ char *e; /* pointer to name from readd() */ int m; /* matched flag */ char *p; /* path for recursion */ struct stat s; /* result of stat() */ struct zlist far *z; /* steps through zfiles list */ if (strcmp(n, "-") == 0) /* if compressing stdin */ return newname(n, 0, caseflag); else if (LSSTAT(n, &s)) { /* Not a file or directory--search for shell expression in zip file */ p = ex2in(n, 0, (int *)NULL); /* shouldn't affect matching chars */ m = 1; for (z = zfiles; z != NULL; z = z->nxt) { if (MATCH(p, z->iname, caseflag)) { z->mark = pcount ? filter(z->zname, caseflag) : 1; if (verbose) fprintf(mesg, "zip diagnostic: %scluding %s\n", z->mark ? "in" : "ex", z->name); m = 0; } } free((zvoid *)p); return m ? ZE_MISS : ZE_OK; } /* Live name--use if file, recurse if directory */ if ((s.st_mode & S_IFREG) == S_IFREG || (s.st_mode & S_IFLNK) == S_IFLNK) { /* add or remove name of file */ if ((m = newname(n, 0, caseflag)) != ZE_OK) return m; } else if ((s.st_mode & S_IFDIR) == S_IFDIR) { /* Add trailing / to the directory name */ if ((p = malloc(strlen(n)+2)) == NULL) return ZE_MEM; if (strcmp(n, ".") == 0) { *p = '\0'; /* avoid "./" prefix and do not create zip entry */ } else { strcpy(p, n); a = p + strlen(p); if (a[-1] != '/') strcpy(a, "/"); if (dirnames && (m = newname(p, 1, caseflag)) != ZE_OK) { free((zvoid *)p); return m; } } /* recurse into directory */ if (recurse && (d = opendir(n)) != NULL) { while ((e = readd(d)) != NULL) { if (strcmp(e, ".") && strcmp(e, "..")) { if ((a = malloc(strlen(p) + strlen(e) + 1)) == NULL) { closedir(d); free((zvoid *)p); return ZE_MEM; } strcat(strcpy(a, p), e); if ((m = procname(a, caseflag)) != ZE_OK) /* recurse on name */ { if (m == ZE_MISS) zipwarn("name not matched: ", a); else ziperr(m, a); } free((zvoid *)a); } } closedir(d); } free((zvoid *)p); } /* (s.st_mode & S_IFDIR) */ else zipwarn("ignoring special file: ", n); return ZE_OK; } char *ex2in(x, isdir, pdosflag) char *x; /* external file name */ int isdir; /* input: x is a directory */ int *pdosflag; /* output: force MSDOS file attributes? */ /* Convert the external file name to a zip file name, returning the malloc'ed string or NULL if not enough memory. */ { char *n; /* internal file name (malloc'ed) */ char *t = NULL; /* shortened name */ int dosflag; dosflag = dosify; /* default for non-DOS and non-OS/2 */ /* Find starting point in name before doing malloc */ /* Strip "//host/share/" part of a UNC name */ if (!strncmp(x,"//",2) && (x[2] != '\0' && x[2] != '/')) { n = x + 2; while (*n != '\0' && *n != '/') n++; /* strip host name */ if (*n != '\0') { n++; while (*n != '\0' && *n != '/') n++; /* strip `share' name */ } if (*n != '\0') t = n + 1; } else t = x; while (*t == '/') t++; /* strip leading '/' chars to get a relative path */ while (*t == '.' && t[1] == '/') t += 2; /* strip redundant leading "./" sections */ /* Make changes, if any, to the copied name (leave original intact) */ if (!pathput) t = last(t, PATH_END); /* Malloc space for internal name and copy it */ if ((n = malloc(strlen(t) + 1)) == NULL) return NULL; strcpy(n, t); if (isdir == 42) return n; /* avoid warning on unused variable */ if (dosify) msname(n); /* Returned malloc'ed name */ if (pdosflag) *pdosflag = dosflag; return n; } char *in2ex(n) char *n; /* internal file name */ /* Convert the zip file name to an external file name, returning the malloc'ed string or NULL if not enough memory. */ { char *x; /* external file name */ if ((x = malloc(strlen(n) + 1 + PAD)) == NULL) return NULL; strcpy(x, n); return x; } /* * XXX use ztimbuf in both POSIX and non POSIX cases ? */ void stamp(f, d) char *f; /* name of file to change */ ulg d; /* dos-style time to change it to */ /* Set last updated and accessed time of file f to the DOS time d. */ { #ifdef _POSIX_VERSION struct utimbuf u; /* argument for utime() const ?? */ #else time_t u[2]; /* argument for utime() */ #endif /* Convert DOS time to time_t format in u */ #ifdef _POSIX_VERSION u.actime = u.modtime = dos2unixtime(d); utime(f, &u); #else u[0] = u[1] = dos2unixtime(d); utime(f, u); #endif } ulg filetime(f, a, n, t) char *f; /* name of file to get info on */ ulg *a; /* return value: file attributes */ long *n; /* return value: file size */ iztimes *t; /* return value: access, modific. and creation times */ /* If file *f does not exist, return 0. Else, return the file's last modified date and time as an MSDOS date and time. The date and time is returned in a long with the date most significant to allow unsigned integer comparison of absolute times. Also, if a is not a NULL pointer, store the file attributes there, with the high two bytes being the Unix attributes, and the low byte being a mapping of that to DOS attributes. If n is not NULL, store the file size there. If t is not NULL, the file's access, modification and creation times are stored there as UNIX time_t values. If f is "-", use standard input as the file. If f is a device, return a file size of -1 */ { struct stat s; /* results of stat() */ char *name; int len = strlen(f); if (f == label) { if (a != NULL) *a = label_mode; if (n != NULL) *n = -2L; /* convention for a label name */ if (t != NULL) t->atime = t->mtime = t->ctime = label_utim; return label_time; } if ((name = malloc(len + 1)) == NULL { ZIPERR(ZE_MEM, "filetime"); } strcpy(name, f); if (name[len - 1] == '/') name[len - 1] = '\0'; /* not all systems allow stat'ing a file with / appended */ if (strcmp(f, "-") == 0) { if (fstat(fileno(stdin), &s) != 0) { free(name); error("fstat(stdin)"); } } else if (LSSTAT(name, &s) != 0) { /* Accept about any file kind including directories * (stored with trailing / with -r option) */ free(name); return 0; } free(name); if (a != NULL) { #ifndef OS390 *a = ((ulg)s.st_mode << 16) | !(s.st_mode & S_IWRITE); #else /* ** The following defines are copied from the unizip source and represent the ** legacy Unix mode flags. These fixed bit masks are no longer required ** by XOPEN standards - the S_IS### macros being the new recommended method. ** The approach here of setting the legacy flags by testing the macros should ** work under any _XOPEN_SOURCE environment (and will just rebuild the same bit ** mask), but is required if the legacy bit flags differ from legacy Unix. */ #define UNX_IFDIR 0040000 /* Unix directory */ #define UNX_IFREG 0100000 /* Unix regular file */ #define UNX_IFSOCK 0140000 /* Unix socket (BSD, not SysV or Amiga) */ #define UNX_IFLNK 0120000 /* Unix symbolic link (not SysV, Amiga) */ #define UNX_IFBLK 0060000 /* Unix block special (not Amiga) */ #define UNX_IFCHR 0020000 /* Unix character special (not Amiga) */ #define UNX_IFIFO 0010000 /* Unix fifo (BCC, not MSC or Amiga) */ { mode_t legacy_modes; /* Initialize with permission bits - which are not implementation optional */ legacy_modes = s.st_mode & (S_IRWXU | S_IRWXG | S_IRWXO | S_ISUID | S_ISGID | S_ISVTX); if (S_ISDIR(s.st_mode)) legacy_modes |= UNX_IFDIR; if (S_ISREG(s.st_mode)) legacy_modes |= UNX_IFREG; if (S_ISLNK(s.st_mode)) legacy_modes |= UNX_IFLNK; if (S_ISBLK(s.st_mode)) legacy_modes |= UNX_IFBLK; if (S_ISCHR(s.st_mode)) legacy_modes |= UNX_IFCHR; if (S_ISFIFO(s.st_mode)) legacy_modes |= UNX_IFIFO; if (S_ISSOCK(s.st_mode)) legacy_modes |= UNX_IFSOCK; *a = ((ulg)legacy_modes << 16) | !(s.st_mode & S_IWRITE); } #endif if ((s.st_mode & S_IFMT) == S_IFDIR) { *a |= MSDOS_DIR_ATTR; } } if (n != NULL) *n = (s.st_mode & S_IFMT) == S_IFREG ? s.st_size : -1L; if (t != NULL) { t->atime = s.st_atime; t->mtime = s.st_mtime; t->ctime = t->mtime; /* best guess, (s.st_ctime: last status change!!) */ } return unix2dostime(&s.st_mtime); } /* ---------------------------------------------------------------------- Return a malloc()'d buffer containing all of the attributes and their names for the file specified in name. You have to free() this yourself. The length of the buffer is also returned. If get_attr_dir() fails, the buffer will be NULL, total_size will be 0, and an error will be returned: EOK - no errors occurred EINVAL - attr_buff was pointing at a buffer ENOMEM - insufficient memory for attribute buffer Other errors are possible (whatever is returned by the fs_attrib.h functions). PROBLEMS: - pointers are 32-bits; attributes are limited to ssize_t in size so it's possible to overflow... in practice, this isn't too likely... your machine will thrash like hell before that happens */ #define INITIAL_BUFF_SIZE 65536 int get_attr_dir( const char *name, char **attr_buff, off_t *total_size ) { int retval = EOK; int fd; DIR *fa_dir; struct dirent *fa_ent; off_t attrs_size = 0; size_t entname_size; char *ptr; struct attr_info fa_info; *total_size = 0; /* ----------------------------------------------------------------- */ /* Sanity-check. */ if( *attr_buff != NULL ) { return EINVAL; } /* ----------------------------------------------------------------- */ /* Can we open the file/directory? */ /* */ /* linkput is a zip global; it's set to 1 if we're storing symbolic */ /* links as symbolic links (instead of storing the thing the link */ /* points to)... if we're storing the symbolic link as a link, we'll */ /* want the link's file attributes, otherwise we want the target's. */ fd = open( name, linkput ? O_RDONLY | O_NOTRAVERSE : O_RDONLY ); if( fd < 0 ) { return errno; } /* ----------------------------------------------------------------- */ /* Allocate an initial buffer; 64k should usually be enough. */ *attr_buff = (char *)malloc( INITIAL_BUFF_SIZE ); ptr = *attr_buff; if( ptr == NULL ) { close( fd ); return ENOMEM; } /* ----------------------------------------------------------------- */ /* Open the attributes directory for this file. */ fa_dir = open_attrdir( fd ); if( fa_dir == NULL ) { close( fd ); free( ptr ); *attr_buff = NULL; return retval; } /* ----------------------------------------------------------------- */ /* Read all the attributes; the buffer could grow > 64K if there are */ /* many and/or they are large. */ while( ( fa_ent = read_attrdir( fa_dir ) ) != NULL ) { retval = stat_attr( fd, fa_ent->d_name, &fa_info ); /* TODO: check retval != EOK */ entname_size = strlen( fa_ent->d_name ) + 1; attrs_size += entname_size + sizeof( struct attr_info ) + fa_info.ai_size; if( attrs_size > INITIAL_BUFF_SIZE ) { unsigned long offset = ptr - *attr_buff; *attr_buff = (char *)realloc( *attr_buff, attrs_size ); if( *attr_buff == NULL ) { retval = close_attrdir( fa_dir ); /* TODO: check retval != EOK */ close( fd ); return ENOMEM; } ptr = *attr_buff + offset; } /* Now copy the data for this attribute into the buffer. */ strcpy( ptr, fa_ent->d_name ); ptr += entname_size; memcpy( ptr, &fa_info, sizeof( struct attr_info ) ); ptr += sizeof( struct attr_info ); if( fa_info.ai_size > 0 ) { ssize_t read_bytes = read_attr( fd, fa_ent->d_name, fa_info.ai_type, ptr, 0, fa_info.ai_size ); if( read_bytes != fa_info.ai_size ) { /* print a warning about mismatched sizes */ char buff[80]; sprintf( buff, "read %d, expected %d", read_bytes, (ssize_t)fa_info.ai_size ); zipwarn( "attribute size mismatch: ", buff ); } ptr += fa_info.ai_size; } } /* ----------------------------------------------------------------- */ /* Close the attribute directory. */ retval = close_attrdir( fa_dir ); /* TODO: check retval != EOK */ /* ----------------------------------------------------------------- */ /* If the buffer is too big, shrink it. */ if( attrs_size < INITIAL_BUFF_SIZE ) { *attr_buff = (char *)realloc( *attr_buff, attrs_size ); if( *attr_buff == NULL ) { close( fd ); return ENOMEM; } } *total_size = attrs_size; close( fd ); return EOK; } /* ---------------------------------------------------------------------- */ /* Add a 'UT' extra field to the zlist data pointed to by z. */ #define EB_L_UT_SIZE (EB_HEADSIZE + EB_UT_LEN(2)) #define EB_C_UT_SIZE (EB_HEADSIZE + EB_UT_LEN(1)) local int add_UT_ef( struct zlist far *z ) { char *l_ef = NULL; char *c_ef = NULL; struct stat s; #ifdef IZ_CHECK_TZ if (!zp_tz_is_valid) return ZE_OK; /* skip silently if no valid TZ info */ #endif /* We can't work if there's no entry to work on. */ if( z == NULL ) { return ZE_LOGIC; } /* Check to make sure we've got enough room in the extra fields. */ if( z->ext + EB_L_UT_SIZE > USHRT_MAX || z->cext + EB_C_UT_SIZE > USHRT_MAX ) { return ZE_MEM; } /* stat() the file (or the symlink) to get the data; if we can't get */ /* the data, there's no point in trying to fill out the fields. */ if(LSSTAT( z->name, &s ) ) { return ZE_OPEN; } /* Allocate memory for the local and central extra fields. */ if( z->extra && z->ext != 0 ) { l_ef = (char *)realloc( z->extra, z->ext + EB_L_UT_SIZE ); } else { l_ef = (char *)malloc( EB_L_UT_SIZE ); z->ext = 0; } if( l_ef == NULL ) { return ZE_MEM; } z->extra = l_ef; l_ef += z->ext; if( z->cextra && z->cext != 0 ) { c_ef = (char *)realloc( z->cextra, z->cext + EB_C_UT_SIZE ); } else { c_ef = (char *)malloc( EB_C_UT_SIZE ); z->cext = 0; } if( c_ef == NULL ) { return ZE_MEM; } z->cextra = c_ef; c_ef += z->cext; /* Now add the local version of the field. */ *l_ef++ = 'U'; *l_ef++ = 'T'; *l_ef++ = (char)(EB_UT_LEN(2)); /* length of data in local EF */ *l_ef++ = (char)0; *l_ef++ = (char)(EB_UT_FL_MTIME | EB_UT_FL_ATIME); *l_ef++ = (char)(s.st_mtime); *l_ef++ = (char)(s.st_mtime >> 8); *l_ef++ = (char)(s.st_mtime >> 16); *l_ef++ = (char)(s.st_mtime >> 24); *l_ef++ = (char)(s.st_atime); *l_ef++ = (char)(s.st_atime >> 8); *l_ef++ = (char)(s.st_atime >> 16); *l_ef++ = (char)(s.st_atime >> 24); z->ext += EB_L_UT_SIZE; /* Now add the central version. */ memcpy(c_ef, l_ef-EB_L_UT_SIZE, EB_C_UT_SIZE); c_ef[EB_LEN] = (char)(EB_UT_LEN(1)); /* length of data in central EF */ z->cext += EB_C_UT_SIZE; return ZE_OK; } /* ---------------------------------------------------------------------- */ /* Add a 'Ux' extra field to the zlist data pointed to by z. */ #define EB_L_UX2_SIZE (EB_HEADSIZE + EB_UX2_MINLEN) #define EB_C_UX2_SIZE (EB_HEADSIZE) local int add_Ux_ef( struct zlist far *z ) { char *l_ef = NULL; char *c_ef = NULL; struct stat s; /* Check to make sure we've got enough room in the extra fields. */ if( z->ext + EB_L_UX2_SIZE > USHRT_MAX || z->cext + EB_C_UX2_SIZE > USHRT_MAX ) { return ZE_MEM; } /* stat() the file (or the symlink) to get the data; if we can't get */ /* the data, there's no point in trying to fill out the fields. */ if(LSSTAT( z->name, &s ) ) { return ZE_OPEN; } /* Allocate memory for the local and central extra fields. */ if( z->extra && z->ext != 0 ) { l_ef = (char *)realloc( z->extra, z->ext + EB_L_UX2_SIZE ); } else { l_ef = (char *)malloc( EB_L_UX2_SIZE ); z->ext = 0; } if( l_ef == NULL ) { return ZE_MEM; } z->extra = l_ef; l_ef += z->ext; if( z->cextra && z->cext != 0 ) { c_ef = (char *)realloc( z->cextra, z->cext + EB_C_UX2_SIZE ); } else { c_ef = (char *)malloc( EB_C_UX2_SIZE ); z->cext = 0; } if( c_ef == NULL ) { return ZE_MEM; } z->cextra = c_ef; c_ef += z->cext; /* Now add the local version of the field. */ *l_ef++ = 'U'; *l_ef++ = 'x'; *l_ef++ = (char)(EB_UX2_MINLEN); *l_ef++ = (char)(EB_UX2_MINLEN >> 8); *l_ef++ = (char)(s.st_uid); *l_ef++ = (char)(s.st_uid >> 8); *l_ef++ = (char)(s.st_gid); *l_ef++ = (char)(s.st_gid >> 8); z->ext += EB_L_UX2_SIZE; /* Now add the central version of the field. */ *c_ef++ = 'U'; *c_ef++ = 'x'; *c_ef++ = 0; *c_ef++ = 0; z->cext += EB_C_UX2_SIZE; return ZE_OK; } /* ---------------------------------------------------------------------- */ /* Add a 'At' extra field to the zlist data pointed to by z. */ #define EB_L_AT_SIZE (EB_HEADSIZE + EB_L_AT_LEN) /* + attr size */ #define EB_C_AT_SIZE (EB_HEADSIZE + EB_C_AT_LEN) #define MEMCOMPRESS_HEADER 6 /* ush compression type, ulg CRC */ #define DEFLAT_WORSTCASE_ADD 5 /* byte blocktype, 2 * ush blocklength */ #define MEMCOMPRESS_OVERHEAD (MEMCOMPRESS_HEADER + DEFLAT_WORSTCASE_ADD) local int add_At_ef( struct zlist far *z ) { char *l_ef = NULL; char *c_ef = NULL; char *attrbuff = NULL; off_t attrsize = 0; char *compbuff = NULL; ush compsize = 0; uch flags = 0; /* Check to make sure we've got enough room in the extra fields. */ if( z->ext + EB_L_AT_SIZE > USHRT_MAX || z->cext + EB_C_AT_SIZE > USHRT_MAX ) { return ZE_MEM; } /* Attempt to load up a buffer full of the file's attributes. */ { if (get_attr_dir( z->name, &attrbuff, &attrsize) != EOK ) { return ZE_OPEN; } if (attrsize == 0) { return ZE_OK; } if (attrbuff == NULL) { return ZE_LOGIC; } /* Check for way too much data. */ if (attrsize > (off_t)ULONG_MAX) { zipwarn( "uncompressed attributes truncated", "" ); attrsize = (off_t)(ULONG_MAX - MEMCOMPRESS_OVERHEAD); } } if (verbose) { printf( "\t[in=%lu]", (unsigned long)attrsize ); } /* Try compressing the data */ compbuff = (char *)malloc( (size_t)attrsize + MEMCOMPRESS_OVERHEAD ); if( compbuff == NULL ) { return ZE_MEM; } compsize = memcompress( compbuff, (size_t)attrsize + MEMCOMPRESS_OVERHEAD, attrbuff, (size_t)attrsize ); if (verbose) { printf( " [out=%u]", compsize ); } /* Attempt to optimise very small attributes. */ if (compsize > attrsize) { free( compbuff ); compsize = (ush)attrsize; compbuff = attrbuff; flags = EB_AT_FL_NATURAL; } /* Check to see if we really have enough room in the EF for the data. */ if( ( z->ext + compsize + EB_L_AT_LEN ) > USHRT_MAX ) { compsize = USHRT_MAX - EB_L_AT_LEN - z->ext; } /* Allocate memory for the local and central extra fields. */ if( z->extra && z->ext != 0 ) { l_ef = (char *)realloc( z->extra, z->ext + EB_L_AT_SIZE + compsize ); } else { l_ef = (char *)malloc( EB_L_AT_SIZE + compsize ); z->ext = 0; } if( l_ef == NULL ) { return ZE_MEM; } z->extra = l_ef; l_ef += z->ext; if( z->cextra && z->cext != 0 ) { c_ef = (char *)realloc( z->cextra, z->cext + EB_C_AT_SIZE ); } else { c_ef = (char *)malloc( EB_C_AT_SIZE ); z->cext = 0; } if( c_ef == NULL ) { return ZE_MEM; } z->cextra = c_ef; c_ef += z->cext; /* Now add the local version of the field. */ *l_ef++ = 'A'; *l_ef++ = 't'; *l_ef++ = (char)(compsize + EB_L_AT_LEN); *l_ef++ = (char)((compsize + EB_L_AT_LEN) >> 8); *l_ef++ = (char)((unsigned long)attrsize); *l_ef++ = (char)((unsigned long)attrsize >> 8); *l_ef++ = (char)((unsigned long)attrsize >> 16); *l_ef++ = (char)((unsigned long)attrsize >> 24); *l_ef++ = flags; memcpy( l_ef, compbuff, (size_t)compsize ); z->ext += EB_L_AT_SIZE + compsize; /* And the central version. */ *c_ef++ = 'A'; *c_ef++ = 't'; *c_ef++ = (char)(EB_C_AT_LEN); *c_ef++ = (char)(EB_C_AT_LEN >> 8); *c_ef++ = (char)compsize; *c_ef++ = (char)(compsize >> 8); *c_ef++ = (char)(compsize >> 16); *c_ef++ = (char)(compsize >> 24); *c_ef++ = flags; z->cext += EB_C_AT_SIZE; return ZE_OK; } /* Extra field info: - 'UT' - UNIX time extra field - 'Ux' - UNIX uid/gid extra field - 'At' - AtheOS file attributes extra field This is done the same way ../unix/unix.c stores the 'UT'/'Ux' fields (full data in local header, only modification time in central header), with the 'At' field added to the end and the size of the 'At' field in the central header. See the end of atheos/osdep.h for a simple explanation of the 'At' EF layout. */ int set_extra_field(z, z_utim) struct zlist far *z; iztimes *z_utim; /* store full data in local header but just modification time stamp info in central header */ { int retval; /* Check to make sure z is valid. */ if( z == NULL ) { return ZE_LOGIC; } retval = add_UT_ef(z); if( retval != ZE_OK ) { return retval; } retval = add_Ux_ef(z); if( retval != ZE_OK ) { return retval; } return add_At_ef(z); /* last function; we can use return value directly */ } /* ---------------------------------------------------------------------- */ /* Set a file's MIME type. */ void setfiletype(const char *file, const char *type) { int fd; off_t nLen; ssize_t nError; fd = open( file, O_RDWR ); if (fd < 0) { zipwarn( "can't open zipfile to write file type", "" ); } else { nLen = strlen( type ); /* FIXME: write_attr() should return count of writed bytes */ nError = write_attr( fd, "os::MimeType", O_TRUNC, ATTR_TYPE_STRING, type, 0, nLen ); if (nError < 0) { zipwarn( "couldn't write complete file type", "" ); } close( fd ); } } #endif /* !UTIL */ /******************************/ /* Function version_local() */ /******************************/ void version_local() { static ZCONST char CompiledWith[] = "Compiled with %s%s for %s%s%s%s.\n\n"; printf(CompiledWith, #ifdef __GNUC__ "gcc ", __VERSION__, #else "(unknown compiler)", "", #endif "Syllable", #if defined(i486) || defined(__i486) || defined(__i486__) || defined(i386) || defined(__i386) || defined(__i386__) " (x86)", #else " (unknown platform)", #endif #ifdef __DATE__ " on ", __DATE__ #else "", "" #endif ); } /* end function version_local() */ zip30/atheos/Makefile0100644000076400000060000000705110550047734012714 0ustar edisk###################################################################### # # Makefile for Info-ZIP's zip, zipcloak, zipnote, and zipsplit on AtheOS # # Copyright (C) 1999-2007 Info-ZIP # Chris Herborth (chrish@pobox.com) # Ruslan Nickolaev (nruslan@hotbox.ru) # ###################################################################### # Things that don't change: # Punish people who don't have SMP hardware. MAKE = make -j 4 -f atheos/Makefile SHELL = /bin/sh LN = ln -s RM = rm -f BIND = $(CC) AS = as INSTALL = install # Target directories prefix = /usr BINDIR = $(prefix)/bin manext = 1 MANDIR = $(prefix)/man/man$(manext) ZIPMANUAL = MANUAL VERSION = Version 2.3 of __DATE__ ###################################################################### CC:=gcc CFLAGS:=-O3 -march=i586 -Wall -I. -DHAVE_DIRENT_H -DPASSWD_FROM_STDIN -DASMV -DASM_CRC LFLAGS1:= LFLAGS2:= TARGET=$(ZIPS) ###################################################################### # Helpful targets all: $(MAKE) CC=$(CC) CFLAGS="$(CFLAGS)" \ LFLAGS1="$(LFLAGS1)" LFLAGS2="$(LFLAGS2)" \ $(TARGET) ###################################################################### # Object file lists and other build goodies # Object file lists OBJZ = zip.o zipfile.o zipup.o fileio.o util.o globals.o crc32.o crypt.o \ ttyio.o atheos.o OBJI = deflate.o trees.o OBJA = match.o crc_i386.o OBJU = zipfile_.o fileio_.o util_.o globals.o atheos_.o OBJN = zipnote.o $(OBJU) OBJC = zipcloak.o $(OBJU) crc32_.o crypt_.o ttyio.o OBJS = zipsplit.o $(OBJU) # Headers ZIP_H = zip.h ziperr.h tailor.h atheos/osdep.h # What to build? ZIPS = zip zipnote zipsplit zipcloak # suffix rules .SUFFIXES: .SUFFIXES: _.o .o .c .doc .1 .c_.o: $(RM) $*_.c; $(LN) $< $*_.c $(CC) -c $(CFLAGS) -DUTIL $*_.c $(RM) $*_.c .c.o: $(CC) -c $(CFLAGS) $< .1.doc: groff -man -Tascii $< > $@ # rules for zip, zipnote, zipcloak, zipsplit, and the Zip MANUAL. $(OBJZ): $(ZIP_H) $(OBJI): $(ZIP_H) $(OBJN): $(ZIP_H) $(OBJS): $(ZIP_H) $(OBJC): $(ZIP_H) zip.o crc32.o crypt.o fileio.o zipfile.o zipup.o: crc32.h zipcloak.o crc32_.o crypt_.o fileio_.o zipfile_.o: crc32.h zip.o zipup.o crypt.o ttyio.o zipcloak.o crypt_.o: crypt.h zip.o zipup.o zipnote.o zipcloak.o zipsplit.o: revision.h zip.o crypt.o ttyio.o zipcloak.o crypt_.o: ttyio.h zipup.o: atheos/zipup.h match.o: match.S $(CC) -E match.S > matchs.s $(AS) -o $@ matchs.s $(RM) matchs.s crc_i386.o: crc_i386.S $(CC) -E crc_i386.S > crc_i386s.s $(AS) -o $@ crc_i386s.s $(RM) crc_i386s.s atheos.o: atheos/atheos.c $(CC) -c $(CFLAGS) atheos/atheos.c atheos_.o: atheos/atheos.c $(RM) $*_.c; $(LN) atheos/atheos.c $*_.c $(CC) -c $(CFLAGS) -DUTIL $*_.c $(RM) $*_.c zips: $(ZIPS) zipsman: $(ZIPS) $(ZIPMANUAL) zip: $(OBJZ) $(OBJI) $(OBJA) $(BIND) -o zip $(LFLAGS1) $(OBJZ) $(OBJI) $(OBJA) $(LFLAGS2) zipnote: $(OBJN) $(BIND) -o zipnote $(LFLAGS1) $(OBJN) $(LFLAGS2) zipcloak: $(OBJC) $(BIND) -o zipcloak $(LFLAGS1) $(OBJC) $(LFLAGS2) zipsplit: $(OBJS) $(BIND) -o zipsplit $(LFLAGS1) $(OBJS) $(LFLAGS2) $(ZIPMANUAL): man/zip.1 groff -man -Tascii man/zip.1 > $(ZIPMANUAL) # install install: $(ZIPS) $(INSTALL) -m755 $(ZIPS) $(BINDIR) mkdir -p $(MANDIR) $(INSTALL) -m644 man/zip.1 $(MANDIR)/zip.$(manext) uninstall: -cd $(BINDIR); $(RM) $(ZIPS) -cd $(MANDIR); $(RM) zip.$(manext) dist: $(ZIPMANUAL) zip -u9T zip`sed -e '/VERSION/!d' -e 's/.*"\(.*\)".*/\1/' \ -e s/[.]//g -e q revision.h` \ `awk '/^Makefile/,/vms_zip.rnh/ {print $$1}' < contents` # clean up after making stuff and installing it clean: $(RM) *.o $(ZIPS) flags # end of Makefile zip30/atheos/osdep.h0100644000076400000060000000413010145121124012514 0ustar edisk/* Copyright (c) 1990-1999 Info-ZIP. All rights reserved. See the accompanying file LICENSE, version 1999-Oct-05 or later (the contents of which are also included in zip.h) for terms of use. If, for some reason, both of these files are missing, the Info-ZIP license also may be found at: ftp://ftp.cdrom.com/pub/infozip/license.html */ #ifndef _OSDEP_H_ #define _OSDEP_H_ #include #include #include #define USE_EF_UT_TIME /* Enable use of "UT" extra field time info */ #define EB_L_AT_LEN 5 /* min size is an unsigned long and flag */ #define EB_C_AT_LEN 5 /* Length of data in local EF and flag. */ #define EB_AT_FL_NATURAL 0x01 /* data is 'natural' (not compressed) */ #define EB_AT_FL_BADBITS 0xfe /* bits currently undefined */ #ifndef ZP_NEED_MEMCOMPR define ZP_NEED_MEMCOMPR #endif #define deletedir(d) rmdir(d); /* Set a file's MIME type. */ void setfiletype( const char *file, const char *type ); /* 'At' extra-field layout: 'At' - signature ef_size - size of data in this EF (little-endian unsigned short) full_size - uncompressed data size (little-endian unsigned long) flag - flags (byte) flags & EB_AT_FL_NATURAL = the data is not compressed flags & EB_AT_FL_BADBITS = the data is corrupted or we can't handle it properly data - compressed or uncompressed file attribute data If flag & EB_AT_FL_NATURAL, the data is not compressed; this optimisation is necessary to prevent wasted space for files with small attributes. In this case, there should be ( ef_size - EB_L_AT_LEN ) bytes of data, and full_size should equal ( ef_size - EB_L_AT_LEN ). If the data is compressed, there will be ( ef_size - EB_L_AT_LEN ) bytes of compressed data, and full_size bytes of uncompressed data. If a file has absolutely no attributes, there will not be a 'At' extra field. The uncompressed data is arranged like this: attr_name\0 - C string struct attr_info (little-endian) attr_data (length in attr_info.ai_size) */ #endif zip30/atheos/README0100644000076400000060000000117610145127316012131 0ustar ediskInfo-ZIP's zip for AtheOS/Syllable FEATURES stores AtheOS/Syllable file attributes, compressing them if possible TODO ---- There is only one thing to be fixed: write_attr() should return count of writed bytes. However that's bug related with AFS only. Please report any bugs to Info-ZIP at www.info-zip.org. If this bug related with AtheOS/Syllable only, you can mail me directly: nruslan@hotbox.ru. Visit the Info-ZIP web site (http://www.info-zip.org) for all the latest zip and unzip information, FAQs, source code and ready-to-run executables. - Ruslan Nickolaev (nruslan@hotbox.ru) Sep 06/2004 (updated 12 November 2004) zip30/atheos/zipup.h0100644000076400000060000000122510145121340012553 0ustar edisk/* Copyright (c) 1990-1999 Info-ZIP. All rights reserved. See the accompanying file LICENSE, version 1999-Oct-05 or later (the contents of which are also included in zip.h) for terms of use. If, for some reason, both of these files are missing, the Info-ZIP license also may be found at: ftp://ftp.cdrom.com/pub/infozip/license.html */ #ifndef _ZIPUP_H_ #define _ZIPUP_H_ #ifndef O_RDONLY # include #endif #define fhow O_RDONLY #define fbad (-1) typedef int ftype; #define zopen(n,p) open(n,p) #define zread(f,b,n) read(f,b,n) #define zclose(f) close(f) #define zerr(f) (k == (extent)(-1L)) #define zstdin 0 #endif /* _ZIPUP_H_ */ zip30/beos/0040755000076400000060000000000011033727770010723 5ustar ediskzip30/beos/beos.c0100644000076400000060000006532210154331732012014 0ustar edisk/* Copyright (c) 1990-2002 Info-ZIP. All rights reserved. See the accompanying file LICENSE, version 2000-Apr-09 or later (the contents of which are also included in zip.h) for terms of use. If, for some reason, all these files are missing, the Info-ZIP license also may be found at: ftp://ftp.info-zip.org/pub/infozip/license.html */ /* This BeOS-specific file is based on unix.c in the unix directory; changes by Chris Herborth (chrish@pobox.com). */ #include "zip.h" #ifndef UTIL /* the companion #endif is a bit of ways down ... */ #include #include #include #include #include #include #include #include #include #include #include #include #include #define PAD 0 #define PATH_END '/' /* Library functions not in (most) header files */ #ifdef _POSIX_VERSION # include #else int utime OF((char *, time_t *)); #endif extern char *label; local ulg label_time = 0; local ulg label_mode = 0; local time_t label_utim = 0; /* Local functions */ local char *readd OF((DIR *)); local int get_attr_dir( const char *, char **, off_t * ); local int add_UT_ef( struct zlist far * ); local int add_Ux_ef( struct zlist far * ); local int add_Be_ef( struct zlist far * ); #ifdef NO_DIR /* for AT&T 3B1 */ #include #ifndef dirent # define dirent direct #endif typedef FILE DIR; /* ** Apparently originally by Rich Salz. ** Cleaned up and modified by James W. Birdsall. */ #define opendir(path) fopen(path, "r") struct dirent *readdir(dirp) DIR *dirp; { static struct dirent entry; if (dirp == NULL) return NULL; for (;;) if (fread (&entry, sizeof (struct dirent), 1, dirp) == 0) return NULL; else if (entry.d_ino) return (&entry); } /* end of readdir() */ #define closedir(dirp) fclose(dirp) #endif /* NO_DIR */ local char *readd(d) DIR *d; /* directory stream to read from */ /* Return a pointer to the next name in the directory stream d, or NULL if no more entries or an error occurs. */ { struct dirent *e; e = readdir(d); return e == NULL ? (char *) NULL : e->d_name; } int procname(n, caseflag) char *n; /* name to process */ int caseflag; /* true to force case-sensitive match */ /* Process a name or sh expression to operate on (or exclude). Return an error code in the ZE_ class. */ { char *a; /* path and name for recursion */ DIR *d; /* directory stream from opendir() */ char *e; /* pointer to name from readd() */ int m; /* matched flag */ char *p; /* path for recursion */ struct stat s; /* result of stat() */ struct zlist far *z; /* steps through zfiles list */ if (strcmp(n, "-") == 0) /* if compressing stdin */ return newname(n, 0, caseflag); else if (LSSTAT(n, &s)) { /* Not a file or directory--search for shell expression in zip file */ p = ex2in(n, 0, (int *)NULL); /* shouldn't affect matching chars */ m = 1; for (z = zfiles; z != NULL; z = z->nxt) { if (MATCH(p, z->iname, caseflag)) { z->mark = pcount ? filter(z->zname, caseflag) : 1; if (verbose) fprintf(mesg, "zip diagnostic: %scluding %s\n", z->mark ? "in" : "ex", z->name); m = 0; } } free((zvoid *)p); return m ? ZE_MISS : ZE_OK; } /* Live name--use if file, recurse if directory */ if ((s.st_mode & S_IFDIR) == 0) { /* add or remove name of file */ if ((m = newname(n, 0, caseflag)) != ZE_OK) return m; } else { /* Add trailing / to the directory name */ if ((p = malloc(strlen(n)+2)) == NULL) return ZE_MEM; if (strcmp(n, ".") == 0) { *p = '\0'; /* avoid "./" prefix and do not create zip entry */ } else { strcpy(p, n); a = p + strlen(p); if (a[-1] != '/') strcpy(a, "/"); if (dirnames && (m = newname(p, 1, caseflag)) != ZE_OK) { free((zvoid *)p); return m; } } /* recurse into directory */ if (recurse && (d = opendir(n)) != NULL) { while ((e = readd(d)) != NULL) { if (strcmp(e, ".") && strcmp(e, "..")) { if ((a = malloc(strlen(p) + strlen(e) + 1)) == NULL) { closedir(d); free((zvoid *)p); return ZE_MEM; } strcat(strcpy(a, p), e); if ((m = procname(a, caseflag)) != ZE_OK) /* recurse on name */ { if (m == ZE_MISS) zipwarn("name not matched: ", a); else ziperr(m, a); } free((zvoid *)a); } } closedir(d); } free((zvoid *)p); } /* (s.st_mode & S_IFDIR) == 0) */ return ZE_OK; } char *ex2in(x, isdir, pdosflag) char *x; /* external file name */ int isdir; /* input: x is a directory */ int *pdosflag; /* output: force MSDOS file attributes? */ /* Convert the external file name to a zip file name, returning the malloc'ed string or NULL if not enough memory. */ { char *n; /* internal file name (malloc'ed) */ char *t; /* shortened name */ int dosflag; dosflag = dosify; /* default for non-DOS and non-OS/2 */ /* Find starting point in name before doing malloc */ for (t = x; *t == '/'; t++) ; /* strip leading '/' chars to get a relative path */ while (*t == '.' && t[1] == '/') t += 2; /* strip redundant leading "./" sections */ /* Make changes, if any, to the copied name (leave original intact) */ if (!pathput) t = last(t, PATH_END); /* Malloc space for internal name and copy it */ if ((n = malloc(strlen(t) + 1)) == NULL) return NULL; strcpy(n, t); if (isdir == 42) return n; /* avoid warning on unused variable */ if (dosify) msname(n); /* Returned malloc'ed name */ if (pdosflag) *pdosflag = dosflag; return n; } char *in2ex(n) char *n; /* internal file name */ /* Convert the zip file name to an external file name, returning the malloc'ed string or NULL if not enough memory. */ { char *x; /* external file name */ if ((x = malloc(strlen(n) + 1 + PAD)) == NULL) return NULL; strcpy(x, n); return x; } /* * XXX use ztimbuf in both POSIX and non POSIX cases ? */ void stamp(f, d) char *f; /* name of file to change */ ulg d; /* dos-style time to change it to */ /* Set last updated and accessed time of file f to the DOS time d. */ { #ifdef _POSIX_VERSION struct utimbuf u; /* argument for utime() const ?? */ #else time_t u[2]; /* argument for utime() */ #endif /* Convert DOS time to time_t format in u */ #ifdef _POSIX_VERSION u.actime = u.modtime = dos2unixtime(d); utime(f, &u); #else u[0] = u[1] = dos2unixtime(d); utime(f, u); #endif } ulg filetime(f, a, n, t) char *f; /* name of file to get info on */ ulg *a; /* return value: file attributes */ long *n; /* return value: file size */ iztimes *t; /* return value: access, modific. and creation times */ /* If file *f does not exist, return 0. Else, return the file's last modified date and time as an MSDOS date and time. The date and time is returned in a long with the date most significant to allow unsigned integer comparison of absolute times. Also, if a is not a NULL pointer, store the file attributes there, with the high two bytes being the Unix attributes, and the low byte being a mapping of that to DOS attributes. If n is not NULL, store the file size there. If t is not NULL, the file's access, modification and creation times are stored there as UNIX time_t values. If f is "-", use standard input as the file. If f is a device, return a file size of -1 */ { struct stat s; /* results of stat() */ /* convert FNAMX to malloc - 11/8/04 EG */ char *name; int len = strlen(f); if (f == label) { if (a != NULL) *a = label_mode; if (n != NULL) *n = -2L; /* convention for a label name */ if (t != NULL) t->atime = t->mtime = t->ctime = label_utim; return label_time; } if ((name = malloc(len + 1)) == NULL) { ZIPERR(ZE_MEM, "filetime"); } strcpy(name, f); if (name[len - 1] == '/') name[len - 1] = '\0'; /* not all systems allow stat'ing a file with / appended */ if (strcmp(f, "-") == 0) { if (fstat(fileno(stdin), &s) != 0) { free(name); error("fstat(stdin)"); } } else if (LSSTAT(name, &s) != 0) { /* Accept about any file kind including directories * (stored with trailing / with -r option) */ free(name); return 0; } free(name); if (a != NULL) { *a = ((ulg)s.st_mode << 16) | !(s.st_mode & S_IWRITE); if ((s.st_mode & S_IFMT) == S_IFDIR) { *a |= MSDOS_DIR_ATTR; } } if (n != NULL) *n = (s.st_mode & S_IFMT) == S_IFREG ? s.st_size : -1L; if (t != NULL) { t->atime = s.st_atime; t->mtime = s.st_mtime; t->ctime = s.st_mtime; /* best guess (s.st_ctime: last status change!) */ } return unix2dostime(&s.st_mtime); } /* ---------------------------------------------------------------------- Return a malloc()'d buffer containing all of the attributes and their names for the file specified in name. You have to free() this yourself. The length of the buffer is also returned. If get_attr_dir() fails, the buffer will be NULL, total_size will be 0, and an error will be returned: EOK - no errors occurred EINVAL - attr_buff was pointing at a buffer ENOMEM - insufficient memory for attribute buffer Other errors are possible (whatever is returned by the fs_attr.h functions). PROBLEMS: - pointers are 32-bits; attributes are limited to off_t in size so it's possible to overflow... in practice, this isn't too likely... your machine will thrash like hell before that happens */ #define INITIAL_BUFF_SIZE 65536 int get_attr_dir( const char *name, char **attr_buff, off_t *total_size ) { int retval = EOK; int fd; DIR *fa_dir; struct dirent *fa_ent; off_t attrs_size; off_t this_size; char *ptr; struct attr_info fa_info; struct attr_info big_fa_info; retval = EOK; attrs_size = 0; /* gcc still says this is used uninitialized... */ *total_size = 0; /* ----------------------------------------------------------------- */ /* Sanity-check. */ if( *attr_buff != NULL ) { return EINVAL; } /* ----------------------------------------------------------------- */ /* Can we open the file/directory? */ /* */ /* linkput is a zip global; it's set to 1 if we're storing symbolic */ /* links as symbolic links (instead of storing the thing the link */ /* points to)... if we're storing the symbolic link as a link, we'll */ /* want the link's file attributes, otherwise we want the target's. */ if( linkput ) { fd = open( name, O_RDONLY | O_NOTRAVERSE ); } else { fd = open( name, O_RDONLY ); } if( fd < 0 ) { return errno; } /* ----------------------------------------------------------------- */ /* Allocate an initial buffer; 64k should usually be enough. */ *attr_buff = (char *)malloc( INITIAL_BUFF_SIZE ); ptr = *attr_buff; if( ptr == NULL ) { close( fd ); return ENOMEM; } /* ----------------------------------------------------------------- */ /* Open the attributes directory for this file. */ fa_dir = fs_fopen_attr_dir( fd ); if( fa_dir == NULL ) { close( fd ); free( ptr ); *attr_buff = NULL; return retval; } /* ----------------------------------------------------------------- */ /* Read all the attributes; the buffer could grow > 64K if there are */ /* many and/or they are large. */ fa_ent = fs_read_attr_dir( fa_dir ); while( fa_ent != NULL ) { retval = fs_stat_attr( fd, fa_ent->d_name, &fa_info ); /* TODO: check retval != EOK */ this_size = strlen( fa_ent->d_name ) + 1; this_size += sizeof( struct attr_info ); this_size += fa_info.size; attrs_size += this_size; if( attrs_size > INITIAL_BUFF_SIZE ) { unsigned long offset = ptr - *attr_buff; *attr_buff = (char *)realloc( *attr_buff, attrs_size ); if( *attr_buff == NULL ) { retval = fs_close_attr_dir( fa_dir ); /* TODO: check retval != EOK */ close( fd ); return ENOMEM; } ptr = *attr_buff + offset; } /* Now copy the data for this attribute into the buffer. */ strcpy( ptr, fa_ent->d_name ); ptr += strlen( fa_ent->d_name ); *ptr++ = '\0'; /* We need to put a big-endian version of the fa_info data into */ /* the archive. */ big_fa_info.type = B_HOST_TO_BENDIAN_INT32( fa_info.type ); big_fa_info.size = B_HOST_TO_BENDIAN_INT64( fa_info.size ); memcpy( ptr, &big_fa_info, sizeof( struct attr_info ) ); ptr += sizeof( struct attr_info ); if( fa_info.size > 0 ) { ssize_t read_bytes; read_bytes = fs_read_attr( fd, fa_ent->d_name, fa_info.type, 0, ptr, fa_info.size ); if( read_bytes != fa_info.size ) { /* print a warning about mismatched sizes */ char buff[80]; sprintf( buff, "read %ld, expected %ld", (ssize_t)read_bytes, (ssize_t)fa_info.size ); zipwarn( "attribute size mismatch: ", buff ); } /* Wave my magic wand... this swaps all the Be types to big- */ /* endian automagically. */ (void)swap_data( fa_info.type, ptr, fa_info.size, B_SWAP_HOST_TO_BENDIAN ); ptr += fa_info.size; } fa_ent = fs_read_attr_dir( fa_dir ); } /* ----------------------------------------------------------------- */ /* Close the attribute directory. */ retval = fs_close_attr_dir( fa_dir ); /* TODO: check retval != EOK */ /* ----------------------------------------------------------------- */ /* If the buffer is too big, shrink it. */ if( attrs_size < INITIAL_BUFF_SIZE ) { *attr_buff = (char *)realloc( *attr_buff, attrs_size ); if( *attr_buff == NULL ) { /* This really shouldn't happen... */ close( fd ); return ENOMEM; } } *total_size = attrs_size; close( fd ); return EOK; } /* ---------------------------------------------------------------------- */ /* Add a 'UT' extra field to the zlist data pointed to by z. */ #define EB_L_UT_SIZE (EB_HEADSIZE + EB_UT_LEN(2)) #define EB_C_UT_SIZE (EB_HEADSIZE + EB_UT_LEN(1)) local int add_UT_ef( struct zlist far *z ) { char *l_ef = NULL; char *c_ef = NULL; struct stat s; #ifdef IZ_CHECK_TZ if (!zp_tz_is_valid) return ZE_OK; /* skip silently if no valid TZ info */ #endif /* We can't work if there's no entry to work on. */ if( z == NULL ) { return ZE_LOGIC; } /* Check to make sure we've got enough room in the extra fields. */ if( z->ext + EB_L_UT_SIZE > USHRT_MAX || z->cext + EB_C_UT_SIZE > USHRT_MAX ) { return ZE_MEM; } /* stat() the file (or the symlink) to get the data; if we can't get */ /* the data, there's no point in trying to fill out the fields. */ if(LSSTAT( z->name, &s ) ) { return ZE_OPEN; } /* Allocate memory for the local and central extra fields. */ if( z->extra && z->ext != 0 ) { l_ef = (char *)realloc( z->extra, z->ext + EB_L_UT_SIZE ); } else { l_ef = (char *)malloc( EB_L_UT_SIZE ); z->ext = 0; } if( l_ef == NULL ) { return ZE_MEM; } z->extra = l_ef; l_ef += z->ext; if( z->cextra && z->cext != 0 ) { c_ef = (char *)realloc( z->cextra, z->cext + EB_C_UT_SIZE ); } else { c_ef = (char *)malloc( EB_C_UT_SIZE ); z->cext = 0; } if( c_ef == NULL ) { return ZE_MEM; } z->cextra = c_ef; c_ef += z->cext; /* Now add the local version of the field. */ *l_ef++ = 'U'; *l_ef++ = 'T'; *l_ef++ = (char)(EB_UT_LEN(2)); /* length of data in local EF */ *l_ef++ = (char)0; *l_ef++ = (char)(EB_UT_FL_MTIME | EB_UT_FL_ATIME); *l_ef++ = (char)(s.st_mtime); *l_ef++ = (char)(s.st_mtime >> 8); *l_ef++ = (char)(s.st_mtime >> 16); *l_ef++ = (char)(s.st_mtime >> 24); *l_ef++ = (char)(s.st_atime); *l_ef++ = (char)(s.st_atime >> 8); *l_ef++ = (char)(s.st_atime >> 16); *l_ef++ = (char)(s.st_atime >> 24); z->ext += EB_L_UT_SIZE; /* Now add the central version. */ memcpy(c_ef, l_ef-EB_L_UT_SIZE, EB_C_UT_SIZE); c_ef[EB_LEN] = (char)(EB_UT_LEN(1)); /* length of data in central EF */ z->cext += EB_C_UT_SIZE; return ZE_OK; } /* ---------------------------------------------------------------------- */ /* Add a 'Ux' extra field to the zlist data pointed to by z. */ #define EB_L_UX2_SIZE (EB_HEADSIZE + EB_UX2_MINLEN) #define EB_C_UX2_SIZE (EB_HEADSIZE) local int add_Ux_ef( struct zlist far *z ) { char *l_ef = NULL; char *c_ef = NULL; struct stat s; /* Check to make sure we've got enough room in the extra fields. */ if( z->ext + EB_L_UX2_SIZE > USHRT_MAX || z->cext + EB_C_UX2_SIZE > USHRT_MAX ) { return ZE_MEM; } /* stat() the file (or the symlink) to get the data; if we can't get */ /* the data, there's no point in trying to fill out the fields. */ if(LSSTAT( z->name, &s ) ) { return ZE_OPEN; } /* Allocate memory for the local and central extra fields. */ if( z->extra && z->ext != 0 ) { l_ef = (char *)realloc( z->extra, z->ext + EB_L_UX2_SIZE ); } else { l_ef = (char *)malloc( EB_L_UX2_SIZE ); z->ext = 0; } if( l_ef == NULL ) { return ZE_MEM; } z->extra = l_ef; l_ef += z->ext; if( z->cextra && z->cext != 0 ) { c_ef = (char *)realloc( z->cextra, z->cext + EB_C_UX2_SIZE ); } else { c_ef = (char *)malloc( EB_C_UX2_SIZE ); z->cext = 0; } if( c_ef == NULL ) { return ZE_MEM; } z->cextra = c_ef; c_ef += z->cext; /* Now add the local version of the field. */ *l_ef++ = 'U'; *l_ef++ = 'x'; *l_ef++ = (char)(EB_UX2_MINLEN); *l_ef++ = (char)(EB_UX2_MINLEN >> 8); *l_ef++ = (char)(s.st_uid); *l_ef++ = (char)(s.st_uid >> 8); *l_ef++ = (char)(s.st_gid); *l_ef++ = (char)(s.st_gid >> 8); z->ext += EB_L_UX2_SIZE; /* Now add the central version of the field. */ *c_ef++ = 'U'; *c_ef++ = 'x'; *c_ef++ = 0; *c_ef++ = 0; z->cext += EB_C_UX2_SIZE; return ZE_OK; } /* ---------------------------------------------------------------------- */ /* Add a 'Be' extra field to the zlist data pointed to by z. */ #define EB_L_BE_SIZE (EB_HEADSIZE + EB_L_BE_LEN) /* + attr size */ #define EB_C_BE_SIZE (EB_HEADSIZE + EB_C_BE_LEN) /* maximum memcompress overhead is the sum of the compression header length */ /* (6 = ush compression type, ulg CRC) and the worstcase deflate overhead */ /* when uncompressible data are kept in 2 "stored" blocks (5 per block = */ /* byte blocktype + 2 * ush blocklength) */ #define MEMCOMPRESS_OVERHEAD (EB_MEMCMPR_HSIZ + EB_DEFLAT_EXTRA) local int add_Be_ef( struct zlist far *z ) { char *l_ef = NULL; char *c_ef = NULL; char *attrbuff = NULL; off_t attrsize = 0; char *compbuff = NULL; ush compsize = 0; uch flags = 0; /* Check to make sure we've got enough room in the extra fields. */ if( z->ext + EB_L_BE_SIZE > USHRT_MAX || z->cext + EB_C_BE_SIZE > USHRT_MAX ) { return ZE_MEM; } /* Attempt to load up a buffer full of the file's attributes. */ { int retval; retval = get_attr_dir( z->name, &attrbuff, &attrsize ); if( retval != EOK ) { return ZE_OPEN; } if( attrsize == 0 ) { return ZE_OK; } if( attrbuff == NULL ) { return ZE_LOGIC; } /* Check for way too much data. */ if( attrsize > (off_t)ULONG_MAX ) { zipwarn( "uncompressed attributes truncated", "" ); attrsize = (off_t)(ULONG_MAX - MEMCOMPRESS_OVERHEAD); } } if( verbose ) { printf( "\t[in=%lu]", (unsigned long)attrsize ); } /* Try compressing the data */ compbuff = (char *)malloc( (size_t)attrsize + MEMCOMPRESS_OVERHEAD ); if( compbuff == NULL ) { return ZE_MEM; } compsize = memcompress( compbuff, (size_t)attrsize + MEMCOMPRESS_OVERHEAD, attrbuff, (size_t)attrsize ); if( verbose ) { printf( " [out=%u]", compsize ); } /* Attempt to optimise very small attributes. */ if( compsize > attrsize ) { free( compbuff ); compsize = (ush)attrsize; compbuff = attrbuff; flags = EB_BE_FL_NATURAL; } /* Check to see if we really have enough room in the EF for the data. */ if( ( z->ext + compsize + EB_L_BE_LEN ) > USHRT_MAX ) { compsize = USHRT_MAX - EB_L_BE_LEN - z->ext; } /* Allocate memory for the local and central extra fields. */ if( z->extra && z->ext != 0 ) { l_ef = (char *)realloc( z->extra, z->ext + EB_L_BE_SIZE + compsize ); } else { l_ef = (char *)malloc( EB_L_BE_SIZE + compsize ); z->ext = 0; } if( l_ef == NULL ) { return ZE_MEM; } z->extra = l_ef; l_ef += z->ext; if( z->cextra && z->cext != 0 ) { c_ef = (char *)realloc( z->cextra, z->cext + EB_C_BE_SIZE ); } else { c_ef = (char *)malloc( EB_C_BE_SIZE ); z->cext = 0; } if( c_ef == NULL ) { return ZE_MEM; } z->cextra = c_ef; c_ef += z->cext; /* Now add the local version of the field. */ *l_ef++ = 'B'; *l_ef++ = 'e'; *l_ef++ = (char)(compsize + EB_L_BE_LEN); *l_ef++ = (char)((compsize + EB_L_BE_LEN) >> 8); *l_ef++ = (char)((unsigned long)attrsize); *l_ef++ = (char)((unsigned long)attrsize >> 8); *l_ef++ = (char)((unsigned long)attrsize >> 16); *l_ef++ = (char)((unsigned long)attrsize >> 24); *l_ef++ = flags; memcpy( l_ef, compbuff, (size_t)compsize ); z->ext += EB_L_BE_SIZE + compsize; /* And the central version. */ *c_ef++ = 'B'; *c_ef++ = 'e'; *c_ef++ = (char)(EB_C_BE_LEN); *c_ef++ = (char)(EB_C_BE_LEN >> 8); *c_ef++ = (char)compsize; *c_ef++ = (char)(compsize >> 8); *c_ef++ = (char)(compsize >> 16); *c_ef++ = (char)(compsize >> 24); *c_ef++ = flags; z->cext += EB_C_BE_SIZE; return ZE_OK; } /* Extra field info: - 'UT' - UNIX time extra field - 'Ux' - UNIX uid/gid extra field - 'Be' - BeOS file attributes extra field This is done the same way ../unix/unix.c stores the 'UT'/'Ux' fields (full data in local header, only modification time in central header), with the 'Be' field added to the end and the size of the 'Be' field in the central header. See the end of beos/osdep.h for a simple explanation of the 'Be' EF layout. */ int set_extra_field(z, z_utim) struct zlist far *z; iztimes *z_utim; /* store full data in local header but just modification time stamp info in central header */ { int retval; /* Tell picky compilers to shut up about unused variables. */ z_utim = z_utim; /* Check to make sure z is valid. */ if( z == NULL ) { return ZE_LOGIC; } /* This function is much simpler now that I've moved the extra fields */ /* out... it simplified the 'Be' code, too. */ retval = add_UT_ef( z ); if( retval != ZE_OK ) { return retval; } retval = add_Ux_ef( z ); if( retval != ZE_OK ) { return retval; } retval = add_Be_ef( z ); if( retval != ZE_OK ) { return retval; } return ZE_OK; } /* ---------------------------------------------------------------------- */ /* Set a file's MIME type. */ void setfiletype( const char *file, const char *type ) { int fd; attr_info fa; ssize_t wrote_bytes; fd = open( file, O_RDWR ); if( fd < 0 ) { zipwarn( "can't open zipfile to write file type", "" ); return; } fa.type = B_MIME_STRING_TYPE; fa.size = (off_t)(strlen( type ) + 1); wrote_bytes = fs_write_attr( fd, BE_FILE_TYPE_NAME, fa.type, 0, type, fa.size ); if( wrote_bytes != (ssize_t)fa.size ) { zipwarn( "couldn't write complete file type", "" ); } close( fd ); } int deletedir(d) char *d; /* directory to delete */ /* Delete the directory *d if it is empty, do nothing otherwise. Return the result of rmdir(), delete(), or system(). For VMS, d must be in format [x.y]z.dir;1 (not [x.y.z]). */ { # ifdef NO_RMDIR /* code from Greg Roelofs, who horked it from Mark Edwards (unzip) */ int r, len; char *s; /* malloc'd string for system command */ len = strlen(d); if ((s = malloc(len + 34)) == NULL) return 127; sprintf(s, "IFS=\" \t\n\" /bin/rmdir %s 2>/dev/null", d); r = system(s); free(s); return r; # else /* !NO_RMDIR */ return rmdir(d); # endif /* ?NO_RMDIR */ } #endif /* !UTIL */ /******************************/ /* Function version_local() */ /******************************/ void version_local() { static ZCONST char CompiledWith[] = "Compiled with %s%s for %s%s%s%s.\n\n"; printf(CompiledWith, #ifdef __MWERKS__ "Metrowerks CodeWarrior", "", #else # ifdef __GNUC__ "gcc ", __VERSION__, # endif #endif "BeOS", #ifdef __POWERPC__ " (PowerPC)", #else # ifdef __INTEL__ " (x86)", # else " (UNKNOWN!)", # endif #endif #ifdef __DATE__ " on ", __DATE__ #else "", "" #endif ); } /* end function version_local() */ zip30/beos/Contents0100644000076400000060000000102307020407710012422 0ustar ediskContents of the "beos" sub-directory for Zip 2.2 and later: Contents this file README Notes from the author of the BeOS port Makefile makefile for building (sorry, no project files) beos.c BeOS-specific routines (similar to the UNIX ones) osdep.h BeOS-specific includes and whatnot zipup.h Definitions for zip routines This port supports both Metrowerks CodeWarrior and GNU C as the compiler, and PowerPC and x86 architectures. - Chris Herborth (chrish@pobox.com) June 24, 1998 zip30/beos/Makefile0100644000076400000060000001043010550047664012356 0ustar edisk###################################################################### # # Makefile for Info-ZIP's zip, zipcloak, zipnote, and zipsplit on BeOS # # Copyright © 1999 Info-ZIP # Chris Herborth (chrish@pobox.com) # # This is the new New and Improved Makefile for BeOS; it automatically # detects your platform and uses the appropriate compiler and compiler # flags. ###################################################################### # Things that don't change: # Punish people who don't have SMP hardware. MAKE = make -j 4 -f beos/Makefile SHELL = /bin/sh LN = ln -s BIND = $(CC) AS = $(CC) -c CPP = $(CC) -E INSTALL = install # Target directories prefix = /boot/home/config BINDIR = $(prefix)/bin manext = 1 MANDIR = $(prefix)/man/man$(manext) ZIPMANUAL = MANUAL VERSION = Version 2.3 of __DATE__ ###################################################################### # Things that change: # PowerPC system ifeq "$(BE_HOST_CPU)" "ppc" CC:=mwcc ifeq "$(shell uname -r)" "4.0" CFLAGS:=-O7 -opt schedule604 -rostr -w9 \ -I. -DHAVE_DIRENT_H -DPASSWD_FROM_STDIN LFLAGS1:=-warn else CFLAGS:=-O7 -proc 604e -w9 -I. -DHAVE_DIRENT_H -DPASSWD_FROM_STDIN LFLAGS1:=-nodup endif LFLAGS2:=-L/boot/develop/lib/ppc -lbe -lroot OBJA = TARGET=$(ZIPS) # x86 system else CC:=gcc # Removed -Wconversion and -Wshadow because of the unnecessary warnings # they generate. - Sept. 28, 1999 CFLAGS:=-O3 -mpentiumpro \ -Wall -Wno-multichar -Wno-ctor-dtor-privacy \ -Wbad-function-cast -Woverloaded-virtual \ -I. -I/boot/develop/headers/be/support \ -I/boot/develop/headers/be/storage \ -DHAVE_DIRENT_H -DPASSWD_FROM_STDIN # -DASMV LFLAGS1:= LFLAGS2:=-L/boot/develop/lib/x86 -lbe -lroot OBJA = #match.o TARGET=$(ZIPS) endif ###################################################################### # Helpful targets all: $(MAKE) CC=$(CC) CFLAGS="$(CFLAGS)" \ LFLAGS1="$(LFLAGS1)" LFLAGS2="$(LFLAGS2)" \ $(TARGET) ###################################################################### # Object file lists and other build goodies # Object file lists OBJZ = zip.o zipfile.o zipup.o fileio.o util.o globals.o crypt.o ttyio.o \ beos.o crc32.o OBJI = deflate.o trees.o # OBJA moved into ifeq block above; we'll use assembly for x86 OBJU = zipfile_.o fileio_.o util_.o globals.o beos_.o OBJN = zipnote.o $(OBJU) OBJC = zipcloak.o $(OBJU) crc32_.o crypt_.o ttyio.o OBJS = zipsplit.o $(OBJU) # Headers ZIP_H = zip.h ziperr.h tailor.h beos/osdep.h # What to build? ZIPS = zip zipnote zipsplit zipcloak # suffix rules .SUFFIXES: .SUFFIXES: _.o .o .c .doc .1 .c_.o: rm -f $*_.c; $(LN) $< $*_.c $(CC) -c $(CFLAGS) -DUTIL $*_.c rm -f $*_.c .c.o: $(CC) -c $(CFLAGS) $< .1.doc: groff -man -Tascii $< > $@ # rules for zip, zipnote, zipcloak, zipsplit, and the Zip MANUAL. $(OBJZ): $(ZIP_H) $(OBJI): $(ZIP_H) $(OBJN): $(ZIP_H) $(OBJS): $(ZIP_H) $(OBJC): $(ZIP_H) zip.o crc32.o crypt.o fileio.o zipfile.o zipup.o: crc32.h zipcloak.o crc32_.o crypt_.o fileio_.o zipfile_.o: crc32.h zip.o zipup.o crypt.o ttyio.o zipcloak.o crypt_.o: crypt.h zip.o zipup.o zipnote.o zipcloak.o zipsplit.o: revision.h zip.o crypt.o ttyio.o zipcloak.o crypt_.o: ttyio.h zipup.o: beos/zipup.h match.o: match.S $(CPP) match.S > _match.s $(AS) _match.s mv -f _match.o match.o rm -f _match.s beos.o: beos/beos.c $(CC) -c $(CFLAGS) beos/beos.c beos_.o: beos/beos.c rm -f $*_.c; $(LN) beos/beos.c $*_.c $(CC) -c $(CFLAGS) -DUTIL $*_.c rm -f $*_.c zips: $(ZIPS) zipsman: $(ZIPS) $(ZIPMANUAL) zip: $(OBJZ) $(OBJI) $(OBJA) $(BIND) -o zip $(LFLAGS1) $(OBJZ) $(OBJI) $(OBJA) $(LFLAGS2) zipnote: $(OBJN) $(BIND) -o zipnote $(LFLAGS1) $(OBJN) $(LFLAGS2) zipcloak: $(OBJC) $(BIND) -o zipcloak $(LFLAGS1) $(OBJC) $(LFLAGS2) zipsplit: $(OBJS) $(BIND) -o zipsplit $(LFLAGS1) $(OBJS) $(LFLAGS2) $(ZIPMANUAL): man/zip.1 groff -man -Tascii man/zip.1 > $(ZIPMANUAL) # install install: $(ZIPS) $(INSTALL) -m755 $(ZIPS) $(BINDIR) mkdir -p $(MANDIR) $(INSTALL) -m644 man/zip.1 $(MANDIR)/zip.$(manext) uninstall: -cd $(BINDIR); rm -f $(ZIPS) -cd $(MANDIR); rm -f zip.$(manext) dist: $(ZIPMANUAL) zip -u9T zip`sed -e '/VERSION/!d' -e 's/.*"\(.*\)".*/\1/' \ -e s/[.]//g -e q revision.h` \ `awk '/^Makefile/,/vms_zip.rnh/ {print $$1}' < contents` # clean up after making stuff and installing it clean: rm -f *.o $(ZIPS) flags # end of Makefile zip30/beos/osdep.h0100644000076400000060000000425107011110574012172 0ustar edisk/* Copyright (c) 1990-1999 Info-ZIP. All rights reserved. See the accompanying file LICENSE, version 1999-Oct-05 or later (the contents of which are also included in zip.h) for terms of use. If, for some reason, both of these files are missing, the Info-ZIP license also may be found at: ftp://ftp.cdrom.com/pub/infozip/license.html */ #include #include #include #include /* for B_NO_ERROR */ #define USE_EF_UT_TIME /* Enable use of "UT" extra field time info */ #define EB_L_BE_LEN 5 /* min size is an unsigned long and flag */ #define EB_C_BE_LEN 5 /* Length of data in local EF and flag. */ #define EB_BE_FL_NATURAL 0x01 /* data is 'natural' (not compressed) */ #define EB_BE_FL_BADBITS 0xfe /* bits currently undefined */ #ifndef ZP_NEED_MEMCOMPR # define ZP_NEED_MEMCOMPR #endif /* Set a file's MIME type. */ #define BE_FILE_TYPE_NAME "BEOS:TYPE" void setfiletype( const char *file, const char *type ); /* DR9 'Be' extra-field layout: 'Be' - signature ef_size - size of data in this EF (little-endian unsigned short) full_size - uncompressed data size (little-endian unsigned long) flag - flags (byte) flags & EB_BE_FL_NATURAL = the data is not compressed flags & EB_BE_FL_BADBITS = the data is corrupted or we can't handle it properly data - compressed or uncompressed file attribute data If flag & EB_BE_FL_NATURAL, the data is not compressed; this optimisation is necessary to prevent wasted space for files with small attributes (which appears to be quite common on the Advanced Access DR9 release). In this case, there should be ( ef_size - EB_L_BE_LEN ) bytes of data, and full_size should equal ( ef_size - EB_L_BE_LEN ). If the data is compressed, there will be ( ef_size - EB_L_BE_LEN ) bytes of compressed data, and full_size bytes of uncompressed data. If a file has absolutely no attributes, there will not be a 'Be' extra field. The uncompressed data is arranged like this: attr_name\0 - C string struct attr_info (big-endian) attr_data (length in attr_info.size) */ zip30/beos/README0100644000076400000060000000177507020407702011601 0ustar ediskInfo-ZIP's zip for BeOS KNOWN BUGS - None! (as of zip 2.21) - building on x86 BeOS generates a hell of a lot of bugs; I'm not going to worry about them until Be fixes their headers though... FEATURES - stores BeOS file attributes, compressing them if possible (as of 2.21, this works properly for symbolic links, too; as of 2.3, this works properly for symbolic links whether you're storing them as links or not) - zip files are created with the correct file type (application/zip) - supports both Metrowerks CodeWarrior (PowerPC platform) and GNU C (x86 platform), automatically picking the default compiler for each architecture Please report any bugs to the Zip-Bugs mailing list; our email address is zip-bugs@lists.wku.edu. If it's something BeOS-specific, you could email me directly. Visit the Info-ZIP web site (http://www.cdrom.com/pub/infozip/) for all the latest zip and unzip information, FAQs, source code and ready-to-run executables. - Chris Herborth (chrish@pobox.com) April 2/1999 zip30/beos/zipup.h0100644000076400000060000000112407011110602012213 0ustar edisk/* Copyright (c) 1990-1999 Info-ZIP. All rights reserved. See the accompanying file LICENSE, version 1999-Oct-05 or later (the contents of which are also included in zip.h) for terms of use. If, for some reason, both of these files are missing, the Info-ZIP license also may be found at: ftp://ftp.cdrom.com/pub/infozip/license.html */ #ifndef O_RDONLY # include #endif #define fhow O_RDONLY #define fbad (-1) typedef int ftype; #define zopen(n,p) open(n,p) #define zread(f,b,n) read(f,b,n) #define zclose(f) close(f) #define zerr(f) (k == (extent)(-1L)) #define zstdin 0 zip30/Betas_Readme.txt0100644000076400000060000000120211002665240013024 0ustar ediskBetas are works in progress. When a beta has a seemingly stable set of features, we may post a public beta so outside developers can see where the code is going and make contributions or comment. A Release Candidate is a beta that we believe has the full feature set that will be released. It's still being tested, and things can still change, but we thought it close when we posted it. We take suggestions, bug fixes, and patches at any time, so send them in. We make no guarantees as to the state of betas so use at your own risk. All code, including releases, are released under the Info-ZIP license. Enjoy! Ed Gordon 20 April 2008 zip30/BUGS0100644000076400000060000000054406254362752010462 0ustar edisk- zip sometimes crashes on some versions of NetBSD (0.8, 0.9 and early 0.9-current), FreeBSD (<= 1.1) and BSDI (< 1.1) . This is due to a bug in stdio. Upgrading the stdio package in /usr/src/lib/libc/stdio should fix the problem. See *BSD mirrors in src/lib/libc/stdio You must at least replace setvbuf.o in all the libc's with a newer version. zip30/bzip2/0040755000076400000060000000000011033727770011021 5ustar ediskzip30/bzip2/install.txt0100644000076400000060000002206411031355136013220 0ustar ediskHOW TO ADD BZIP2 SUPPORT TO ZIP This document describes how to add bzip2 support to Zip. Compiling or linking in the bzip2 library adds an additional bzip2 compression method to Zip. This new method can be selected instead of the Zip traditional compression method deflation to compress files and often gives a better compression ratio (perhaps at the cost of greater CPU time). The compression method is specified using the "-Z method" command-line option, where "method" may be either "deflate" (the default), or "bzip2" (if Zip is built with bzip2 support). Zip has been tested with bzip2 library 1.0.5 and earlier. Notes Compression method bzip2 requires a modern unzip. Before using bzip2 compression in Zip, verify that a modern UnZip program with bzip2 support will be used to read the resulting zip archive so that entries compressed with bzip2 (compression method 12) can be read. Older unzips probably won't recognize the compression method and will skip those entries. The Zip source kit does not include the bzip2 library or source files, but these can be found at "http://www.bzip.org/" for example. See below for how to add bzip2 to Zip for various operating systems. Zip using bzip2 compression is not compatible with the bzip2 application, but instead provides an additional way to compress files before adding them to a Zip archive. It does not replace the bzip2 program itself, which creates bzip2 archives in a different format that are not compatible with zip or unzip. The bzip2 code and algorithms are provided under the bzip2 license (provided in the bzip2 source kit) and what is not covered by that license is covered under the Info-ZIP license. Info-ZIP will look at issues involving the use of bzip2 compression in Zip, but any questions about the bzip2 code and algorithms or bzip2 licensing, for example, should be directed to the bzip2 maintainer. Installation To build Zip with bzip2 support, Zip generally needs one bzip2 header file, "bzlib.h", and the object library, typically "libbz2.a", except in cases where the source files are compiled in directly. If you are either compiling the bzip2 library or compiling in the bzip2 source files, we recommend defining the C macro BZ_NO_STDIO, which excludes a lot of standalone error code (not used when bzip2 is used as a library and makes the library smaller) and provides hooks that Zip can use to provide better error handling. However, a standard bzip2 object library will work, though any errors that bzip2 generates may be more cryptic. Building the bzip2 library from the bzip2 source files (recommended): Download the latest bzip2 package (from "http://www.bzip.org/", for example). Unpack the bzip2 source kit (bzip2-1.0.5.tar.gz was current as of this writing, but the latest should work). Read the README file in the bzip2 source kit. Compile the bzip2 library for your OS, preferably defining BZ_NO_STDIO. Note: On UNIX systems, this may be done automatically when building Zip, as explained below. Installation on UNIX (see below for installation on other systems): Note: Zip on UNIX uses the "bzlib.h" include file and the compiled "libbz2.a" library to static link to bzip2. Currently we do not support using the shared library (patches welcome). The easiest approach may be to drop the two above files in the bzip2 directory of the Zip source tree and build Zip using the "generic" target, that is, using a command like make -f unix/Makefile generic If all goes well, make should confirm that it found the files and will be compiling in bzip2 by setting the BZIP2_SUPPORT flag and then including the libraries while compiling and linking Zip. To use bzlib.h and libbz2.a from somewhere else on your system, define the "make" macro IZ_BZIP2 to point to that directory. For example: make -f unix/Makefile generic IZ_BZIP2=/mybz2 where /mybz2 might be "/usr/local/src/bzip2/bzip2-1.0.5" on some systems. Only a compiled bzip2 library can be pointed to using IZ_BZIP2 and Zip will not compile bzip2 source in other than the bzip2 directory. If IZ_BZIP2 is not defined, Zip will look for the bzip2 files in the "bzip2" directory in the Zip source directory. The bzip2 directory is empty in the Zip source distribution (except for this install.txt file) and is provided as a place to put the bzip2 files. To use this directory, either drop bzlib.h and libbz2.a in it to use the compiled library as noted above or drop the contents of the bzip2 source kit in this directory so that bzlib.h is directly in the bzip2 directory and Zip will try to compile it if no compiled library is already there. Unpacking bzip2 so Zip compiles it: To make this work, the bzip2 source kit must be unpacked directly into the Zip "bzip2" directory. For example: # Unpack the Zip source kit. gzip -cd zip30.tar-gz | tar xfo - # Move down to the Zip kit's "bzip2" directory, ... cd zip30/bzip2 # ... and unpack the bzip2 source kit there. gzip -cd ../../bzip2-1.0.5.tar.gz | tar xfo - # Move the bzip2 source files up to the Zip kit's bzip2 directory. cd bzip2-1.0.5 mv * .. # Return to the Zip source kit directory, ready to build. cd ../.. # Build Zip. make -f unix/Makefile generic Using a system bzip2 library: If IZ_BZIP2 is not defined and both a compiled library and the bzip2 source files are missing from the Zip bzip2 directory, Zip will test to see if bzip2 is globally defined on the system in the default include and library paths and, if found, link in the system bzip2 library. This is automatic. Preventing inclusion of bzip2: To build Zip with _no_ bzip2 support on a system where the automatic bzip2 detection scheme will find bzip2, you can specify a bad IZ_BZIP2 directory. For example: make -f unix/Makefile generic IZ_BZIP2=no_such_directory You can also define NO_BZIP2_SUPPORT to exclude bzip2. Verifying bzip2 support in Zip: When the Zip build is complete, verify that bzip2 support has been enabled by checking the feature list: ./zip -v If all went well, bzip2 (and its library version) should be listed. Installation on other systems MSDOS: Thanks to Robert Riebisch, the DJGPP 2.x Zip port now supports bzip2. To include bzip2, first install bzip2. The new msdos/makebz2.dj2 makefile then looks in the standard bzip2 installation directories for the needed files. As he says: It doesn't try to be clever about finding libbz2.a. It just expects bzip2 stuff installed to the default include and library folders, e.g., "C:\DJGPP\include" and "C:\DJGPP\lib" on DOS. Given a standard DJGPP 2.x installation, this should create a version of Zip 3.0 with bzip2 support. The bzip2 library for DJGPP can be found on any DJGPP mirror in "current/v2apps" (or "beta/v2apps/" for the latest beta). This library has been ported to MSDOS/DJGPP by Juan Manuel Guerrero. WIN32 (Windows NT/2K/XP/2K3/... and Windows 95/98/ME): For Windows there seems to be two approaches, either use bzip2 as a dynamic link library or compile the bzip2 source in directly. I have not gotten the static library libbz2.lib to work, but that may be me. Using bzip2 as a dynamic link library: Building bzip2: If you have the needed bzlib.h, libbz2.lib, and libbz2.dll files you can skip building bzip2. If not, open the libbz2.dsp project and build libbz2.dll This creates debug/libbz2.lib and libbz2.dll Building Zip: Copy libbz2.lib to the bzip2 directory in the Zip source tree. This is needed to compile Zip with bzip2 support. Also copy the matching bzlib.h from the bzip2 source to the same directory. Add libbz2.lib to the link list for whatever you are building. Also define the compiler define BZIP2_SUPPORT. Build Zip. Using Zip with bzip2 as dll: Put libbz2.dll in your command path. This is needed to run Zip with bzip2 support. Verify that bzip2 is enabled with the command zip -v You should see bzip2 listed. Compiling in bzip2 from the bzip2 source: This approach compiles in the bzip2 code directly. No external library is needed. Get a copy of the bzip2 source and copy the contents to the bzip2 directory in the Zip source tree so that bzlib.h is directly in the bzip2 directory. Use the vc6bz2 project to build Zip. This project knows of the added bzip2 files. Verify that bzip2 is enabled with the command zip -v Windows DLL (WIN32): Nothing yet. Mac OS X: Follow the standard UNIX build procedure. Mac OS X includes bzip2 and the UNIX builders should find the bzip2 files in the standard places. Note that the version of bzip2 on your OS may not be current and you can instead specify a different library or compile your own bzip2 library as noted in the Unix procedures above. OS/2: Nothing yet. VMS (OpenVMS): See [.vms]install_vms.txt for how to enable bzip2 support on VMS. Last updated 26 March 2007, 15 July 2007, 9 April 2008, 27 June 2008 S. Schweda, E. Gordon zip30/CHANGES0100644000076400000060000063266211033727574011004 0ustar edisk------------------------- August 7th 1996 version 2.2a ------------------ 1. QDOS port (Jonathan Hudson) 2. win32 volumelabel handling (Paul) 3. VM/CMS clean up (Greg Hartwig) 4. leading "../" in internal filenames are allowed (Paul) 5. System V packages support (John Bush) 6. Fix handling of atx in zipup() (Onno, Greg) 7. Fixed typo that caused zip -R to dump core (Onno) 8. msdos/makefile.dj2: fix for command line too long when linking zip.exe 9. win95 long filename support with djgpp v2 (Onno, Kimio Itoh) ------------------------- August 9th 1996 version 2.2b ------------------ 1. windll: use wiz instead of wizip (Mike) 2. use z->name NOT z->zname to open files (Onno, Mike) ------------------------ September 1st 1996 version 2.2c ------------------ 1. windll: use fprintf instead of putc to send data to std{out,err} (Mike) 2. os2: make borlandc version detection equal to unzip 5.30d (Kai Uwe) 3. use #elif constructions for msdos,os2 and win32 compiler detection (Onno) 4. fix for incorrect free in zip.c (Onno, Mike, Steve) 5. BeBox port from Chris 6. unix/{configure,Makefile} fixes for SCO Xenix 286 (Tom Schmidt) 7. remove zilog entry from unix/Makefile (Onno) 8. man page fixes (Tom Schmidt) 9. SCO ODT {3,5} fixes (Bill Davidsen) ------------------------ October 8th 1996 version 2.2d ------------------ 1. Fix bug in QDOS patch that broke zipsplit.c (Onno, Paul) 2. Fix a couple of warnings from BorlandC (Mike) 3. msdos/makefile.wat: Delete some more files when cleaning up (Paul) 4. store msdos volumelabels without a dot in them (Paul) 5. clean up of unix/{Makefile,configure,packaging} (Tom Schmidt) 6. make QDOS port case independent (Jonathan Hudson) 7. new amiga SASC makefile (Walter Haidinger) 8. don't truncate filenames in win32's in2ex() (Paul) 9. os2/makefile.os2 update for emx 0.9c (Kai Uwe) 10. password() function for QDOS (Jonathan) 11. fix the last(?) free() related bug (Mike) 12. win32: security descriptors operations (Scott Field) 13. win32: FILE_SHARE_DELETE is not defined in some win32 compilers (Onno) 14. win32: fix makefile.wat to include nt.c (Onno) ------------------------ January 17th 1997 version 2.2e ------------------ 1. define USE_CASE_MAP in osdep.h for those ports that need it (Onno) 2. define PROCNAME in osdep.h for those ports that need it (Onno) 3. wild() prototype decl only if PROCNAME defined => delete MSVMS define (Onno) 4. add DOS EMX makefile (E-Yen Tan) 5. include a little earlier in qdos/qdos.c (Jonathan) 6. add ttyio.o to OBJZ in qdos/Makefile.qdos (Jonathan) 7. remove unused fprintebc define from zip.c (Onno) 8. use the right password routine in ttyio.c for unzip (Mike) 9. BeOS update from Chris 10. Fix for 'zip -r foo x:' (Paul) 11. Fix library bug on beos (Chris) 12. Fix calculating version number (kitoh_@mix.or.jp, Walter Haidinger) 13. IsWinNT always returned TRUE (Mike) 14. Windll update from Mike 15. Improved crc routines for x86 from Scott Field 16. Detect in unix/configure if we can use crc_i386.S (Onno) 17. Fix spurious internal logic error (Paul) 18. Fix to include directory names on the Acorn when needed (Sergio) 19. include zip.h in mvs.h (Onno, George Carr) 20. add workaround for AZTEC C compiler bug to revision.h (Paul, Walter) 21. MVS doesn't have rmdir (George Carr) 22. define and use USE_ZIPMAIN for WINDLL en VM_CMS (Onno) 23. Fixes from Greg Hartwig to make CMS standalone versions possible. 24. Move OS specific encryption stuff to the os specific directories (Christian) 25. Change password fetching interface in ttyio and crypt (Christian) 26. Update emx support for 0.9c (Christian) 27. Define WINDLL instead of MSWIN (Christian) 28. Extended time stamp extra field format support (Christian) 29. Support for rsxnt-emx 0.9c win32 compiler (Christian) 30. Use izshr017b (Christian) ------------------------ March 11th 1997 version 2.2f ------------------ 1. Move makefile.emx, rsxwinnt.h and zip.def to win32 subdir (Kai Uwe) 2. Add win32 target to makefile.os2 to allow cross compilation (Kai Uwe) 3. Fix NTSD_EAS link time failures with win32 (Paul) 4. Fix buffer freed too early in password verification code (Mike) 5. Remove unix/zipgrep and man/zipgrep.1 (sanvila@ctv.es) 6. Only use crc_i386.o when we're using an x86 (Onno, Mark) 7. Remove carriage returns from amiga/crc_68.a (Paul) 8. New windll from Mike 9. Fix typo in os2/os2zip.c (Kai Uwe) 10. Don't use ctime (last file status change) for unix and qdos cross compile (Greg) 11. added gccwin32 crosscompilation target (RSXNT) to os2/makefile.os2 (Kai Uwe) 12. fixed the OS/2 file attribute and time stamp generation for zipping stdin ("-") (Kai Uwe) 13. fixed the atime and ctime stat fields for the OS/2 Watcom C library (Kai Uwe) 14. added atime and ctime support for the UT extra field when generated under OS/2, the atime and ctime values are only stored when zipping (Kai Uwe) 15. qdos patches from Jonathan Hudson mainly for extended time flag handling 16. amiga aztec compiler bug workaround (Paul) 17. fix -v output of zipcloak, zipnote and zipsplit (Paul) 18. new amiga/makefile.azt with targets for debug versions (Paul) ------------------------ March 31st 1997 version 2.2g ------------------ 1. remove -I/usr/local/include from unix/Makefile (Chris) 2. Update versinfolines in revision.h (Greg) 3. change 1U to 0x1 to accomodate non ANSI compilers (Onno, Rodney Brown) 4. win32zip.c: cast buffer parameter in memcompress() to char * (Mike) 5. remove beos/zipgrep (Chris) 6. correct the -e password verification check in zip.c (Christian) 7. use ZCONST instead of const in the generic code. (Christian) 8. fix mktime timezone correction when time is near to daylight/nodaylight switch points. (Christian) 9. correct dependencies in makefile.os2 (Christian) 10. use a more sensible default for iztime.ctime than "0" when system does not not support creation time stamps. (Christian) 11. fix VMS_PK_EXTRA function interface declarations. (Christian) 12. implement atime/ctime support in win32. (Christian) 13. win32/win32.c: replacement getch() for Watcom. (Paul) 14. win32/makefile.wat: debug object files kept separate. (Paul) 15. msdos/makefile.wat: debug object files kept separate. (Paul) 16. Fix extended time defines for the acorn. (Sergio) 17. Define PROCNAME() in acorn/osdep.h (Sergio) 18. Ignore exit status of ${INSTALL_D} in unix/Makefile (Chris) 19. Add Metroworks and BEOS info to version() in several files (Chris) 20. Move defines for the password fetch to zip.h (Christian) 21. Support the obsolete version rsxnt 1.1 / emx 0.9b (Christian) 22. Remove obsolete "#define PROCNAME ..." from cmsmvs/cmsmvs.h (Christian) 23. Fix extended time defines for qdos (Jonathan Hudson) 24. Use watcom getch() from unz530q in win32/win32.c (Onno) 25. Don't install zipgrep via the unix package tools (John Bush) 26. use izshr021 (Onno) 27. Fix zipnote: use iname not zname in zipnote.c (Onno) 28. Create proginfo directory (Christian) ------------------------ May 5th 1997 version 2.2h -------------------- 1. Fix vms/zipup.h: iztime --> iztimes (Onno, Mike Freeman) 2. Remove windll/wizdll.def (Mike) 3. Add a couple of external variable declaration to windll.h (Mike) 4. Remove zipgrep from install in unix/Makefile (Onno) 5. Make updating .zip files with extended time fields possible (Kai Uwe) 6. Delete beos/Makefile.gcc, beos/Makefiles handles both compilers (Chris) 7. Fixes for unused variables (Chris) 8. Added very simplistic example how to load and call the windll (Mike) 9. Updated windll documentation to note this example (Mike) 10. Removed an unused memeber of a structure in windll (Mike) 11. Add BUGS instead of infozip.who and algorith.doc with the packaging tools (John Bush) 12. tailor.h: increment NUM_HOSTS to keep in sync with UnZip (Christian) 13. win32/osdep.h: remove NO_SECURE_TESTS define (Christian) 14. zip.h: add declaration for free_crc_table() (Christian) 15. windll: move everything that's not windows specific into api.* (Mike) 16. use iname when checking for directory names in zipfile.c (Sergio) 17. improved mktime.c with better error checking (Christian) 18. improved crc routines (Christian, Rodney Brown) 19. get the -z option working again (Onno, Brad Clarke) 20. define BROKEN_FSEEK and seekable() for those systems where fseek() always returns 0 (== OK) (Onno, Jeffrey Altman) ------------------------ May 10th 1997 version 2.2i -------------------- 1. win32's seekable should only check for FILE_TYPE_DISK (Onno, Jeffrey Altman) 2. add (ulg) cast to zipbeg = ~0 in zipfile.c (Steve) 3. seekable() *really* belongs in flush_block, keep it there (Onno) 4. seekable() calls fseekable(FILE *) (Onno) 5. define HAVE_FSEEKABLE if a port has their own fseekable (Onno) 6. WatCom doesn't have _get_osfhandle, use _os_handle instead (Paul) 7. upgrade to Mike's latest windll sources (Mike) 8. add -P option so you can specify a password on the commandline (Onno) 9. Get -@ working again (Onno) 10. emx+RSXNT doesn't know about _get_osfhandle() (Kai Uwe) 11. fix a couple of typos in the OS/2 makefiles (Kai Uwe) 12. fix initialization bug in windll code (Mike) 13. tweak deletedir for RISC OS (Sergio) 14. RISCOS doesn't know about fstat() (Sergio) 15. Remove acorn/acorn (Sergio) 16. Delete debugging statements from version_local() in msdos.c (Greg) 17. Fix huge bug in readzipfile() (Onno) ------------------------ May 18th 1997 version 2.2j -------------------- 1. Add missing ';' after return ZE_PARMS in zip.c (Mike) 2. Remove obsolete 'struct stat st' in zipfile.c (Onno) 3. Get Amiga SFX handling working again (Paul) 4. Get zip -A working again (Onno) 5. Change an && to & in zipfile.c (Johnny) 6. Fix handling of empty sfx archives (Onno, Mike) 7. Remove experimental entries from the makefiles (Jean-loup) 8. Add exit codes to the manual page (Onno) 9. Remove lines from the help screen that contain lesser used options (Onno) ------------------------ June 8th 1997 version 2.2k -------------------- 1. use zip -t ddmmyyyy for year 2000 stuff (Greg) 2. zip -@ only handles ONE filename per line (Jean-loup) 3. beos support for DR9 filesystem and symlinks (Chris) 4. VB support for windll (Mike) ------------------------ June 10th 1997 version 2.2l ------------------- 1. beos filetype support (Chris) 2. fill the buffer in getnam() to get it working again (Onno) 3. implement -x@filename and -i@filename (Onno) ------------------------ June 22nd 1997 version 2.2m ------------------- 1. Add a ; after de nextarg label in main() (Onno, Erik Baatz) 2. Initialize p to NULL in get_filters() (Onno, Frank Donahoe) 3. Fix typo in first if statement in filetypes() (Johnny Lee) 4. zip -A works again (Onno, Greg) 5. don't free zipbuf for VMS and CMS_MVS in main() (Onno, Mike Freeman) 6. fix make_zip.com, link_zip.com and vmsdefs.h for gcc 2.6.3 on VMS (Onno) 7. clarify -g option in the man page (Jean-loup) ------------------------ July 6th 1997 version 2.2n ------------------- 1. use local in readzipfile2() declaration (Onno, Mike Freeman) 2. return values with windll in get_filters() (Mike) 3. a couple of minor patches for BEOS (Chris) 4. zip -g works again (Onno, Chris) 5. Some more Visual Basic dll support (Mike) 6. Fix stack overflow in readzipfile() for DOS (Onno, Michael Mauch) ------------------------ August 19th 1997 version 2.2o ------------------- 1. beos README and Makefile tweaks from Chris. 2. Syntax corrections for README and man/zip.1 (Frank Donahoe) 3. Use name not iname when deleting directories in trash() (Christian) 4. change several wkuvx1 to lists in e-mail addresses (Christian) 5. default to PK style extra fields for VMS (Christian) 6. use izshr023 (Christian) 7. replace buggy time library functions (Walter Haidinger, Paul, Christian) 8. in2ex() and stat() are needed also when UTIL isn't defined (Greg Hartwig) 9. don't use type=record in fopen() for MVS and CMS (Greg Hartwig) 10. Change P and K literals to hex for EBCDIC systems (Greg Hartwig) 11. Add output path support for CMS and MVS (Greg Hartwig) 12. Add memtoasc and memtoebc for EBCDIC systems (Greg Hartwig) 13. Handle comments correctly to fix zipnote for CMS and MVS (Greg Hartwig) 14. Add -tt option (do not operate on files after date mmddyy) (Christian) 15. move alloc routines for DOS into the !UTIL block (Christian) 16. move UTIL blocks and version_local() functions to a more logical place (Christian) 17. Handle -P, -R, -x@, -i@ and -tt for the VMS CLI (Christian) 18. Update VMS help file with the new options (Christian) 19. Use iname in MATCH, not zname (Jonathan Hudson) 20. windll: more Visual Basic support (Mike) 21. windll: more project makefiles (Mike) 22. windll: insert Zip in front of global variable names (Mike) ------------------------ August 25th 1997 version 2.2p ------------------- 1. Remove unused flags from LFLAGS2 in unix/Makefile (Onno) 2. SunOS make bug: change unix_.o rule in unix/Makefile (Onno, Mike Freeman) 3. ZipIsWinNT() instead of IsWinNT() in zip.h (Mike) 4. Fix -t and -tt behaviour for windll (Mike) 5. Remove windll makefiles that are now elsewhere (Mike) 6. BEOS: preserve file attributes associated with symbolic links (Chris) 7. No need to use in2ex() for ziputils (Christian) 8. Fix comment handling for EBCDIC systems (Christian) 9. EBCDIC conversion for entry names read from zipfile in UTIL mode (Christian) 10. Fix "fatal" error messages on EBCDIC systems (Christian) 11. zipnote.c: Fix handling of entry name changes for EBCDIC systems (Christian) 12. removed a large part of "dead" code from ziputils version (Christian) 13. use z->iname in comparison functions for sorting (Christian) 14. new installation utils for the acorn (Sergio) 15. use LSSTAT in set_extra_field for unix and beos (Onno) 16. perror(z->zname) instead of perror("zip warning") (Onno, Geoff Pennington) 17. Amiga SFX should work again (Paul) 18. refer to zip22 in install.doc (Frank Donahoe) ------------------------ September 10th 1997 version 2.2q ------------------- 1. Change .doc to .txt, these aren't MS-Word documents (John D. Mitchell) 2. Change msdos$_(OBJ) to msdos_$(OBJ) (Kai Uwe) 3. Fix a couple of amiga related glitches (Paul) 4. Support for DOS packed .exe files in makefile.dj2 (Frank Donahoe) 5. Change warning message for zip -A (Greg) ------------------------ September 29th 1997 version 2.2r ------------------- 1. Fix make svr4package (Eric Baatz) 2. Fix VMS warning (Mike Freeman, Christian) 3. Clean up beos gcc port and beos README (Chris) -------------------------- October 6th 1997 version 2.2s -------------------- 1. Change lpPrint to lpZipPrint for windll (Mike) 2. Change lpPassword to lpZipPassword for windll (Mike) 3. Amiga timezone fixes (Paul) 4. WatCom C 11.0 makefile fixes (Paul) 5. Tandem port from Dave Smith 6. Corrections and updates for install.txt (Christian) 7. Minor VMS README update (Christian) -------------------------- October 12th 1997 version 2.2t -------------------- 1. qdos compiler bug workaround (Jonathan) 2. prevent storing qdos specific filenames that exceed filesystem limits (Jonathan) 3. fix undelimited comment in fileio.c (Frank Donahoe) 4. disable storing of symlinks in BEOS until OS support is available (Chris) 5. Init hash_head to 0 in amiga/deflate.a (Paul) 6. Upgrade to izshr025 (Christian) 7. don't add ".zip" to ZIP name for TANDEM (Dave Smith) 8. use zipup.h not tandem.h in zipup.c (Dave Smith) 9. rename history to CHANGES (Onno) 10. rename install.txt to INSTALL (Onno) 11. rename zip.txt to ZIPMAN (Onno) 12. create WHATSNEW (Onno) -------------------------- October 15th 1997 version 2.2u -------------------- 1. Use Info-ZIP instead of Info-Zip (Christian) 2. Note recent filename changes in several files (Christian) 3. Remove a couple of items from the TODO list (Christian, Onno) 4. Add windll port, zip -t yyyymmdd and zip -R to WHATSNEW (Christian) 5. VMS documentation cleanups and clarifications (Christian) 6. dist entry in unix/Makefile (Onno) 7. remove duplicate amiga/timezone.txt (Christian) 8. rename ZIPMAN to MANUAL and update a couple of files regarding this (Onno) -------------------------- October 24th 1997 version 2.2v -------------------- 1. izshr026: in WHERE wiz40 instead of wiz30 (Christian) 2. izshr026: another couple of Info-ZIP spelling fixes (Christian) 3. Remove zipgrep from the makefiles that still had it (Christian) 4. Update makefiles to handle the MANUAL renaming change (Christian) 5. Fix the last daylight savings bug on the Amiga (Paul) 6. Fix the SCO Unix specialty detection in unix/configure (Onno, bug reported by Bo Kullmar for Solaris 2.6 and with uname -X output for SCO Unix from ken@apisys.com and dgsmith@vnet.ibm.com) 7. Update WHERE and amiga/time_lib.c from unzip 5.32g (Greg) -------------------------- October 26th 1997 version 2.2w -------------------- 1. Additional +Onolimit check in unix/configure (Onno, Peter Jones) 2. Use ZIPERR macro instead of ziperr (Christian) 3. initialize z->lflg for zip entries without extra field (Christian) 4. "local (+ locextend)" vs. "central" header consistency check (Christian) 5. Override local header values with central header values with -A and differences between these headers (Christain) 6. made "deltaoff" signed long; offset adjustment may be negative (Christian) 7. fix a number of "wild" deallocation bugs (Christian) 8. When zipping from a FAT drive (only 8.3 DOS names) under OS/2 or WIN32, set z->vem to "OS_DOS | ". Mark as "made by DOS PKZIP 2.0" only when dosify was requested. (Christian) 9. DOS port should not store fake unix style external attributes. (Christian) 10. amiga/time_lib.c from izshr028 (Christian) -------------------------- October 31st 1997 version 2.2y -------------------- 1. amiga/time_lib.c from izshr029 (Christian) 2. Turbo C++ version code clarification (E-Yen Tan) 3. Fix spelling in cmsvms/zipname.conven (Rodney Brown) 4. Fix memset check in unix/configure for Unixware 2.1.1 (Rodney Brown) 5. Forward declaration fixes for HP-UX bundled compiler (Rodney Brown) -------------------------- November 3rd 1997 version 2.2 -------------------- 1. Update WHERE (Greg). -------------------------- January 4th 1998 version 2.21a ------------------- 1. BSD friendly version of version_local() in unix/unix.c (Onno) 2. No NT versions in DOS version_local() (Steve Salisbury) 3. -t mmddyyyy instead of -t ddmmyyyy in WHATSNEW (Walter Haidinger) 4. use generic fseekable() for rsxnt (Christian) 5. Fix MSC 8.x warnings (Christian, Steve Salisbury) 6. win32 Borland C++ makefile (E-Yen Tan) 7. Tandem doesn't know about extensions like .zip,.arj, ... (Dave Smith) 8. Use dosmatch for EMX and DJGPP too (Christian) 9. dummy djgpp startup functions to remove command line globbing and recognition of environment variables from djgpp.env (Christian) 10. include DJGPP_MINOR in DOS version_local() (Christian) 11. TC 2.0 doesn't have mktime() (Christian, mmp@earthling.net) 12. VMS: rename opendir() to zopendir() so avoiding name clash with VMS 7.x POSIX libraries (Christian, Martin Zinser) 13. Add support for VMS DEC C V 5.6 features (Christian) 14. Use iname for comparison in check_dup (Christian Spieler, Christian Michel) 15. Fix access to uninitialized ioctx records in vms_get_attributes() Christian, Robert Nielsen) 16. Parenthesis around MAX_MATCH>>1 in match.S (Greg) 17. Use strchr() not strrchr() for -i and -x to get -i@ and -x@ really working (Onno, Kai Uwe) 18. add chmod statements to unix/Makefile (Quentin Barnes) 19. Windll: handle both -r and -R (Mike) 20. Windll: general error handler in main() via setjmp/longjmp (Mike) 21. Don't allow zip -i@x.lst foo.zip (Onno) 22. vms/link_zip.com: use .eqs. not .nes. when checking with f$search for the zip AXP object library (David Dachtera) 23. rsxnt 1.3.1 fixes (E-Yen Tan) -------------------------- January 20th 1998 version 2.21b ------------------- 1. Bigger PATH_MAX for win32's windll (Mike) 2. Update windll.txt w.r.t. PATH_MAX (Mike) 3. Amiga SAS/C fixes (Walter, Paul) 4. zip -i@ and -x@ should *really* work now ...... (Onno) -------------------------- February 20th 1998 version 2.21c ------------------- 1. make -f unix/Makefile qnx needs LN=ln in its options (Chris) 2. Support Metroworks Codewarrior/x86 on BEOS (Chris) 3. Add Norbert Pueschel to proginfo/infozip.who (Walter) 4. Use big endian for Be types (Chris) 5. zip -i and -x were broken by the -i@ fix last time around (Christian) 6. win32 stat bandaid (Paul) 7. acorn filetype and timestamp fixes (Sergio, D. Krumbholz) 8. update to izshr30 (Christian) 9. Support for NTSD in the RSXNT environment (Christian) 10. restructure readzipfile() (Christian) 11. Where needed define MATCH in osdep.h (Christian) 12. version_local() fixes for RSXNT (Christian) 13. New vmsmunch.c (Christian) -------------------------- March 15th 1998 version 2.3a ------------------- 1. Fixes for the windll API (Mike) 2. Use CPUTYPE in BorlandC Makefile for DOS (E-Yen Tan) 3. BEOS: -rostr not available for the x86 compiler (Chris) 4. preserve file attributes of a symlink on BEOS (Chris) 5. New VM/CMS README.CMS and version_local() (Ian Gorman) 6. INSTALL fixes from Takahiro Watanabe 7. OS/390 port from Paul von Behren 8. new api.h from Mike -------------------------- April 19th 1998 version 2.3b ------------------- 1. Improve Tandem file I/O performance (Dave Smith) 2. New VM/CMS README.CMS and version_local() (Ian Gorman) 3. cygwin32 port from Cosmin Truta 4. Workaround for tasm32 5.0 bug in win32/crc_i386.asm (Cosmin Truta) 5. win32/match32.asm fixes for tasm 5.0 (Cosmin Truta) 6. simplify OS/390 port (Christian) 7. win32 timezone handling fixes (Christian) 8. fix 40-bit time conversion on the acorn (Sergio and Christian) 9. strip network part from UNC type filenames (Christian) 10. Makefile for OpenMVS (Ian Gorman) 11. Use the Watcom getch() for cygwin32 (Christian) 12. Borland C++ 5.x added to win32's version_local() (Cosmin Truta) 13. Borland C++ needs tzset() in win32 (Christian, Cosmin Truta) -------------------------- May 21st 1998 version 2.3c ------------------- 1. Better error messages for -i and -x (Christian) 2. Win32 stat() wrapper needs dos2unixtime (Christian,Paul,Mike) 3. DJGPP: use _chmod to handle LFN attributes correctly (Michael Mauch) 4. Fix Borlandc warnings (Mike) 5. win32/makefile.bor fixes from Michael Mauch 6. win32/makefile.{dj,emx} fixes from E-Yen Tan 7. Use izshr031 (Christian) 8. CMS: use RECFM=V LRECL=32760 by adding "byteseek" (Greg Hartwig) 9. Check external name for trailing "/" (Greg Hartwig) 10. More specific info in CMS version_local() (Greg Hartwig) 11. Changed usage info to refer to "fm" rather than "path" on CMS (Greg Hartwig) 12. No more "extra data" messages when using the same OS (Greg Hartwig) 13. Rewritten README.CMS, one version for ZIP and UNZIP (Greg Hartwig) 14. DOS/OS2/WIN32/UNIX: ex2in() strips off "//host/share/" from UNC names (SPC) -------------------------- June 23rd 1998 version 2.3d ------------------- 1. Fixed Win32's stat() bandaid handling of time stamps (SPC) 2. General fix of file selections for DELETE and FRESHEN action (SPC) 3. CMS_MVS: Use ASCII coding for TIME extra field ID (SPC) 4. EBCDIC: Repaired bogus CMS_MVS fix in zipup.c; check the internal name for trailing (ASCII) '/' to detect directory entries (SPC) 5. Use explicit ASCII coding when comparing or setting chars in iname (SPC) 6. Fixed win32/makefile.bor, win32/makefile.dj (support NTSD), win32/makefile.emx (SPC) 7. Replaced win32/makefile.cyg by win32/makefile.gcc, containing new support for mingw32 GCC environment (SPC) 8. Use izshr032 (SPC) 9. Modified zipup.c to hold (un)compressed lengths in "ulg" variables, in an attempt to support handling of huge (>2GByte) files. (SPC) 10. Removed some duplicate #defines from api.h, they are now in crypt.h (SPC) 11. Reenabled "extra data size" info messages in noisy mode for all systems except RISCOS and CMS_MVS (SPC) 12. For EMX 0.9c, the runtime lib contains a working mktime(), use it (SPC) 13. Miscellanous cosmetic changes (SPC) 14. Move win32/makefile.emx to msdos (E-Yen Tan) 15. make api.h work with zcrypt2.8 (Mike) 16. define ydays differently in api.h to avoid linking problems (Mike) 17. New windll.txt (Mike) 18. win32 lcc patches (E-Yen Tan) 19. win32 lcc makefile (E-Yen Tan) 20. Multiple inclusion bug: no malloc.h when using lcc-win32 (E-Yen Tan) 21. New VB support files for windll (Mike Le Voi, Raymond King) 22. MacOS port by Dirk Haase -------------------------- August 1st 1998 version 2.3e ------------------- 1. Generalized check for validy of TZ timezone setup info, similar to UnZip; use it on AMIGA and MSDOS, as before. (SPC) 2. Apply TZ validy check on OS/2 and enable creation of UT e.f. (SPC) 3. BEOS: New Makefile, updates for README and Contents (Chris Herborth) 4. beos/beos.c: declare some private functions as "local" (SPC) 5. Include memcompress() code only for ports that make use of it, controlled by preprocessor symbol ZP_NEED_MEMCOMPR (SPC) 6. cmsmvs/README.CMS fix: Zip archive entries to be extracted into var-length records CMS files should >>NOT<< contain binary data ... (SPC) 7. crc32.c, crctab.c: the crc polynom table is ZCONST (SPC) 8. trees.c: fixed a bug in the deflate algorithm that limited the compressed size of an archive member to 512 MByte (SPC) 9. deflate.c: Integrated the changes found in zlib that are neccessary to make the deflate algorithm deterministic; modified msdos/match.asm to take care of the "nice_match" global no longer being constant. (SPC) 10. deflate.c, trees.c, zipup.c: Reorganized and simplified deflate's compressed output buffer handling. I/O and compression code are now separated more cleanly. (SPC) 11. Killed bits.c by moving its contents into trees.c resp. zipup.c; synchronized all Makefiles and Make procedures with this change. (SPC) 12. Integrated support for optionally replacement of deflate and crc32 by public domain zlib code. (SPC) 13. Synchronize the different variants (UNIX/GNU C, OS/2, WIN32) of i386 assembler replacement for deflate's longest_match() (SPC) 14. Moved the EMX+rsxnt Makefile.emx from msdos/ back into win32/ (SPC) 15. Restored a separate Makefile.emx for DOS; on DOS, some make programs may have difficulties with recursive invokation (SPC) 16. Fixed the "include header mess" of the new MACOS port and removed the "work-around hacks" caused by these bad MACOS .h-file includes (SPC) 17. Integrated Dirk Haase's beta4 (27-Jun-98) release of MacZIP (Dirk Haase) 18. Added support for MS Quick C in the MSDOS version_local() report (SPC) 19. Added WIN32 rsxnt targets linking against the emx crtl DLL to Makefile.emx in os2/ and win32/ (SPC) 20. Fixed typo in os2/os2.c wild() function. (Kai Uwe Rommel) 21. Removed ChangeNameForFAT() from os2/os2.c in2ex() to fix problem with long filename support. (Kai Uwe Rommel) 22. os2/os2zip.[ch]: correct type of DOS-style timestamp data is "ulg" (SPC) 23. vms/cmdline.c: Removed wrong ';' behind if condition (Johnny Lee) 24. VMS: Preliminary preparations in C code for supporting GNU C on OpenVMS Alpha (Onno van der Linden, Christian Spieler) 25. VMS: Fixed check against adding zipfile to itself in fileio.c (SPC) 26. WIN32: Added lcc-Win32 variants of i386 assembler code for crc32() and longest_match(). (SPC) 27. WIN32: Removed bogus type-cast in assignment to statb st_mode member (SPC) 28. zip.c: Fixed MACOS-related typo that broke "-@" command option (SPC) 29. zipup.c: Fixed messed-up expression for assignment to z->ver (SPC) 30. MACOS extra fields: check realloc return values (Onno, Johnny Lee) 31. Fix the PUTBYTE macro in trees.c: >= instead of < (Onno) -------------------------- September 6th 1998 version 2.3f ------------------- 1. Add zp_tz_is_valid to globals.c (Onno, Frank Donahoe) 2. Updated tandem files from Dave Smith 3. Windll: allow comments to zip archive with VB (Mike) 4. Windll: add support for -b and update the documentation (Mike) 5. win32: use wbS for FOPW to handle large zip files better (Steve Miller) 6. MVS fix: use fseek();clearerr() instead of rewind() (Onno, Lee Burton) 7. Updated VB examples for windll (Mike) 8. Tandem: use UTC timestamps and GID/UID in extra field (Dave Smith) 9. Tandem: handle -o option (Dave Smith) 10. default for ZCONST is const in tailor.h, override in osdep.h (Onno) 11. additional Macintosh options in zip.c (Dirk Haase) 12. additional Macintosh options in zip.1 and MANUAL (Onno, Dirk Haase) 13. Integrate Beta 5 of the Macintosh Port (Dirk Haase) -------------------------- October 27th 1998 version 2.3g ------------------- 1. zip_tz_is_valid should be zp_tz_is_valid (Kai Uwe) 2. MVS native (not OE) beta fixes (Keith Owens) 3. LynxOS support from Giuseppe Guerrini 4. MVS already has stat() and fstat() so use 'em (Keith Owens) 5. MVS fix in readzipfile() for new, unopened dataset without EOF marker (Keith Owens) 6. Remove 16-bit stuff from windll/windll.rc (Mike) 7. Windll: Use hCurrentInst not hInst (Mike) 8. In util.c compare strchr() return value with NULL (Onno, Frank Donahoe) 9. unix/unix.c: initialize variable t in ex2in() (Onno, Frank Danahoe) 10. Remove windll/borland subdirectory (Mike) 11. Really fix extra field realloc() for BeOS and MacOS (Christian) 12. Fix the dj2 LFN related access violation bug (Christian, Joe Forster) 13. proginfo/3rdparty.bug: Added more info about other Zip clone's bugs. 14. The global copyright definitions in revision.h now depend on DEFCPYRT (Christian). 15. tandem/macros: removed obsolete object file references (Christian) 16. fix memory leak with the "filter" patterns (Christian, Leah Kramer) 17. zip.c: completed the support for MacOS specific -N (Christian) 18. reorganized the Mac specific help screen code (Christian) 19. zipup.c: corrected the USE_ZLIB code to emit "stored" entries under the same conditions as the "native deflate" code (Christian) 20. A couple of vars that will never be negative should be unsigned (Christian) -------------------------- November 18th 1998 version 2.3h ------------------- 1. DJGPP: When compressing from stdin don't set binary mode if stdin is a terminal (E-Yen Tan) 2. Fix signed/unsigned comparisons in fileio.c, util.c and zipcloak.c (Frank Donahoe) 3. Move macgetch() prototype from macos/source/macos.c to macos/osdep.h (Christian) 4. _doserrno should have type int, not unsigned int (Christian) 5. In zipfile.c init a file pointer with NULL to fix gcc warning (Christian) 6. Upgrade to MacOS beta 7 (Dirk Haase) 7. Move the #pragma statements from generic sources to cmsmvs.h (Christian) 8. Support for QNX/Neutrino 2.0 (Chris) 9. Default to -r in help screen add -R at the bottom (Chris) 10. Clean up Makefile for BeOS R4 on x86 (Chris) 11. Beos: If not storing symlinks store attributes of symlink target (Chris) 12. Use izshr037 (Christian) 13. Remove ZIPERR() macro from in {msdos,win32}/osdep.h (Christian) 14. win32/win32.c: Fix 1-day offset in non-64bit FileTime2utime() (Christian) 15. win32: enable 64-bit FileTime2utime() for MS VC++ >= 5.0 (Christian) 16. cygwin32 only has _P_WAIT (Thomas Klausner) 17. msname() should *really* ignore illegal characters (Thomas Klausner) 18. Fix a missing ')' in Opendir() from win32zip.c (Thomas Klausner) -------------------------- December 5th 1998 version 2.3i ------------------- 1. Remove the #pragma statements that were forgotten the first time (Ian) 2. Remove obsolete macos/source/CharMap.h (Steve Salisbury) 3. isatty(fileno(zstdin)) in zipup.c should be isatty(zstdin) (Onno, E-Yen Tan) 4. several "shut up warnings from compiler" fixes (Christian) 5. several cosmetic source changes (Christian) 6. win32: make NTSD handling to be robust against alignment and structure padding problems (Christian) 7. Apply don't set binary mode when stdin is a terminal in zipup.c for MSDOS and human68k (Christian) 8. Upgrade to MacOS beta 8 (Dirk Haase) 9. Add callback for WINDLL to handle user termination (Mike) 10. Fix typo in acornzip.c (Darren Salt) 11. acorn/sendbits.s: pass correct parameters to flush_outbuf() (Darren Salt) 12. Fixes for IBM C/C++ 3.6 where time_t is a double (Kai Uwe) 13. Fixes for IBM Visual Age C++ for win32 (Douglas Hendrix) 14. man/zip.1: some version numbers in the text were still "2.2" (Christian) 15. win32/makefile.emx: added a compilation variant that generates standalone executables (Christian) 16. change __CYGWIN32__ into __CYGWIN__ and add compatiblity definition for B19 and older (Cosmin Truta) 17. create uniform win32 getch() replacement (Christian) 18. put back in define of USE_EF_UT_TIME in tandem.h (Dave Smith) 19. put back in define of USE_CASE_MAP in tandem.h (Dave Smith) 20. updates to make/macros to allow the object to be licensed (Dave Smith) 21. updates to macros/doit to remove mktime.c (Dave Smith) 22. updates to tandem.c for in2ex/mapname/chmod amendments to match Unzip (Dave Smith) 23. Use izshr039.zip (Christian) 24. Init filenotes to 0 for the amiga too (Onno) 25. get_filters(): remove one flag=0 statement to make -R work again (Onno) -------------------------- December 17th 1998 version 2.3j ------------------ 1. FOPWT defines opening a temp file for writing (Ian) 2. Remove handling of bits.c from a couple of tandem files (Christian) 3. A couple of "shut up warnings from compiler" fixes (Christian) 4. win32/osdep.h: removed duplicate "IZ_PACKED" definition (Christian) 5. win32/zipup.h: remove invalid "elseif" preprocessor token (Christian) 6. sync MacOS help screen with other ports (Christian) 7. get_filters(): set flag to 0 when -R isn't used (Christian) 8. "local extra != central extra" now has "info" status (Christian) 9. use windll directory as "home" directory for builds (Mike) 10. CMS/MVS: define FOPWT (Ian) 11. Upgrade to MacOS beta 9 (Dirk Haase) -------------------------- January 17th 1999 version 2.3k ------------------ 1. Change FOPW into FOPW_TMP (Christian) 2. win32: #include uses paths relative to the parent directory (Christian) 3. Use forward slashes as path separator in #include statements (Christian) 4. windll: fix descriptions of f{In,Ex}cludeDate (Christian) 5. win32/makefile.lcc: add some -I options to find files in the right places (Christian) 6. Supply default empty IZ_PACKED define (Christian) 7. windll: Fix some typos, descriptions (Christian) 8. windll project files: use relative paths, no specific root directory (Christian) 9. windll project files: remove link references to import libraries that are not used by the zip library (Christian) 10. windll: fix potential infinite loop in a VB sample (Mike) 11. windll/windll.txt: remove "may not work with VB" statement (Mike) 12. Multibyte character set support from Yoshioka Tsuneo 13. Theos port from Jean-Michel Dubois 14. Tandem: added simple handling of Enscribe files by converting them into text type files (Dave Smith) 15. Tandem Extra Field ("TA") containing Tandem File Attributes (Dave Smith) 16. Tandem history file showing background info to (UN)ZIP ports (Dave Smith) 17. create ZIP file on tandem with special file code (1001) (Dave Smith) 18. made tandem.c & tandem.h code completely the same as UNZIP (Dave Smith) 19. unix/configure: move +Onolimit and -Olimit into the machine specific section (Onno, John Wiersba) -------------------------- February 21st 1999 version 2.3l ------------------ 1. Fix qdos Makefile (Jonathan Hudson) 2. fgets instead of gets in zipnote to fix linker warnings (Jonathan Hudson) 3. Theos: remove _setargv.c and a reference in zip.c (Jean-Michel Dubois) 4. Theos README (Jean-Michel Dubois) 5. interchanged the fRecurse flag values for "-R" and "-r" (Christian) 6. add "z" pr prefix to MBCS functions to avoid name clashes (Christian) 7. Whenever the position of the increment operator does not matter, the INCSTR variant is used, which has been mapped to the {PRE|POS}INCSTR variant that is more efficient. (Christian) 8. fixed the "-R" handling in fileio.c, filter() function (Christian) 9. simplified some THEOS specific code additions (Christian) 10. changed the line break of the compiler version message in version_local() for MSDOS and Win32 to take into account some verbose compilers (Christian) 11. removed the THEOS changes from ttyio.c. Instead, a THEOS specific setup was added to ttyio.h (Christian) 12. sync vms/link_zip.com with the corresponding make_zip.com (Christian) 13. added compatibility settings for support of MBCS on Win32 with all tested compilers to win32/osdep.h 14. added type-casts to isalpha() macro calls (Christian) 15. fixed win32's wild_match which was clobbered by the MBCS addition (Christian) 16. finished up the "potential infinite loop" problems in the VB sample that Mike started to repair (Christian) 17. in ziperr.h, AZTEK C might require the false comma that was removed to satisfy THEOS C (Christian) 18. removed the bogus THEOS specific isdir check in zipup.c (Christian) 19. modified the code for line ending translation to be independent of the local system's convention for '\n' and '\r'; this allowed the removal of the THEOS specialities (Christian) 20. Tandem: -B option to zip Enscribe files with no record delimiters (Dave Smith) 21. Tandem: attempt to catch Large Transfer mode failure (Dave Smith) 22. Theos: Fixed keyboard entry functions. (Jean-Michel Dubois) 23. Theos: workaround for the argument wild card expansion that is bugged in the standard library. Managed by MAINWA_BUG flag. (Jean-Michel Dubois) 24. Theos: support for filenames and notes with accented characters. (Jean-Michel Dubois) 25. Upgrade to MacOS final (Dirk Haase) -------------------------- March 31st 1999 version 2.3m ------------------- 1. Theos: for relative paths to root directory cause open, fopen and stat failure, workaround this. (Jean-Michel Dubois) 2. Theos: when no path is indicated in a file or directory name and the file or directory doesn't exist in the current directory it looks for the file or directory in the root directory, workaround this. (Jean-Michel Dubois) 3. Corrected some typos and spelling error in macos/HISTORY.TXT; skipped off invisible trailing whitespace (Christian) 4. proginfo/extra.fld: added documentation for Tandem and Theos extra field layout (Christian with Dave D Smith resp. Jean-Michel Dubois) 5. qdos/Makefile.qdos: The build of ZipCloak requires inclusion of the crctab object module; qfileio_.o compilation requires the -DUTIL flag (Christian) 6. win32: fix incorrect MB_CUR_MAX macro for mingw32 and lcc (Christian) 7. theos/_fprintf.c, theos/_rename.c, theos/osdep.h: Some function parameters require the "const" attribute to achieve compatibility with ANSI C requirements (Christian) 8. theos/theos.c: map Theos' (No)Hidden file attribute to MSDOS Hidden bit in the MSDOS part of zipentry header's external attribute field; 9. theos/stat.h: prevent multiple inclusions 10. Theos: Fixed wild card management for options other than adding (Jean-Michel Dubois) 11. Theos: Removed modifications of const strings (Jean-Michel Dubois) 12. Split tandem.c up into separate zip/unzip parts (Dave Smith, Christian) 13. Move inclusion of OS specific zipup.h files to tailor.h (Onno) -------------------------- August 14th 1999 version 2.3n ------------------- 1. Move inclusion of OS specific zipup.h files back to zipup.c (Onno) 2. Remove getline() from zipnote.c and use gets() again (Onno) 3. BeOS PowerPC R4.1 support (Chris) 4. New DOIT and MACROS files for the tandem port (Dave Smith) 5. Don't switch the console to binary mode (Michel de Ruiter) 6. In some circumstances undosm could be freed twice (Mike) 7. Also define const in tailor.h for ultrix (Onno, Foppa Uberti Massimo) 8. Tandem: Change zopen in TANZIPC to allow opening of files with missing alt keys (err 4) (Dave Smith) 9. Tandem: Assume not DST if can't resolve time (no DST table available) (Dave Smith) 10. WIN32: skip trailing dots and spaces in getnam (Onno, Dan Kegel) 11. Use ZE_NONE when nothing to freshen or update (Onno, Yuri Sidorenko) 12. Remove tabs from files that don't need them (Onno) 13. Remove tabs and spaces from the end of a text line (Onno) 14. Upgrade macos to 1.04b2 (Dirk) 15. Add -Q documentation to manual page (Jonathan Hudson) 16. Copy hiperspace files instead of renaming them (Keith Owens) 17. Disallow some more characters to appear in DOS filenames when using -k (Onno, Thomas Klausner) 18. Document missing options and environment variables in the manual (Onno) 19. New acorn/GMakefile to compile with gcc on RISCOS (Darren Salt) 20. ISO 8601 date format support for -t and -tt (Rodney Brown) -------------------------- September 21st 1999 version 2.3o ------------------- 1. Sync zip.h license with LICENSE (Onno) 2. Add copyright notice to README, os2zip.c and os2.zip.h (Onno, Greg) 3. Fix the ASM variable in acorn/GMakefile (Darren Salt) 4. Add another requirement to acorn/ReadMe.GMakefile (Darren Salt) 5. Fix unbalanced parenthesis in vms_get_attributes declaration in zip.h and move it to vms/zipup.h (Onno, Mike Freeman) 6. Make a couple of os2 files public domain (Kai Uwe) 7. Change and rename disclaimer array in revision.h (Onno) 8. Change copyright array in revision.h (Onno) 9. macstuff.c copyright is the same as macstuff.h (Christian) 10. WHATSNEW: add ISO 8601 dates supported (Christian) 11. fileio.c - msname(): strip off leading dots, these are illegal for MSDOS compatible names (Christian) 13. fileio.c - replace(): deactivate "dead" code for CMS_MVS (Christian) 14. man/zip.1: "-$" option is also used for WIN32 ports 15. msdos/msdos.c - version_local(): break the version line for GNU compilers too (Christian) 16. tailor.h: added typecasts to MBCS macros, to suppress "type mismatch" warnings (Christian) 17. util.c, zip.h, zipfile.c: ZCONSTify several pointers (Christian) 18. util.c - recmatch(), zip.c - version_info(): add compile time option WILD_STOP_AT_DIR (Christian, Darren Salt) 19. util.c - envargs(): MBCS related fixes (Christian) 20. win32/lm32_lcc.asm: add TAB characters that are required by the lcc assembler source parser (Christian) 21. zip.c: fix the "is a console" check (Christian) 22. zipnote.c: use getline() (Christian) 23. zipup.c: use zclose() in case of I/O errors (Christian) 24. zipup.c: use ZE_WRITE when a write error occurs (Christian) 25. win32/win32.c: HAVE_INT64 is used by mingw32 (Cosmin Truta) 26. update shared sources to match izshr041 (Christian) -------------------------- November 29th 1999 version 2.3 ------------------ 1. Missing parenthesis in win32/win32.c (Steve Salisbury) 2. Add Cosmin Truta to proginfo/infozip.who (Onno) 3. Remove one parenthesis pair too many from vms_get_attributes() declaration in vms/zipup.h (Mike Freeman) 4. qdos .s are expected to start with a #, work around it (Jonathan Hudson) 5. tandem: -B0 should be deflating not storing (Dave Smith) 6. human68k updates from Shimazaki Ryo 7. beos Makefile cleanup (Chris) 8. workaround for fseek to negativate offset behaviour of the RISC OS SharedCLibrary (Darren Salt) 9. set file type for RISC OS in zipcloak.c (Darren Salt) 10. change tandem zgetch() to allow crypt version to work (Dave Smith) 11. fix a comment typo in acorn/riscos.c (Christian) 12. fileio.c: two type-cast to shut up noisy compilers (Christian) 13. human68k: fix missing case_flag argmument (Christian) 14. win32/win32.c: remove HAVE_INT64 completely (Christian) 15. zip.c: raise "cannot zip to console" error when stdout IS a tty (Christian) 16. zip.h: don't use dummy argument names in declarations (Christian) 17. Add missing semicolon in fileio.c (Shimazaki Ryo) 18. win32.c: IBMC compiler >= 3.50 have int64 (Kai Uwe) 19. Handle initialization error return value from MVS stat() in procname() (Keith Owens) 20. Use RISC OS instead of RiscOS in the manual (Darren Salt) 21. Use # instead of ? as single character wildcard on RISC OS (Darren Salt) 22. New windll example.c (Mike) 23. Correct storage of 8-bit char filenames with RSXNT (Burkhard Hirzinger) 24. fix install in unix/Makefile (Santiago Vila, Onno) 25. Fix zip -L output (Santiago Vila, Onno) 26. Ignore unix special files (Jonathan O'Brien) 27. Upgrade to izshr042 (Onno) 28. Make copyright notice the same as in izshr042 (Onno) 29. Make copyright notice in zip.h the same as LICENSE (Christian) 30. Set tempzf to NULL _after_ it has been closed (Chris Kacher) 31. Change email address for Jonathan Hudson (Jonathan Hudson) 32. Remove win32/winzip.c.orig (Steve Salisbury) 33. Use 'Steve Salisbury' throughout the documentation (Steve Salisbury) 34. Change email address for Steve Salisbury (Steve Salisbury) 35. Change email address for Chris Herborth (Chris Herborth) 36. Use zip23 in INSTALL (Roger Cornelius) 37. Use zcrypt28 in INSTALL (Onno) 38. New acorn/srcrename (Darren Salt) 39. amiga/makefile.azt: make clean should remove some more items (Paul) 40. Change email address for Cosmin Truta (Cosmin Truta) -------------------------- February 11th 2001 version 2.4a ------------------ 1. Identify newer Borland compilers (Brad Clarke) 2. Detect Turbo C 2.01 which doesn't have mktime (Brian Lindholm) 3. Fix the use of -@ together with -i -x (Christian) 4. Update msdos/README.DOS to match reality (Christian) 5. win32: use assembler crc32 code (Christian) 6. windll: _CRTIMP is needed in several function declarations (Christian) 7. back to zip 2.2 memcompress() behaviour (Kelly Anderson) 8. new amiga time code based on nih public domain code (Paul Kienitz) 9. Detect some more Borland C++ builder versions (Brad Clarke) 10. Fix OS/2's extended file attributes compression code (Christian, Kai Uwe) 11. Correct translation of EBCDIC passwords to ASCII (Christian) 12. Attempt at integrating novell patches from Roger Foss (Onno) 13. Use izshr043 (Christian) -------------------------- July 3rd 2001 version 2.4b ------------------ 1. Fix OS/2's ACL compression code (Christian, Kai Uwe) 2. Rename netware subdir to novell (Christian) 3. Remove -dNETWARE -dDOS from novell Makefile (Christian) 4. Remove defined(NETWARE) from the sources (Christian) 5. printf is a macro in glibc 2.2, fix version_local function (Christian, Matthew Wilcox) -------------------------- January 13th 2002 version 2.4c ------------------ 1. Use klist_items when initilizating koff[] in tandem.c (Dave Smith) 2. Only call NLMsignals() in zip.c when NLM is defined (Mike, Onno) 3. include riscos.h instead of acorn/riscos.h in acorn/osdep.h (Andy Wingate) 4. Use izshr044 (Christian) -------------------------- January 13th 2002 version 2.4d ------------------ 1. Don't use mmap for stored entries (Christian) 2. BIG_MEM and MMAP cannot be defined at the same time (Christian) 3. Allow redirection of version screen to file (Christian) 4. Fix for OS/2 output redirection bug (Christian, Kai Uwe) 5. Acorn script for creating self extracting zips (Darren Salt) 6. Update amiga makefiles to support revised timezone routines (Christian) 7. Correct memcompress calculation for allocation size (Christian) 8. Fix FORCE_METHOD debug option for level 1 and 2 (Christian) 9. Whitespace cleanup in man/zip.1 (Christian) 10. Define IZ_IMP to specify compiler declaration prefixes (Christian) 11. make win32 and msdos version_local() "stdio-macro-safe" (Christian) 12. move tandem's zip specific zipopen to tanzip.c (Christian) 13. first parm is void * in external scope of vms_get_attributes() (Christian) 14. use right novell subdirectory in zipup.c (Christian) 15. update copyright for files modified in 2002 (Onno) -------------------------- January 19th 2002 version 2.4e ------------------ 1. Add MacOS X to version_local() (Mark) 2. unix/configure: Init LFLAGS1 to "", MacOS X doesn't like -s (Onno, Mark) 3. rename errors array to ziperrors to avoid MacOS X library clash (Mark) 4. Support for the upx executable packer in DOS makefiles (Christian) 5. remove obsolete -m486 switch from dos djgpp makefile (Christian) 6. When using DOS, force the use of msdos style external attributes when updating zip entries created under another OS (Christian) 7. os2/makefile.os2: fixed ASFLAGS for watcom16dos (Christian) 8. Update copyright and ftp address in several files (Christian) 9. The RISCOS port uses '.' as directory separator, not '/' (Christian) 10. win32/makefile.bor: more options to compile the asm CRC code (Christian) 11. win32: use registry to handle timezones with MS C rtl (Christian) 12. acorn: use recommended practice for calling the linker (Andy Wingate) 13. unix/configure: check if CPP works else use ${CC} -E (Onno, Mark) 14. update versioninfolines in revision.h to match reality (Onno) -------------------------- February 10th 2002 version 2.4f ------------------ 1. vms: Zip -V is now able to handle file sizes up to 4Gb (Christian) 2. vms: Include target environment detection for MMS/MMK (Christian) 3. Change dummy message from zipcloak (Christian) 4. acorn: add riscos specific -/ option (Darren) 5. Update acorn's WILD_STOP_AT_DIR feature (Christian) 6. acorn: Fix buffer allocation for -/ option (Christian, Darren) 7. acorn: fix make clean (Andy Wingate) 8. acorn: use tabs for GMakefile to make GNU make happy (Andy Wingate) 9. tandem: use nskopen not zipopen (Dave Smith) 10. tandem: allow passing of CRYPT define (Dave Smith) 11. use izshr045 (Christian) -------------------------- April 1st 2002 version 2.4g ------------------ 1. acorn: fix assembler and compiler options in makefile (Darren) 2. use izshr046 (Christian) 3. MVS: define isatty to 1 to fix screen output (Christian) 4. tandem: encryption really works now (Dave Smith) 5. win32: detect Borland C++ builder 6 (Brad Clarke) -------------------------- April 30th 2003 version 2.4h ------------------ 1. tandem: fix temporary file contention (Dave Smith) 2. cmsmvs: generate better filenames with -j (Owen Leibman) 3. tandem: fix temporary file leftovers (Dave Smith) 4. solaris: enable large file I/O to break 2G barrier (Rick Moakley, Onno) Note: Zip 2.4 was never released. That code was the start of the Zip 3.0 effort below. Some changes and fixes also made it to the Zip 2.3x releases. ---------------------- January 21st 2004 version 3.0a ---------------------- Initial work on Zip 3.0 by Ed Gordon and Rainer Nausedat 1. Changed some comments to update copyrights (Ed) 2. Changed text in command line messages from zip 2.4 to zip 3.0 (Ed) 3. Changes to many files for Zip64 wrapped in ifdef ZIP64_SUPPORT (Rainer) 4. Attempt to fix buggy Win32 buffered 64-bit calls (Ed) 5. Add functions to zipfile.c for Little-Endian memory writes (Rainer) 6. Add functions to zipfile.c for writing Zip64 extra fields (Rainer) 7. Major changes to putlocal, putcentral, and putend (Rainer) 8. Fixing -F and -FF for Zip64 postponed (Ed and Rainer) 9. Command line code replaced. Global table sets options, long options now supported. Permutes so order of arguments can vary (Ed) 10. Fix bug where not allowed to use -@ with stdout but was with stdin. Now can read filenames from stdin using -@ and output to stdout and no longer am allowed to use -@ if reading from stdin (Ed) 11. Replace stat() with zstat(), fstat() with zfstat() and struct stat with z_stat in Zip64 blocks. Put 64-bit file calls in ifdef LARGE_FILE_SUPPORT blocks. Can implement Zip64 without > 4 GB file support but for now need large files for Zip64 support (Ed) 12. Move port-specific code to osdep.h and win32.c (port specific) and tailor.h (generic) and remove temporary os_io.c. As OF() is not defined until after osdep.h includes in tailor.h function prototypes for zfseeko, zftello, and zstat after that in tailor.h (Ed) 13. Settings of ZIP64_SUPPORT and LARGE_FILE_SUPPORT automatic based on port and version of compiler. Defining NO_ZIP64_SUPPORT or NO_LARGE_FILE_SUPPORT overrides this (Ed) 14. Bugs compiling scanzipf_fix(...) in zipfile.c and the fix functions could use rewrite (Rainer and Ed) 15. Add prototype for zfopen for mapping to 64-bit fopen on ports using inodes but not implemented (Ed) 16. More work on extended local headers and encypted archives (Rainer) 17. Fix DLL files so now compiles (Ed) 18. File size in dll limited to 32-bit in structure. A new DLL api is needed to return 64-bit file sizes. Current api fixed to return max 32-bit if more than that (Ed) 19. Add local header Zip64 support and local extra field. Fixed cast to ulg missed previously that forced zstat to return value mod 4 GB in zipup.c which kept local header code from seeing actual file size (Ed) 20. Add new option --force-zip64 to force use of zip64 fields. Could be temporary (Ed) 21. Fix for VB added to api.c that just store the passed strings internally. Should update api to optionally return file sizes as 64-bit in call back and to accept RootDir and other strings in same call that zips (Ed) 22. Readme updated to describe new features and mention updated mail group web links (Ed) 23. Minor bugs in output format found and fixed. Now can add files > 4 GB to archive and unzip using major unzippers (Ed) 24. If zip used as filter (zip - -) and sizes exceed limits of extended local header (data descriptor) then set max 32-bit values there. Major unzippers ignore and use central directory values which are correct. Can create Zip64 data descriptor using --force-zip64 option but seems no need for it (Ed) 25. A few bugs in how headers are handled prevented zipping large numbers of files. Fixed (Rainer) 26. A bit of an attempt to fix -F and -FF. Seems to work but not that robust. More work needed (Ed) 27. After some cast and other fixes zip compiles on Linux Red Hat 9 using Unix generic. Added automatic detection of fseeko64 and if detected sets LARGE_FILE_SUPPORT and setting that sets ZIP64_SUPPORT. Works but could not test large files on the small system (Ed) 28. Tried to fix bug that prevents zipnotes from compiling when ZIP64_SUPPORT is set. Still broke. This crashes the Unix Makefile but after zip is compiled (Ed) ---------------------- May 8th 2004 version 3.0b ---------------------- 1. Update license headers on more files (Ed) 2. Change many ZIP64_SUPPORT ifdefs to LARGE_FILE_SUPPORT where appropriate. Now can test ports using three stages, compile with NO_LARGE_FILE_SUPPORT (which disables ZIP64_SUPPORT) to test base code, compile with NO_ZIP64_SUPPORT to test the 64-bit file calls (assuming port sets LARGE_FILE_SUPPORT) but otherwise use the base code, and without either to test Zip64 if enabled on port (Ed) 3. Fix zipnotes bug by moving a ZIP64_SUPPORT block in zipfile.c (Ed) 4. Add Large File Summit (LFS) code to Unix port to enable 64-bit calls. Update configure to include test for all needed 64-bit file calls before enabling LARGE_FILE_SUPPORT for unix port (Ed) 5. Merge encryption code from zcrypt29 (files from unzip) into zip and enable by default (Ed) 6. New man pages for zipnote, zipsplit, and zipcloak (Greg, Ed) 7. Add encryption notice to crypt.c comments and to version information in zip.c (Greg, Ed) 8. Add Russian OEM EBCDIC support when OEM_RUSS defined in ebcdic.h but Dmitri reports that 0x2F not '/' so make recommended change in cutpath call in zipfile.c used by -D option (Dmitri - Nov 10 2003 email) 9. ToDo30 file added to list what's left to do in this release (Ed) 10. Change fopen to zfopen for large file code and map to fopen64 for Unix (Ed) 11. ftello64 seems broken in zipup.c on Linux (kernel 2.4), returning negatives past the 2 GB barrier, though ftello64 works in a test program. Likely error in defines. For now skip ftello64 check for Unix with LARGE_FILE_SUPPORT. 12. A few updates in Readme. Needs overhaul likely. Also verified mxserver is gone and replaced with list addresses (Ed) 13. First iterations at updating WinDLL for Zip64 (Mike) 14. Decide to drop backward dll compatibility in favor of a cleaner dll interface. Decide to add string interfaces for VB (Ed, Mike) 15. Add string interfaces to dll interface to bypass array limitations imposed by VB and add -x and -i to interface (Mike) 16. Create new VB example using new Zip64 dll interface (Ed) 17. Add O_LARGEFILE define for zopen in unix/zipup.h to enable reading large files in unix (Ed) 18. Combine ZpSetOptions and ZpArchive dll calls to allow removing all VB kluges in api.c to work around VB garbage collecting passed strings (Mike) 19. Change new VBz64 example to use updated interface. All works without kluges (Ed) ---------------------- August 15th 2004 version 3.0c ---------------------- 1. Add date formats in -t and -tt date errors (Ed) 2. Add -so to display all available options (Ed) 3. Many fixes from Dan Nelson to fix some large file support problems and add large file support to a few ports. Main change is rather than use explicit 64-bit calls like fopen64 now set 64-bit environment and use standard calls. Also add a define for 64-bit printf format used to print 64-bit stats (Dan, Ed) 4. Changes to Unix config based on suggestions from Dan Nelson. Check if off_t is at least 64 bit (Dan, Ed) 5. Add -- to get_option. Any arguments after -- on command line now read as paths and not options (Ed) 6. Add extended help (Ed) 7. Change add_filter flag parameter from char to int as some compilers have problems with char arguments (Ed) 8. Changed filter() to do R and i separately so i has precedence over R (Ed) 9. Split variable t in zip.c into t (off_t) and tf (ulg) (Ed) 10. Add quotes to zipname in check_zipfile for MSDOS to allow spaces in archive path given to unzip to test ( , Ed) 11. Move zip.h include before ctype.h include in trees.c and zipup.c as when ctype.h is first and using 64-bit environment at least on unix port found it defines off_t as 4 bytes in those files as off_t is defined as 8 bytes in other files and this changes the size of the zlist structure which is not good (Ed) 12. Add default 64-bit file environment to tailor.h if LARGE_FILE_SUPPORT is set but no port 64-bit file defines are set up earlier in the file. Should allow other ports to set LARGE_FILE_SUPPORT on the compiler command line to test if the standard defines work (Ed) 13. Adjust binary detection in trees.c by changing 20% binary (4 out of 5 ascii) that used >> 2 to 2% (64 out of 65) using >> 6 instead. trees.c (Ed) ---------------------- November 12th 2004 version 3.0d ---------------------- 1. Add global variable for EncryptionPassword in VBz64 example and some other password callback cleanup (Ed) 2. Add -W option to turn on WILD_STOP_AT_DIR where wildcards will not include directory boundaries in matches (Ed) 3. Add -nw option "no wild" to completely disable wildcards in MATCH function. Allows a list of files to be read in without worrying about wildcards or escapes (Ed) 4. Add -s option split-size but not implemented (Ed) 5. Add -sp option split-pause but not implemented (Ed) 6. Add changes for WiZ including moving Win32 64-bit wrappers into win32i64.c to avoid naming conflict between libraries in WiZ (Mike, Ed) 7. Some large file fixes in crypt.c (Ed) 8. Add new error code ZE_UNSUP for unsupported compiler options. Add check of size of zoff_t in zip.c when LARGE_FILE_SUPPORT enabled (Ed) 9. Changed ZE_UNSUP to ZE_COMPERR to avoid conflict with unzip (Ed) 10. On VMS (sufficiently recent, non-VAX), DECC$ARGV_PARSE_STYLE is set automatically to preserve case of the command line if the user has SET PROCESS /PARSE = EXTEND. This obviates quoting upper-case options, like -V, when enabled. VMS.C (Steven Schweda (SMS)) 11. On VMS, building with macro VMS_PRESERVE_CASE defined preserves case of names in archive, instead of forcing lower-case (the former and current default behavior). VMSZIP.C (SMS) 12. On VMS, in some of the simplest cases, ODS5 extended file name escape characters ("^") are removed from names in archive. VMSZIP.C (SMS) 13. On VMS, fixed a problem in some cases with mixed-case directory names, where too much of the directory hierarchy was included in the path names in the archive. VMSZIP.C (SMS) 14. On VMS, minor changes for large file support (long -> zoff_t). VMSZIP.C (SMS) 15. On VMS, changed some structure declarations to typedefs, and rearranged to simplify #if's and reduce potential name conflicts. VMS.H, VMS_IM.C, VMS_PK.C (SMS) 16. On VMS, reformed -V (/VMS) processing. Added -VV (/VMS=ALL). Removed some sign bits to accomodate files bigger than 2GB. CMDLINE.C, VMS_IM.C, VMS_PK.C, ZIP.C, ZIP_CLI.CLD, ZIP_CLI.HELP, ZIPUP.H (SMS) 17. Update command line options to support -VV as distinct option (Ed) 18. More VMS changes (SMS) 19. Add zoff_t format function (SMS) 20. On VMS, when -b was not used, temporary archive files were always created in the current default directory, rather than in the archive file destination directory. VMS now uses its own tempname() function. FILEIO.C, VMS.C (SMS) 21. Remove using FNMAX for path size in a few places including filetime.c to avoid exceeding limit (based on fixes from Greg and others) (Ed) 22. Add port atheos (Ruslan Nickolaev, Ed) 23. Bug fix adds different extra fields for local and central in VMS (SMS) 24. Now short options also take optional values as next argument (Ed) 25. Change -dd to control -v dots (SMS, Ed) 26. On VMS, a new open callback function senses (where supported) the process RMS_DEFAULT values for file extend quantity (deq), multi-block count (mbc), and multi-buffer count (mbf), and sets the FAB/RAB parameters accordingly. The default deq is now much larger than before (16384, was none), and the default mbc is now 127 (up from 64), speeding creation of a large archive file. Explicitly set RMS_DEFAULT values override built-in defaults. OSDEP.H, VMS.C (SMS) 27. VMS CLI definitions and CLI help have been updated, and may be approximately correct. CMDLINE.C, ZIP_CLI.CLD, ZIP_CLI.HELP (SMS) 28. The man file zip.1 updated and Makefile updated to generate manual pages for zipcloak.1, zipnote.1, and zipsplit.1 (Ed) ---------------------- July 23rd 2005 version 3.0e ---------------------- 1. Debian patch 004 - apply 2.4i configure changes from Onno to remove need for -fno-builtin in unix/configure (Onno, Ed) 2. Debian patch 005 for bug 279867 - fix bug that could crash on large paths and create security problem. Apply patch changes from Greg (Greg, Ed) 3. SourceForge patch 1074363 - add win32i64.c to win32/makefile.w32 (Ed) 4. Add check when not ZIP64_SUPPORT in scanzipf_reg() in zipfile.c if Zip64 archive being read (Ed) 5. Renamed fzofft() used to format zoff_t values to zip_fzofft() to remove conflict when combined with UnZip in WiZ (Mike) 6. Add check in scanzipf_reg() in zipfile.c if Zip64 archive being read (Ed) 7. Fixes for amiga/makefile.azt to define directory for object files (Paul) 8. Define prototypes for local functions optionerr, get_shortopt and get_longopt in fileio.c. Define err argument of optionerr as ZCONST (Paul) 9. Add help_extended and DisplayRunningStats prototypes, fix other prototypes in zip.c (Paul) 10. Split int kk off of k for argument types (Paul) 11. Aztec #endif quirk fix in zip.c for Amiga (Paul) 12. Add detection of binary in first buffer read from file in zipup.c to avoid a -l or -ll translation on binary file. Not perfect but at least should catch some binary files (Ed) 13. Remove check for >= 128 from binary check in zipup.c as <= 6 enough for signed char (SMS, Ed) 14. SF Bug 1074368 - check for empty zip file in readzipfile() in zipfile.c (Christian d'Heureuse, Ed) 15. Add error exit to prevent archive corruption when updating a large-file archive with a small-file program. Add ZE_ZIP64 error. ziperr.h, zipfile.c (SMS) 16. Change percent() in zipup.c to do rounding better, handle cases near limits while rounding, and allow negative percent returns (SMS, Ed) 17. Add function ffile_size() in zipfile.c but in #if 0 block until determine if works on all ports under all conditions. Currently only used for size check for Zip64 archive detection if compiled without ZIP64_SUPPORT and this check may already be handled in scanzipf_reg() and should be added to scanzipf_fix() when that is updated (SMS, Ed) 18. Change >>1 to /2 in zipsplit.c to allow for negative percent returns (SMS) 19. Add type uzoff_t for unsigned zoff_t things. Should clean up some casting (Ed) 20. Based on discussions with other development groups, when data descriptors (extended local headers) are used, force to Zip64. This is compatible with other unzips and does not require a change of the AppNote, but the resulting archive requires Zip64 to read. Using standard data descriptors would mean that the zip operation would fail if a Zip64 entry was encountered. See zipfile.c (Ed) 21. Add define SPLIT_SUPPORT to enable splits. The command line options are done and the globals are set up but nothing more. globals.c, zip.h, and zip.c mainly (Ed) 22. Create spanning signature at beginning of archive when splitting enabled. If reading a split archive skip the spanning signature unless creating a split archive. zip.c, globals.c (Ed) 23. Start implementing split archives. Define two methods. split_method = 1 updates local headers and is the most compatible but requires updating previous splits. split_method = 2 uses data descriptors and should work for streams and removable media but may not be as compatible with other zip applications. (In part based on previous discussions with Rainer.) Updated global variables to include bytes written to just the current entry in the current split. zipfile.c (Ed) 24. Add note about output redirection to zip.1 (?, Ed) 25. Remove num < 0 check as num now unsigned. util.c (SMS, Ed) 26. Change lastchar to lastchr in fileio.c in places to avoid function by same name (SMS, Ed) 27. Moved #endif /* !WINDLL */ in zip.c (Mike) 28. Account for vms directory version being ;1. vmszip.c (SMS) 29. Fix Zip64 check in scanzipf_reg to use the buffer. zipfile.c (Ed) 30. Default define size_t (for use by Steve's ffile_size() function). tailor.h (Ed) 31. Enable Steve's ffile_size() function and enable large file check. It currently does not allow file sizes over 2 GB but the code is not supporting it anyway without large file support. Should remove that part of the check when the casts are fixed. zipfile.c (Ed) 32. Fixes for djgpp. Now compiles with djgpp 2 (Ed) 33. Add new VC6 projects for win32 and windll (Cosmin) 34. Convert some variables in zipsplit.c from ulg to zoff_t so compiles (Ed) 35. Add wildcards to extended help. zip.c (Ed) 36. For optional option value now '-' is same as missing value. fileio.c (Ed) 37. Remove extra free() from -dd option switch. zip.c (Ed) 38. Change write_unsigned_to_mem() to write_ulong_to_mem() and write_short_to_mem() to write_ushort_to_mem(). zipfile.c (Ed) 39. Create new append to mem functions. zipfile.c (Ed) 40. Change zlist nam and ext from extent to ushort as that is what gets written. zipfile.c (Ed) 41. Change GetSD to use ush instead of size_t. win32/win32zip.c (Ed) 42. Change PutLocal(), PutExtended(), PutCentral(), and PutEnd() to write to memory and then write the block at once to the file. zipfile.c (Ed) 43. Change zcomlen from extent to ush, other extent conversions. zipfile.c, globals.c, zip.h (Ed) 44. Add is_seekable() and global output_is_seekable. Do seekable check when output file is opened. zipup.c, globals.c, zip.h, zip.c (Ed) 45. Do not increment files_so_far and bytes_so_far if file could not be read. zip.c (Ed) 46. If force_zip64 set, only force compressed size in central directory to Zip64 instead of all entries (csize, usize, off, disk) in Zip64 extra field. This fixes inconsistent handling of disk numbers. zipfile.c (Ed) 47. Add end status if displaying running stats and not all files were read. zip.c (Ed) 48. Change force_zip64 to zip64_archive in putend(). zipfile.c (Ed) 49. Enable the i686-optimized code by default. crc_i386.S, win32/crc_i386.asm, win32/crc_i386.c (Cosmin) 50. Document and implement a new text detection scheme provided by Cosmin in set_file_type(). Should be able to handle UTF-8 and some other character sets. proginfo/txtvsbin.txt, trees.c (Cosmin, Johnny, Christian) 51. Update binary detection for -l and -ll to use Cosmin black list. zipup.c (Ed) 52. Change ZE_BIG to include read and write. ziperr.h (Ed) 53. If archive not seekable then use data descriptors. If ZIP64_SUPPORT always create Zip64 data descriptors and add a Zip64 extra field to flag it is a Zip64 data descriptor. This is klugy but should be compatible with other unzips. See the note in zipfile.c for details. (Ed) 54. Use ush for comment length in putend(). Instead of extent use ush for zcount and fcount same as in zip file. zip.h (Ed) 55. Update VB readme. windll/VB/readmeVB.txt (Ed) 56. Change (INSTALL) to (INSTALL_PROGRAM). unix/Makefile (, Ed) 57. During update the file and byte status counts were off. Fixed by not coun- ting files copied from old to new as those are not in totals. zip.c (Ed) 58. Change from -b to -bx for nroff of manuals to text files. unix/Makefile (Ed) 59. Add cygwin to makefile. unix/Makefile (, Ed) 60. Fix bug where files to delete not added to list. zip.c (Ed) 61. Fix delete stats. zip.c (Ed) 62. Increment version of crypt to 2.10. Update default behavior notes. crypt.c, crypt.h (Paul, Christian) 63. Format changes, add parentheses to zfseeko(), fix output bytes, add ifdef blocks for ZIP10, fzofft formatting, casts. crypt.c (Christian) 64. Cast block_start to unsigned. deflate.c (Christian) 65. Let -R patterns match in subdirectories. Update filter() to use switch, use global icount and Rcount, handle subdirectories, update icount and RCount in filterlist_to_patterns(). fileio.c, zip.c, zip.h, globals.c (Christian) 66. Enclose option -! and use_privileges under NTSD_EAS guard. globals.c, zip.c, zip.h (Cosmin) 67. Updates to version, copyright, license. [I did not split the copyright to 2 lines as it already takes up space on the help screen. Ed] revision.h (Christian) 68. Add ZCONST to some read-only string pointer arguments in function declarations. zipcloak.c, zipnote.c, zipsplit.c, zip.c, zip.h (Christian) 69. Fix byte counts on exit in zipcloak() and zipbare() to fix zipcloak bug (Christian) 70. Modified zipnote.c to use WRBUFSIZ to handle line widths of at least 2047 characters in write mode (Christian) 71. Change simple() and greedy() from zoff_t to uzoff_t. zipsplit.c (Christian) 72. Remove duplicate copyright notices. zipsplit.c (Christian) 73. Remove export notice from help page. Move notice to bottom of license page. zipcloak.c (Ed) 74. File USexport.msg export history added. (Greg) 75. Added support for VMS ODS5 extended file names. (Eight-bit only, no Unicode.) VMS name character "/" is mapped to Zip name character "?". New command-line options -C[2|5][-] (/PRESERVE_CASE[=opts]) control name case preservation and/or down-casing. globals.c, zip.c, zip.h, vms/cmdline.c, vms/vms_im.c, vms/vms_pk.c, vms/vms.c, vms/vmszip.c, vms/vms.h (SMS) 76. New VMS option -ww (/DOT_VERSION) stores version numbers as ".nnn" instead of ";nnn" [changed from -Y to -ww (Ed)]. zip.c (SMS) 77. Changes to vms_open(). vms/vms_im.c, vms/vms_pk.c 78. Changes to vms_read(). vms/vms_pk.c (SMS) 79. Documentation updates. vms/vms_zip.rnh (SMS) 80. Minor updates. vms/zip_cli.help, vms/cmdline.c, vms/vms_zip.rnh (Ed) 81. Changes to vmsmunch(). vms/vmsmunch.c (SMS) 82. Do some updating of VMS options. vms/zip_cli.cld (SMS) 83. Moved the VMS-specific ziptyp() function from zipfile.c to vms/vms.c to segregate better the RMS stuff. (SMS) 84. Put 64-bit calls in ZIP64_SUPPORT ifdef blocks, change some long parameters for append to memory block functions to ulg, remove redundant includes, add OFT protos to some functions with parameter types that get promoted like ush to avoid warnings in VMS. zipfile.c (SMS) 85. Use zip_fzofft() to format number. zipsplit.c (SMS) 86. Add file_id.diz from Zip 2.31 (?, Ed) 87. Update install from Zip 2.31 (?, Ed) 88. Update license from Zip 2.31. License (?, Ed) 89. Update Readme.cr from Zip 2.31 (?, Ed) 90. Add 64-bit assembler for Win32 from Zip 2.31. win32/makefile.a64, win32/readme.a64, win32/gvmat64.asm (?, Ed) 91. Update Readme (Ed) 92. Update headers. crctab.c, crc32.c, deflate.c, ebcdic.h, fileio.h (Ed) 93. Option for extra verbose VMS, change DIAG_FLAG from verbose to (verbose >= 2). vms/vms.c (SMS) 94. Update copyright header. qdos/qdos.c (Christian, Ed) 95. Change exit(0) to exit(ZE_OK). qdos/qdos.c (Christian) 96. Change ulg to unsigned long. tailor.h (, Christian) 97. Default uzoff_t to unsigned long long if LARGE_FILE_SUPPORT manually enabled for an otherwise unsupported port. tailor.h (Ed) 98. Update copyright header. tailor.h (Ed) 99. Change EXIT(0) to EXIT(ZE_LOGIC) for ziperr recursion. zip.c (Christian) 100. Change EXIT(0) to EXIT(ZE_OK) for successful returns. zip.c, zipcloak.c (Christian) 101. Update license. zip.h (Christian) 102. Initialized mesg in zipcloak.c, zipnote.c, zipsplit.c to fix access violation crashes. (Christian) 103. Added -q (Quiet mode) option to zipcloak, zipnote, zipsplit. (Christian) 104. Add proto of mb_clen(). fileio.c (Cosmin) 105. Synchronize ttyio.c and ttyio.h with the unzip-5.52 source. (Cosmin) 106. Control the POSIX emulation provided by some Unix-on-Windows compiler distributions, such as Cygwin, via the FORCE_WIN32_OVER_UNIX macro. tailor.h, win32/Makefile.gcc (Cosmin) 107. Remove getenv() declaration. util.c (Cosmin) 108. Fix definitions of zopen and zstdin. unix/zipup.h (Cosmin) 109. Enable binary file operations for DJGPP and Cygwin. unix/osdep.h (Cosmin) 110. Remove -DMSDOS from CFLAGS; use correct dependency in target crc_i386.obj. win32/makefile.w32, win32/makenoas.w32 (Cosmin) 111. Update win32/makefile.bor and win32/makefile.gcc (Cosmin) 112. Put mktemp() declaration inside the NO_PROTO guard. tailor.h (Cosmin) 113. Use the right type (DWORD) for volSerNo, maxCompLen and fileSysFlags in FSusesLocalTime(). win32/win32.c (Cosmin) 114. Set the "zip Debug" configuration as default. win32/vc6/zip.dsp (Cosmin) 115. Define ASM_CRC by default. win32/osdep.h (Cosmin) 116. Avoid using file names that are distinguished solely by letter case; e.g. crc_i386.S and crc_i386.s. unix/Makefile (Cosmin) 117. Stylistic fix inside ex2in(). unix/unix.c (Cosmin) 118. Change zlist dsk from ush to ulg to support Zip64 and added casts in zipfile.c to write ush. zip.h, zipfile.c (Christian, Ed) 119. Conditionally apply S_IFLNK to support DJGPP. unix/unix.c (Cosmin) 120. Change -dd [siz] (display dots, set optional dot size) to the options -dd (turn dots on, use 10 MB default) and -ds siz (set dot size). Found that using -dd with an optional value got confusing as detection of an optional argument, when the next argument was not either an option or the end of the line, was easy to overlook. Easier to avoid optional values. zip.c (Ed) 121. Change text output of manual pages to zip.txt, zip.txt, zipcloak.txt, zipnote.txt, zipsplit.txt. unix/Makefile (Christian, Ed) 122. Change comments using // to /* */ format. api.c, zip.c (Christian) 123. Add support for signals SIGABRT, SIGBREAK, SIGBUS, SIGILL, and SIGSEGV to utilities. zipcloak.c, zipnote.c, zipsplit.c (Christian) 124. Update ToDo30.txt file (Ed) 125. Delete old Manual file (Ed) 126. Update WHERE from Zip 2.32 (Ed) 127. Change description of dot-size. zip.c (Ed) 128. Change VMS to use -ds to set dotsize. vms/cmdline.c (Ed) 129. Update manuals. man/zip.1, man/zipsplit.1, man/zipnote.1, man/zipcloak.1 (Ed) 130. Detect i586, i686 and Cygwin in version_local(). unix/unix.c (Cosmin) 131. Add clean target. win32/makefile.w32, win32/makenoas.w32 (Cosmin) 132. Changed most 64-bit size/offset variable declarations (like zoff_t) into "unsigned" type (like uzoff_t), for better backward compatibility with non-ZIP64_SUPPORT setups where "ulg" was used for these variables. deflate.c, fileio.c, globals.c, trees.c, vms/vms_pk.c, win32zip.c, zip.c, zip.h, zipfile.c, zipup.c (Christian) 133. Add (ulg) cast to strstart in flush_block. deflate.c (Christian) 134. Updated Win32 LARGE_FILE_SUPPORT setup for Watcom and MinGW. tailor.h, win32/osdep.h (Christian) 135. Add attempt count to tempname(). fileio.c (Christian) 136. Fixed size counter handling in debug code for Zip64. trees.c (Christian) 137. Moved cryptnote display text definition into revision.h, like was done in Zip 2.31. zip.c, revision.h (Christian) 138. Add ZCONST. fileio.c (Christian) 139. Removed earlier change in trash() where ASCII-containing iname was searched for native-coded '/' characters. [Added note but left as changed 5/20/05 EG] zipfile.c (Christian) 140. Change zipup size error message to use zip_fzofft(). zipup.c (Christian) 141. Updated win32/makefile.wat to enable Zip64 support and use directory for intermediate files. (Christian) 142. Change fcount and zcount from ulg to extent as extent is used internally, but Zip64 standard supports up to ulg. Add note to zip.h. globals.c, zip.h (Christian) 143. Define NO_W32TIMES_IZFIX in compile options when appropriate. Add version information for USE_ZLIB compiler option. zip.c (Christian) 144. Add support for SIGABRT, SIGBREAK, SIGBUS, SIGILL, and SIGSEGV signals. zip.c (Christian) 145. Add display-usize option to show uncompressed size. zip.c (Ed) 146. Add many descriptions to options table. zip.c (Ed) 147. Remove -R from help screen as on extended help screen. zip.c (Ed) 148. Add basics to extended help. zip.c (Ed) 149. Fix checks in scanzipf_reg() for empty file since cenbeg now unsigned. Change buffer from t to b in small big check. Back up after small zip big archive check. zipfile.c (Ed) 150. Change Zip64 not supported warning in scanzipf_reg(). zipfile.c (Ed) 151. Fix bug where local and central headers were not matching when compiled with NO_LARGE_FILE_SUPPORT. Restored order of zlist structure elements to match order of local header as scanzipf_reg() compares it as an array of bytes to the local header. Gag. It needs fixing but at least it works as intended now. zip.h, zipfile.c (Ed) 152. Minor fix from 10000 to 10 K for WriteNumString(). util.c (Ed) 153. Add overflow check to file_read(). zipup.c (SMS) 154. Add parameter p1 product specification. vms/collect_deps.com (SMS) 155. VMS changes. vms/descrip_mkdeps.mms (SMS) 156. Change zoff_t to uzoff_t and unsigned int to size_t. vms/vms_im.c, vms/vms_pk.c (SMS) 157. Fix ; that was : at end of line. Fix DisplayNumString() prototype. zip.h (Ed) 158. Get rid of leading blanks in DisplayNumString(). util.c (Ed) 159. Reset dot_count each file. zipup.c (Ed) 160. Minor changes to extended help. zip.c (Ed) 161. Move defines into DEFINED_ONCE block. api.h (Mike) 162. Add Still Remaining And Planned For Zip 3.0 section. WhatsNew (Ed) 163. Delete quotes around CHANGES. Readme (Ed) 164. Add -lf, open file at path and use for logging, -la, append to existing logfile, and -li, include informational messages, options. globals.c, zip.h, zip.c (Ed) 165. Update extended help to include logging. zip.c (Ed) 166. Add support for required short option value in form -o=value as optional does. fileio.c (Ed) 167. If bytes_total is smaller than bytes_so_far for some reason then display negative of bytes_to_go. This can happen if files grow in size after all the sizes are initially added up. zip.c (Ed) 168. Use usize from filetime for adding to bytes_total when updating instead of size in old entry. zip.c (Ed) 169. Change status counts files_so_far and bytes_so_far to include bad files so the status counts end at the end but add bad_files_so_far and bad_bytes_so_far to track bad files. After minor fixes it looks like the counts remaining at the end are correct, even when some files are not readable. Update bad file warnings. zip.c, zip.h, globals.c, zipup.c (Ed) 170. Add uq for unsigned q in zipup(). Initialize z->len in case an error later so have a valid size. zipup.c (Ed) 171. Check noisy in DisplayRunningStats() so logging is independent of it. zip.c (Ed) 172. Add check in DOS for windows and if running DOS version on Windows warn user. zip.c, msdos/msdos.c, msdos/osdep.h (Johnny) 173. Add errno.h for strerror(errno) call. zip.c, zipup.c (SMS) 174. Fix log problem if using -q option. zipup.c (Ed) 175. Change "Far char" to "char Far" as Far is a qualifier not for the char type but the storage allocation of the array. fileio.c (Christian) 176. Update note on extent. globals.c (Christian, Ed) 177. Remove extra USE_ZLIB. zip.c (Christian) 178. Add note for the OEM_RUSS '/' bug. Need to look at later as it seems the Russian bug remains unfixed. zipfile.c (Christian, Ed) 180. So byte counts always come out even, create good_bytes_so_far to count bytes read in and convert bytes_so_far to use the counts from the initial scan. If files change during the zip operation good_bytes_so_far will change and not match bytes_so_far. zip.h, globals.c, zip.c (Ed) 181. Changes to extended help. zip.c (Ed) 182. Update WhatsNew (Ed) 183. Update DLL resource copyright. windll.rc, windll.aps (Ed) 184. Add directory search improvements to Win32 (within recursion, reuse attribs from directory lookup to avoid calling stat()). Add getd_attribs(), procname_win32(). win32/win32zip.c (Johnny) 185. Cache result of IsFileSystemOldFAT() to avoid repetitive system calls for identical information. win32/win32.c (Johnny) 186. Add optimization to dosmatch(): apply alternate shortcut code when the pattern to match consists of one multichar wildcard ('*') followed by a fixed string. util.c (Johnny) 187. Move DOS check_for_windows() checks to Help and Version and errors only. Shorten message to one line. zip.c, msdos/msdos.c (Ed) 188. Define WIN32_OEM to enable oem ansi conversions for more than RSXNT. Not yet fully implemented. win32/win32.c, win32zip.c, zip.c, zipfile.c (Ed) 189. Directory search improvements for MSDOS. msdos/msdos.c (Johnny) 190. Add caching of directory information. If pattern is just *string no need to recurse. win32/win32.c (Johnny) 191. If wild_stop_at_dir then do recurse to handle cases like a/b/*.txt. win32/win32.c (Ed) 192. Additional improvements to directory search speedups, including a) MSDOS port fixes for Turbo C++ compiler b) In both Win32 and MSDOS, change getDirEntryAttr() into macro, saving one function call overhead e) Add explaining comment to optimized procname_{local} code f) In util.c, move "*literal" pattern-matching optimization from dosmatch() to recmatch(). Advantages: - optimization used for all systems - optimization applied to all occurences where a "*" is last wildcard in pattern - "dosmatch()" only preconditoning wrapper for matching workhorse "recmatch()", it should not implement matching algorithms itself - optimization not applied for WILD_STOP_AT_DIR option g) >>>disabled<<< "*literal" optimization for all MBCS-aware environments, because suspect that supplied optimization code is not MBCS-clean (for details see the comment within the patch), so IS NOT USED for win32 port! Can force activation of match optimization by specifying conditional compilation symbol TEST_FOR_MBCS_CLEAN. (Christian) 193. Add and move comments, implement changes for directory search improvements in Zip 3.0 util.c (Ed) 194. In win32/win32.c, IsFileSystemOldFAT(), add declarations of static caching variables where missing to fix win32 port compilation bug (Christian) 195. Correct changed arguments in RSXNT-only character set conversion call. win32/win32zip.c (Christian) 196. Implement Directory Search improvements from Zip 2.32. win32/win32zip.c (Johnny, Ed) 197. Debian Bug #312090 fix. Reworded man page to give multiple examples of recursion, not just zip -r foo foo. man/zip.1 (Ed) 198. Change "-Aa -D_HPUX_SOURCE +e" to -Ae for HP. "HP-UX with the HP compiler and on AIX 4.2.0. AIX 5.1 with gcc-3.4.3 (32-bit) and Darwin built fine - though AIX 5.1 needed CC=gcc make -e ... to find gcc. According to the HP-UX man page -Ae is equivalent to -Aa -D_HPUX_SOURCE +e it seems the +e is needed and -Ae is more terse anyway." Expression generated before was too long. unix/configure (Rodney Brown) 199. Add support for osf4.0f that does not have fseeko or ftello but has 64-bit fseek and ftell though. tailor.h (Rodney) 200. Fix unsigned char to char in recmatch(), add casts for compares. util.c (Ed) 201. Fix for alpha off_t long long. unix/osdep.h (Rodney) 202. Change shmatch() from uch to char and change parameters to recmatch(). Change dosmatch(). util.c (SMS, Rodney, Ed) 203. Add local for DisplayRunningStats(). zip.c (Rodney, Ed) 204. Disable unused append_ubyte_to_mem(). Fix error messages in other append. zipfile.c (Rodney, Ed) 205. Delete unused getDirEntryAttribs(). msdos/msdos.c (Christian) 206. Change warning when running msdos version on Windows. msdos/msdos.c (Ed) 207. Change recmatch() to support MBCS matching. util.c (Christian) 208. Update WhatsNew (Ed) 209. Update Readme (Ed) 210. Format Readme to fit in 80 character lines (SMS, Ed) 211. Rename install.vms to install_vms.txt. vms/install_vms.txt (SMS) 212. Add reference to vms/install_vms.txt in INSTALL (SMS) 213. Update INSTALL (Ed) 214. Remove ALT_NEXTBYTE and Building UnZip sections as no longer needed. vms/notes.txt (SMS, Ed) 215. Add note to TODO (Ed) 216. Update Makefile message to suggest using generic. unix/Makefile (Ed) 217. Update text output of manual. zip.txt (Ed) 218. Update VMS section. INSTALL (SMS, Ed) 219. Minor changes in vms/install_vms.txt (SMS, Ed) 220. Update VMS install information. INSTALL, vms/install_vms.txt (SMS, Ed) 221. Do not use _stati64 under Cygwin. win32/osdep.h (Cosmin) 222. Add note to Makefile to use generic first. unix/Makefile (Ed) 223. Add Test option for VMS CLI. vms/cmdline.c (SMS, ?) 224. Add noconfirm to deletes, define symbol edit. vms/descrip.mms (SMS) 225. Changes to vms/install_vms.txt (SMS) 226. Add note on symbols to VMS. INSTALL (SMS) 227. Update license headers. vms/osdep.h, vms/vms.h, vms/vmsmunch.c, vms/zipup.h, vms/vmszip.c, vms/vms.c, vms/vms_im.c, vms/vms_pk.c, vms/command.c (Ed) 228. Add stsdef.h include for VMS and convert unzip test return to VMS result for VMS. zip.c (SMS) 229. Add const to ziperr(). amiga/amiga.c (Paul) 230. Clean up makefile. amiga/makefile.azt (Paul) 231. Don't try Amiga large file support. amiga/osdep.h (Paul) 232. Add note on -V and -VV. vms/notes.txt (SMS) 233. Small update. vms/zip_cli.help (SMS) 234. Format Windows warning message. msdos/msdos.c (Christian) 235. Format changes. util.c (Christian) 236. Update VMS. INSTALL (SMS) 237. Add creation of intermediate object directories. msdos/makefile.wat (Christian) 238. Add void * cast. msdos/msdos.c (Christian) 239. Add include for mktemp(). msdos/osdep.h (Christian) 240. Fix __RSXNT__ and WIN32_OEM define blocks. win32/win32.c (Christian) 241. Fix __RSXNT__ and WIN32_OEM define blocks. win32/win32zip.c (Christian) 242. Add != NULL to check. zip.c (Christian) 243. Fix WIN32_OEM. zipfile.c (Christian) ---------------------- October 11th 2005 version 3.0f01 ---------------------- (the internal betas may be merged later) 1. Add DSEG for Watcom data segment. msdos/makefile.wat (Christian) 2. Add -zq and use assembler. os2/makefile.os2 (Christian) 3. Update header. os2/match32.asm (Christian) 4. Change len from int to unsigned int. os2/os2.c (Christian) 5. In GetLongPathEA() limit tempbuf to CCHMAXPATH. os2/os2.c (Christian) 6. Add DWATCOM_DSEG to use data segment. win32/makefile.wat (Christian) 7. Update header and add DGROUP. win32/match32.asm (Christian) 8. Add UNICODE_SUPPORT define. zip.h, zip.c (Ed) 9. Add oname to f and z structs for the display name to use in messages. Change z->zname to z->oname in messages. fileio.c, zip.c, win32zip.c, zipup.c, zipfile.c, zip.h (Ed) 10. Move multi-byte defines to make global (they were needed with wide characters but that was taken out and left them where they are). fileio.c, zip.h 11. Add copy_args(), free_args(), and insert_arg() to create copy of argv that can free() and to support inserting "@" in get_option for lists. fileio.c, zip.h 12. Insert arg "@" after list if not followed by option. fileio.c 13. Add args variable and copy argv to args so can use insert_arg(). zip.c 14. Add MKS Korn Shell note. zip.c 15. Change cast of option in add_filter() calls from char to int. zip.c 16. Implement multi-byte version of Unicode support. To support Win32 NT wide calls will require additional work not planned for this release. Changes include (Ed): - Add use_wide_to_mb_default flag. globals.c, zip.h - Add compiler UNICODE_SUPPORT version information. zip.c - Add uname to f and z structs for UTF-8 name. zip.c - Moved some defines out of ZIP64 section. zipfile.c - Add define UTF8_PATH_EF_TAG for Unicode Path extra field. Currently the tag is 0x7075 which is 'u' 'p' for Unicode path and seems free according to the AppNote. The extra field is tag (2 bytes 'u' 'p') size (2 bytes) Unicode Path size (2 bytes) unused (2 bytes set to 0) unused (2 bytes set to 0) Unicode path (variable) The unused locations also serve as a check in case the tag is in use already. - Add add_Unicode_Path_local_extra_field() and add_Unicode_Path_cen_extra_field() functions. zipfile.c - Add read_Unicode_Path_entry() function. zipfile.c - Set uname and oname in scanzipf_ref(). zipfile.c - Add define wide_to_mb_default. Add zchar but not used. win32/osdep.h - Add wide command line reading but don't use. win32/win32.c - Add port functions for Unicode, including local_to_utf8_string(), wide_to_escape_string() (for converting a wide character that can't be converted to mb in the local character set to a reversable escape string), escape_string_to_wide(), wide_to_local_string(), local_to_display_string() (for creating the display version of name), utf8_to_local_string(), local_to_wide_string(), wide_to_utf8_string() (NOT IMPLEMENTED), and utf8_to_wide_string() (NOT IMPLEMENTED). win32/win32.c - Implement attempt at escape function. Whenever a wide character can't be mapped to the local character set, this function gets called. Currently the wide character is converted to a string of hex digits. If the wide can fit in 2 bytes then the form #1234 is used. If not, the 4-byte form #L12345678 is used. It compiles but needs the utf8 functions implemented. Also needs testing in a multi-byte environment and only Windows is implemented so need to at least do Unix. (Ed) 17. Update freeup() to include uname and oname. zip.c 18. Move define wide_to_mb_default so default for all is '_'. zip.h (Ed) 19. No changes needed to osdep.h and update unix/unix.c but not tested. (Ed) ---------------------- October 19th 2005 version 3.0f02 ---------------------- 1. Remove null value check for split_size as get_option() already checks. zip.c (Ed) 2. Update f$search(). vms/descrip.mms (SMS) 3. Save parse name before search and use that on failure. Change name parsing in ziptyp() to solve a problem with search-list logical name device directory specs. vms/vms.c (SMS) 4. Compile in UNICODE_SUPPORT if have wchar_t and mbstowcs(). unix/configure (Ed) 5. Move Unicode defines to zip.h and functions to fileio.c so generic. Create a new OEM function for Windows. fileio.c, zip.h, tailor.h, win32/win32.c (Ed) 6. Add UTF-8 functions. fileio.c (Paul) 7. Convert Unicode functions to use zwchar defined as unsigned long for wide char. fileio.c, zip.h (Ed) 8. Add wchar_t check for Unix. unix/configure (Ed) 9. Add default when zwchar (4 bytes) is too big for wchar_t (2 bytes). zip.h (Ed) 10. Allow for states for wide characters but surrogates not done. fileio.c (Ed) 11. Update WhatsNew (Ed) ---------------------- December 16th 2005 version 3.0f03 ---------------------- 1. Fix broke encryption when ZIP64_SUPPORT enabled by accounting for need for data description when encrypting. Data description is not required for encryption (WinZip does not use one) but seems needed by Zip for some reason. zipfile.c (Ed) 2. Add function bfwrite() to do buffered fwrite(). Most output already is written by zfwrite used by crypt.c which now calls bfwrite. All splitting and new byte counts are done in bfwrite. fileio.c (Ed) 3. Move some functions out of ZIP64_SUPPORT defines for use with UNICODE_SUPPORT. zipfile.c, zip.h (Ed) 4. Add is_ascii_string() and only create Unicode extra field if z->iname is not ascii. zipfile.c, zip.h, fileio.c, (Ed) 5. Add parameter rewrite to putlocal() to note when rewriting bytes so the bytes rewritten are not counted in output totals. zipfile.c, zip.h (Ed) 6. Handle VMS ... wildcard. util.c (SMS) 7. Make tempzip file name global. zip.c, globals.c, zip.h (Ed) 8. Add out_path global and -O path option to allow the output archive to have a different name than the input archive, if there is one. This allows updating a split archive, since output to the same split name would otherwise be complicated and not user friendly. Use out_path for output. zip.h, zip.c, globals.c (Ed) 9. Many output functions that had output file y as parameter, such as zipup(), zipcopy(), putlocal(), putcentral(), and putend(), now do not as y is now global. This allows changing y as splits are created. zip.c (Ed) 10. Add function zipmessage() for writing messages like zipwarn() but are informational. zip.c (Ed) 11. Minor changes to help. zip.c (Ed) 12. Add SPLIT_SUPPORT to version output. zip.c (Ed) 13. Add rename_split() to rename and set attributes for a split. zip.c (Ed) 14. Add set_filetype() to set attributes of split. zip.c (Ed) 15. Change variable a (holds attributes) to zipfile_attributes and make global. zip.c, zip.h, globals.c (Ed) 16. Add key_needed flag for encryption and move setting key to after command line processed. zip.c (SMS) 17. Initialize dot size using default only if dot_size not set. zip.c (Ed) 18. Change command line processing so that last -P or -e is used. zip.c (Ed) 19. Fix broke writing of 4-byte spanning signature at the beginning of the archive if splitting. zip.c (Ed) 20. Use bfcopy() instead of fcopy() to copy archive beginning. bfcopy() uses global y. zip.c (Ed) 21. It looks like tempzf is no longer used. zip.c (Ed) 22. Account for SUNPRO_C and DECC_VER. Change SPARC to Sparc. unix/unix.c (SMS) 23. Remove GNUC. vms/cmdline.c (SMS) 24. Change case of system calls. vms/vms.c (SMS) 25. Add fix for VMS ... matching, but may change Zip to avoid ex2in() and in2ex() for pattern matching in future. vms/vmszip.c (SMS) 26. Remove /NODIRNAMES and /DIRNAMES from VMS help. vms/zip_cli.help (SMS) 27. Define new globals zip64_eocd_disk, zip64_eocd_offset, current_local_tempname, bytes_this_split, and bytes_this_entry for splits. globals.c, zip.h (Ed) 28. Add SUNPRO C and DEC C compile checks. unix/configure (SMS) 29. Add CFLAGS_NOOPT for removing optimization for configure. unix/Makefile (SMS) 30. Modify crypthead() to use bfwrite(). crypt.h, crypt.c (Ed) 31. Modify zfwrite() to use global output file. crypt.h, crypt.c (Ed) 32. Modify zfwrite() when no encryption to use bfwrite(). crypt.h (Ed) 33. Add bfcopy() to copy to y. fileio.c (Ed) 34. Add close_split() and bfwrite() for splits. fileio.c (Ed) 35. Add is_ascii_string() to check if UTF-8 extra field is needed. fileio.c (Ed) 36. Change Unicode escape of 2-byte wide from #1234 to #U1234. fileio.c (Ed) 37. Add read_Unicode_Path_entry() to read the UTF-8 path extra field. zipfile.c (Ed) 38. Latest Unicode Path extra field format is 1 byte Version of Unicode Path Extra Field 2 bytes Name Field Checksum variable UTF-8 Version of Name 39. Use CRC-32 for Unicode Path Checksum and AND halves. zipfile.c (Paul) 40. Add Unicode Path Checksum check to make sure extra field applies to Name field still. zipfile.c (Christian) 41. Move get_extra_field() out of Zip64 block and make available for splits. zipfile.c (Ed) 42. Check in putlocal() using is_ascii_string() and don't create Unicode path extra field if name is ASCII characters. zipfile.c (Ed) 43. If local header for split is on another disk and using split method 1, close that split in putlocal() after rewrite local header. zipfile.c (Ed) 44. Fix data descriptor bug when encrypting where putextended() did not handle the not Zip64 case, which mostly only happens now for encryption. zipfile.c (Ed) 45. Check for ASCII name using is_ascii_string() in putcentral() for Unicode path extra field. zipfile.c (Ed) 46. Instead of single disk values, update putend() to use real split values for current_disk, cd-start_disk, cd_entries_this_disk, cd_start_offset, zip64_eocd_disk, zip64_eocd_offset, and current_disk and allow for needing Zip64 if exceed standard max values for current_disk, cd_start_disk, cd_entries_this_disk, total_cd_entries, and cd_start_offset. zipfile.c (Ed) 47. Use current_local_offset and current_local_disk for z->off and z->dsk in zipup(). zipup.c (Ed) 48. Fix bug where force_zip64 was used to determine descriptor size but can have Zip64 entry without force_zip64 so use zip64_entry. zipup.c (Ed) 49. Change the p - o != s compression size test for splits to bytes_this_entry != (key ? s + 12 : s) and avoid ftell() in split. zipup.c (Ed) 50. If local header is on a previous split and split method 1 do the seek on that split to update header. zipup.c (Ed) 51. For streaming, only force Zip64 if reading stdin and writing a non-seekable device. In other cases can detect either the input file size and set Zip64 if needed or seek in the output to update the local headers. zipup.c, zipfile.c, zipup.c (Ed) 52. Allow creation of stored archives with descriptors for testing. Currently they can't reliably be read but this is planned. zipup.c, zipfile.c, zip.c (Ed) 53. Update help, adding in -e, -P, -s splitsize, -sp, and -sv options. zip.c (Ed) 54. Spelling fix in zipsplit man page. man/zipsplit.1, zipsplit.txt (Ed) 55. New option -sv and variable noisy_splits to enable verbose splitting. Default is to quietly create splits, unless -sp set to pause between splits. zip.h, zip.c, globals.c, fileio.c (Ed) ---------------------- December 23rd 2005 version 3.0f04 ---------------------- 1. Move inlined text-vs-binary checks from file_read() into a separate, new function named is_text_buf(). zipup.c, util.c, zip.h (Cosmin) 2. Fix calls to putlocal to remove the removed dest parameter. crypt.c (Ed) 3. Add get_split_path() to get the path for a split given the disk number. fileio.c, zip.h (Ed) 4. Change formatting of zipmessage() to remove tabbing and add formatting to call to zipmessage(). fileio.c, zip.c (Ed) 5. Initialize many variables such as y and tempzip. zip.c, fileio.c, zipfile.c (Ed) 6. Add loop to pause during split method 2 to allow changing disk or changing the path for the next split. fileio.c (Ed) 7. If after starting new split there is not enough room for the remaining buffer for split method 1 display error and exit and for split method 2 we can display a warning and user can replace disk or change path. fileio.c (Ed) 8. Add list to store input file arguments using add_name() to add the name to filelist_struc filelist and then process the names after the input archive is read. zip.c (Ed) 9. Fix infinite loop when opening a log file whose name contains multiple '/'. zip.c (Cosmin) 10. Move split size message lower and only output if option sv sets noisy splits. zip.c (Ed) 11. Set y to output file, remove output file from zipcopy(), putlocal(), putcentral(), and putend(). zipsplit.c, zipnote.c, zipcloak.c (Ed) 12. Add code for not SPLIT_SUPPORT case. zipfile.c, zipup.c (Ed) 13. Prepend '-' to commands from target clean. win32/makefile.w32, win32/makenoas.w32, win32/makefile.bor (Cosmin) 14. Must not call putenv() in iz_w32_prepareTZenv() under Cygwin. win32/osdep.h (Cosmin) 15. Add browse info in Visual C++ 6 project. win32/vc6/zip*.dsp (Cosmin) ---------------------- December 27th 2005 version 3.0f05 ---------------------- 1. Add proposed changes to License (Ed) 2. Fix -l corruption bug by using memcpy() instead of wrongly changing the buffer pointer. Fix was left out of last beta. zipup.c (Cosmin) 3. Fix get_split_path() parameter. zip.h (SMS, Ed) 4. Add -dg and display_globaldots to display dots globally for entire archive instead of for each file. Is not affected by noisy flag. globals.c, zip.h, zip.c, zipup.c, fileio.c (Ed) 5. Make dot_count and dot_size uzoff_t, dot_count because with global dots dot_count does not reset and with terabyte files the number of buffers could exceed 2G, dot_size to allow use of ReadNumString() to read number. zip.c, zip.h, globals.c (Ed) 6. Add Deletion to help. zip.c (Ed) 7. Fix delete date. zip.c (Ed) 8. For streaming, need to assume Zip64 if writing a non-seekable device so extra field for Zip64 is created if needed. zipup.c, zipfile.c, zipup.c (Ed) 9. Add remove_local_extra_field() and remove_central_extra_field(). zipfile.c (Ed) 10. Remove disabled copyright from license(). zip.c (Ed) 11. Clean up recent changes. zip.c, zipfile.c, fileio.c, zip.h, zipup.c (Ed) 12. Create scanzipf_regnew() for new file scan. zipfile.c (Ed) ---------------------- December 29th 2005 version 3.0f06 ---------------------- 1. Change dot_size and dot_count from uzoff_t to zoff_t to allow use of negative flag values. globals.c, zip.h (SMS, Ed) 2. Remove file parameter to bfwrite() in putend(). zipfile.c (SMS, Ed) 3. Add back code for not SPLIT_SUPPORT to putend(). zipfile.c (SMS, Ed) 4. Change tag from ush to ulg in remove_local_extra_field() and remove_central_extra_field() to avoid parameter problems. zipfile.c (Ed) 5. Add allow_empty_archive to flag when want to create an empty archive. globals.c, zip.h (Ed) 6. Set allow_empty_archive when using -i and expecting an archive to be created. This is in response to the 2/14/05 email. zip.c (Ed) 7. Make before and after variables that hold the dates of files to process or delete global so can use them in scanzipf_regnew(). zip.h, zip.c, globals.c (Ed) 8. Change scanzipf_regnew() to be based on scanzipf_fix() which seems closer. Still have not coded the new regular zipfile reader. zipfile.c (Ed) 9. For new reader first get add list and then read old archive and filter as reading old entries. zip.c, zipfile.c (Ed) 10. Define USE_NEW_READ to turn on using new reader, which is being created. This allows all to work while the new reader is being worked on. zip.c, zipfile.c (Ed) ---------------------- January 9th 2006 version 3.0f07 ---------------------- 1. Remove dest parameter from crypthead() and zipcopy(). crypt.c (SMS, Ed) 2. Change -ds to handle dots for as small as every 32 KB. zip.c (Ed) 3. Add ask_for_split_write_path() and ask_for_split_read_path() for asking where to put the next write split and for locating the next read split. zip.h, fileio.c (Ed) 4. Add in_path to track where reading splits from. zip.h, globals.c, zip.c (Ed) 5. Update copyright date on changed files to include 2006 (Ed) 6. Replace stderr with mesg for most output messages. deflate.c, fileio.c, trees.c, util.c, zip.c, zipcloak.c, zipfile.c, zipnote.c, zipsplit.c 7. Add mesg_line_started to track if need new line on mesg output and update zipmessage() and zipwarn() to use it. Set mesg_line_started to 1 when newline not last character written to mesg and 0 when it is. deflate.c, zip.h, zip.c, globals.c, zipup(), fileio.c (Ed) 8. Include base_path as parameter for get_split_path(). fileio.c (Ed) 9. Account for VMS version in split path. Add vms_file_version(). fileio.c, zip.c, vms/vms.c, vms/vms.h (SMS) 10. Create crc16f() to create ANDed halves crc32 for Unicode using copy of crc32() but may change to use main copy. zipfile.c, zip.h, fileio.c (Ed) 11. Close in_path and out_path in finish() and ziperr(). zip.c (Ed) 12. Change perror() to strerror() and print to mesg in ziperr(). zip.c (Ed) 13. Add find_next_signature() to find the next signature when reading a zip file. zipfile.c (Ed) 14. Add find_signature() to find a given signature from current point in archive. zipfile.c (Ed) 15. Add at_signature() to check if at a given signature in archive. zipfile.c (Ed) 16. Changes to scanzipf_regnew() but far from done. zipfile.c (Ed) 17. Changes to readzipfile() to close input archive file and allow new zipfile reader to open and close files as goes through splits. zipfile.c (Ed) 18. Change -s to default to MB and set minimum split size to 64k. zip.c (Ed) 19. Add link to user32.lib for CharToOem(). makefile.w32, makenoas.w32 (Cosmin) 20. Remove unused Z64_EFPos. globals.c (Ed) ---------------------- February 13th 2006 version 3.0f08 ---------------------- 1. Move option checks before any work is done. zip.c (Ed) 2. Update bfcopy() to handle reading splits and remove input file parameter and use global in_file. fileio.c (Ed) 3. Change ask_for_split_read_path() to allow user aborting. fileio.c (Ed) 4. Change get_split_path() to use standard file extensions from most recent AppNote of .z01, .z02, ..., .z99, .z100, .z101, ... fileio.c (Ed) 5. Change is_ascii_string to use 0x7F for ASCII detection. fileio.c (Ed) 6. Add copy_only global for when -O is used to change the format of an archive without changing the contents. This allows for converting an archive to a split archive for instance. The global copy_only is used to output status information for copies when normally copied files have no status messages. globals.c (Ed) 7. Add in_file, split_path, total_disks, current_in_disk, and current_in_offset as globals to track reading splits. zip.h, globals.c (Ed) 8. Update copyright date. revision.h (Ed) 9. Close in_file if open in finish(). zip.c (Ed) 10. Add -O (big o) to extended help. zip.c (Ed) 11. Remove readzipfile() from zipstdout() and use main call later down. zip.c (Ed) 12. Move archive reading and file scanning after command line checks. zip.c (Ed) 13. If -O out_zip and so have_out is set then set copy_only and allow copying instead of error message *Nothing to do*. zip.c (Ed) 14. If zipbeg is just 4 bytes and spanning then assume is spanning signature and set zipbeg to 0 to ignore. zip.c (Ed) 15. Don't open initial write test as modify if have_out is set and so have a separate output file. zip.c (Ed) 16. If zipbeg is 0 and nothing at beginning of archive to copy then don't open input file until zipcopy() does. zip.c (Ed) 17. If stuff at beginning then copy and close input file. Should be able to keep it open but easier to close it and let zipcopy() reopen it. zip.c (Ed) 18. Add status message when copy_only set so something is displayed. zip.c (Ed) 19. Instead of closing x at bottom close in_file. The variable x was used inconsistently and it seemed easier to make in_file global instead. Then again y remains the global output variable. zip.c (Ed) 20. Update copyright. zipnote.c, zipsplit.c, zipcloak.c (Ed) 21. Change adjust_zip_local_entry() to return 1 if the entry is Zip64 and 0 if not. This is needed to know how large the extended local header is later. zipfile.c (Ed) 22. Add read_Unicode_Path_local_entry() to read the local version of the Unicode Path extra field. zipfile.c (Ed) 23. Handle disk in adjust_zip_central_entry(). zipfile.c (Ed) 24. Change USE_NEW_READ to SPLIT_SUPPORT as splits seems to be stable more or less. zipfile.c (Ed) 25. Add is_signature() to compate signatures. zipfile.c (Ed) 26. Create scanzipf_fixnew(). It should look like scanzipf_regnew(). zipfile.c (Ed) 27. Change scanzipf_regnew() to read the central directory and create zlist and handle reading traditionally. Allows using central directory information, in particular file sizes, in zipcopy() while reading entries. Use global in_file instead of f for input file and set to NULL when not a valid file so finish() only tries to close it if needed. Check to make sure the End Of Central Directory record found is infact the last one in case a stored archive is in the last 64 KB. Refuse to update a split archive but recommend using -O instead. zipfile.c (Ed) 28. Change readable check in readzipfile() to require input archive to exist if using -O out_archive. zipfile.c (Ed) 29. Change putlocal() to not create a Zip64 extra field unless needed and on rewriting the local header to remove Zip64 extra field if was created but not needed. Add check if assumed entry does not need Zip64 but does, meaning probably the uncompressed size is less than 4 GB but the compressed size is over 4 GB. zipfile.c (Ed) 30. Change zipcopy() to use the global in_file and y files and to open and close read splits as needed. Checks the local header against the central directory header to verify same file, which should be as using the disk and offset values from the central directory. Update disk and offset in central directory. zipfile.c (Ed) 31. Change out_path and out_len to base_path and base_len in get_split_path(). fileio.c (SMS) 32. Update command line options for VMS to include verbose splitting. vms/zip_cli.cmd, vms/cmdline.c (SMS) 33. Handle HP. unix/unix.c (SMS) 34. Add adler16() checksum function. util.c (Cosmin) 35. Use FILE_FLAG_BACKUP_SEMANTICS and a less demanding access mode in CreateFile() when retrieving file attributes. Fixes a problem when adding a directory entry from an NTFS or a CDFS partition (i.e. one that stores timestamps using universal time), and the directory timestamp is not the same daylight savings time setting. The effect is an offset in the timestamp by one hour, if zip is built using NT_TZBUG_WORKAROUND. The problem is not exposed, however, if NO_W32TIMES_IZFIX is defined. win32/win32.c (Cosmin) ---------------------- March 19th 2006 version 3.0f09 ---------------------- 1. Fix encryption problem where a large file with uncompressable data can cause deflate to store bad data. See crypt.c for details. Thanks to the nice people at WinZip for finding and providing the details of this problem. crypt.c (Ed) 2. Add note at top of Extended Help to refer to the Zip Manual. zip.c (Ed) 3. Update extended help for delete. zip.c (Ed) 4. Change crypthead() to use buffer and bfwrite() which is split aware. crypt.c (Ed) 5. Create SPLIT_SUPPORT version of zipcloak() and zipbare() and read local header rather than assume data using central header. crypt.c (Ed) 6. Change zfwrite() to use global output file y. crypt.c (Ed) 7. Remove in and out parameters from zipcloak() and zipbare() for splits. crypt.h, zipcloak.c (Ed) 8. Change get_split_path() to get_in_split_path() and get_out_split_path(). zipfile.c, fileio.c, zip.h (Ed) 9. Change crc32f() to crc32u(). fileio.c, zip.h (Ed) 10. Add encryption overwrite fix to copy_block() and remove from zfwrite(). crypt.c, tree.c (Ed, Christian) 11. Add note on bug fix. WhatsNew (Ed) 12. Add copy_only mode. zip.c (Ed) 13. Make SPLIT_SUPPORT the default. zip.h (Ed) 14. Add set_filetype(), rename_split(), and zipmessage(). zipcloak.c, zipnote.c, zipsplit.c (Ed) 15. Add long option support. zipcloak.c (Ed) 16. Set in_path. zipcloak.c, zipnote.c, zipsplit.c (Ed) 17. Use SPLIT_SUPPORT calls. zipcloak.c, zipnote.c, zipsplit.c (Ed) 18. Set current_disk, cd_start_disk, and cd_entries_this_disk for use by putend() and bytes_this_split for putcentral(). zipsplit.c (Ed) 19. Include ctype.h for toupper(). zipfile.c (Ed) 20. Add readlocal() for utilities to read local header. zipfile.c (Ed) 21. Put Zip64 variables and code in ZIP64_SUPPORT ifdef in scanzipf_regnew(). zipfile.c (Ed, SMS) 22. Use zip_fzofft() for converting offset. zipfile.c (Ed, SMS) 23. Add casts to many append to memory calls. zipfile.c (Ed) 24. Move handling of .zip split to get_in_split_path() and get_out_split_path(). zipfile.c (Ed) 25. Handle fix = 3 case for ZipNote that renames entries in zipcopy(). zipfile.c (Ed) 26. Restore clearing of extended local header bit when not encrypting. When encrypting need to output extended local header using putextended() in zipcopy(). zipfile.c (Ed) 27. Add notes on using file time for encrypting. zipup.c (Ed) 28. Remove extended local header bit separately for z->lflg (local flags) and z->flg (central directory flags). These should be the same but could be different. zipup.c (Ed) 29. Suppress command line globbing for MINGW. win32/win32.c (Christian) 30. Add EF UT time fix for delete. zip.c (Christian) ---------------------- April 28th 2006 version 3.0f10 ---------------------- 1. Add note to extended help to escape [ as [[] or use -nw. zip.c (Ed) 2. Remove local declaration of tempfile as now global. zipnote.c, zipcloak.c (SMS) 3. Add zip_fzofft() for outputting uzoff_t bin size c. zipsplit.c (SMS) 4. Add only_archive_set and clear_archive_bits to do Window archive bit selection and clearing. Add -AS option to require DOS Archive bit be set and -AC to clear archive bits of included files. Add ClearArchiveBit() to clear archive bits after archive created. Only Win32. globals.c, zip.h, zip.c, win32zip.c, win32.c (Ed) 5. Change procname_win32() and readd() to check archive bit. win32/win32zip.c (Ed) 6. Update copyright. win32/win32zip.h (Ed) 7. Add mesg_line_started = 0 to stats to remove blank line when clearing archive bits. zipup.c (Ed) 8. Add zip_fzofft() to format split size. zipsplit.c (SMS) 9. Update help for splits and archive bit and add note on escaping [. zip.c (Ed) 10. Add -M option and bad_open_is_error to exit with error if any input file unreadable. Also error if -M and would get "name not matched" warning. zip.c (Ed) 11. Copy Zip 2.32 csharp example, though it is designed for zip32.dll and not zip32z64.dll from Zip 3.0. Updated note. windll/csharp (Ed) 12. Change -M to -MM and define -mm to avoid accidental use of -m. zip.c (Ed) 13. Define split_method -1 to not allow splitting, mainly used when reading a split archive to stop automatic splitting of output with same split size. Now -s=0 or -s- disables splitting. zip.h, globals.c, zip.c (Ed) 14. Add fflush() after dots displayed. deflate.c, fileio.c, zipup.c (Ed) 15. Instead of assuming buffer size as 32 KB for dots, use WSIZE for compressing and SBSZ for storing and calculate as dots are counted. Now dot_count and dot_size are bytes instead of buffers. Add dots to Delete and Archive modes. zip.c, zipup.c, deflate.c, fileio.c (Ed) 16. If reading a split archive and split size has not been given, get size of first split read by zipcopy(), which should be the first split, and set split size to that, making the output archive the same split size as the input archive. Delay -sv split size message if split size is 0 at first but then changed. zipfile.c (Ed) 17. Add proc_archive_name() for new archive mode to process names in old archive only and skip looking on the file system. Easier than modifying the various port codes. fileio.c (Ed) 18. Fix cd_start_offset bug. fileio.c (Ed) 19. Create new action ARCHIVE that looks for matches only in old archive for Copy Mode. If no input paths and there is an output archive, Copy Mode is assumed even without ARCHIVE. Old default Copy Mode when no input files updated to work like -U mode and allow filters. New global copy_only currently only used to control global dots. zip.c, fileio.c, globals.c, zip.h (Ed) 20. Update help. Change extended help to more help. Update more help to include internal modes delete and new Archive. Update help for formatting options. Update help for wildcards. Remove streaming examples from top basic section. Indent examples. Help for new --out and Copy Mode. Add warnings that output using data descriptors may not be compatible with some unzips. Update dots help and add warning that dot size is approximate. Add help for new DOS archive bit options. More help for -b and -MM. zip.c (Ed) 21. Add support for Unix FIFO (named pipe). Add set_extra_field() stat name ending in '/' fix found in Zip 2.32. unix/unix.c (Ed) 22. Add check to not allow setting -U (internal copy) in similar cases to -d (delete). zip.c (Ed) 23. Add counts for internal modes Delete and Archive. Byte counts for -db remain uncompressed size for external modes, but internal modes Delete and Archive now use compressed sizes as these copy that many bytes. zip.c (Ed) 24. Add check for when ftell() wraps. zipup.c (Ed) 25. Add mesg_line_started = 0 to result percentage message. zipup.c (Ed) 26. Update contact information. unix/packaging/preinstall.in (SMS, Ed) 27. A few Zip64 fixes to set Zip64 correctly and fix disk and offset of Zip64 End Of Central Directory. zipsplit.c (Ed) 28. Update comments for get_option(). fileio.c (Ed) 29. Update DLL version. windll/windll.rc (SMS, Ed) 30. New option -sf shows files that would be operated on. zip.c (Ed) ---------------------- May 5th 2006 version 3.0f11 ---------------------- 1. Use C prototypes for Unicode functions. fileio.c (SMS) 2. Change constant for mask in set_file_type from unsigned to signed. trees.c (SMS) 3. Use C prototypes for zip_fzofft() and zip_fuzofft() signed and unsigned zoff_t formatting functions. util.c (SMS) 4. Remove U from constants in Adler16 code. util.c, zip.h (SMS) 5. Add spaces to VMS usage to avoid misinterpretation. zip.c (SMS) 6. Add OF() to at_signature(). zipfile.c (SMS) 7. Use zip_zofft() for entries error. zipfile.c (SMS) 8. Remove U in constants in percent(). zipup.c (SMS) 9. VMS command line updates. vms/cmdline.c, vms/descrip_deps.mms, vms/vms_zip.rnh, zip_cli.cld, vms/zip_cli.help (SMS) 10. Update to VMS help. vms/zip_cli.help (Ed) 11. Check for memmove() and strerror(). Remove specific 64-bit support for SunOS, as large file support now does. unix/configure (SMS) 12. Add emergency replacements for memmove() and strerror(). unix/unix.c (SMS) 13. Remove old not SPLIT_SUPPORT code. globals.c, zipnote.c, fileio.c, crypt.h, crypt.c, zipcloak.c, zip.h, zip.c, zipup.c, zipsplit.c, zipfile.c (Ed) ---------------------- May 12th 2006 version 3.0f12 ---------------------- 1. Add UNICODE_SUPPORT ifdef around uname in zipup(). zip.c (SMS) 2. Change size from uzoff_t to zoff_t in zipcopy(). zipfile.c (SMS, Ed) 3. Fix a bug where filetime() returns -1 for device but not handled in byte counts. zip.c (Ed) 4. Add check for UnZip version and exit if not 6.00 or later if a Zip64 archive. Define popen() and pclose() in Win32 to native _popen() and _pclose(). ziperr.h, zip.c, win32/osdep.h (Ed) 5. Add -sb option to ring bell when pause to change disk. Use new global split_bell. global.c, zip.h, zip.c, fileio.c (Ed) 6. Enable crc32u() and use for Unicode extra field. fileio.c (Ed) 7. Add -dv to display volume being written to. zip.c, zip.h, globals.c (Ed) 8. Update WhatsNew. WhatsNew (Ed) 9. Help updates. zip.c (Ed) 10. Create option -X- (negated -X) to keep old extra fields and remove -XX which is now -X. Make get_extra_field() global. Add copy_nondup_extra_fields()to copy old extra fields not already in new extra fields. zipup.c, zip.c, zipfile.c (Ed) 11. Use output name oname for -sf option to show files that would be worked on. zip.c (Ed) 12. When updating or freshening old entries, read the old local header with readlocal() to get local flags and extra fields. zip.c (Ed) 13. Add UNICODE_SUPPORT ifdefs around uname code. zip.c (SMS, Ed) 14. If WIN32_OEM set then on WIN32 store OEM name in archive. As read DOS or WIN32 archives convert assumed OEM paths to ANSI. Remove old WIN32_OEM code. Make oem_to_local_string() global for WIN32_OEM and local_to_oem_string() global for WIN32_OEM and UNICODE_SUPPORT. zip.h, zipfile.c, zipup.c, win32/win32.c, win32/win32zip.c (Ed) 15. Update error 8 to include wrong unzip. ziperr.h (Ed) 16. Change checksum for Unicode extra field to standard crc32 using C version crc32u(). Add crctab.c. win32/vc6/zipnote.dsp, win32/vc6/zipsplit.dsp, zipfile.c 17. Update readlocal() to handle multi-disk archives if not UTIL. zipfile.c (Ed) 18. Convert size to signed zoff_t in zipcopy(). Update note. zipfile.c (Ed) 19. Update Readme. Readme (Ed) 20. Add crctab.o to zipsplit and zipnote. unix/Makefile (Ed) 21. Proposed update to license. License (Ed) ---------------------- May 20th 2006 version 3.0f13 ---------------------- 1. Reformat License file. License (Cosmin) 2. Change %d to %lu for disk number and add cast. zip.c (Cosmin, Ed) 3. Display Scanning files message after delay at start based on suggestion from Greg. Currently the time is checked every 100 entries processed. After 100 entries the start time is saved. After 5 seconds or 100 entries after that, whichever takes longer, the Scanning files message is displayed and every 2 seconds or 100 entries, whichever takes longer, after that a dot is displayed. fileio.c, zip.c, globals.c, zip.h (Greg, Ed) 4. Add Unicode mismatch flag and option -UN. Default is now a Unicode mismatch is an error. -UN=warn outputs warnings and continues, -UN=ignore disables warnings, and -UN=no ignores the Unicode extra fields. globals.c, zip.h, zipfile.c (Ed) 5. Add options for VMS. vms/cmdline.c, vms/zip_cld.cld (SMS) 6. Add casts to percent(). zipup.c (Ed) 7. Minor changes to logfile formatting. zip.c (Ed) 8. Update help. zip.c (Ed) 9. Add -Z=compression-method option. zip.c (Ed) 10. Add sd: to -sd status messages. zip.c (Ed) 11. Instead of original argv[] use args[] for -sc show command line to show final command line. zip.c (Ed) 12. Change argv[] to args[] for logfile. zip.c (Ed) 13. Put results of -sf show files in log file if open. zip.c (Ed) 14. Add Johnny's bzip2 patch but not tested. win32/makefile, zip.c, zip.h, zipup.c (Johnny) 15. Minor tweeks to bzip2 to work with latest beta. zip.c, zipup.c (Ed) 16. Add -sf- to list files that would be included only in log file and not on stdout as list can be long. Only list totals on stdout. zip.c (Ed) 17. Create check_unzip_version(). Fix Unix check. Zip still creates the temporary archive then does the check, and if it fails the archive is deleted, even if the check fails because of the wrong verion of UnZip. On Unix only 'unzip' the system version of UnZip is checked, not './unzip' which would allow putting a local more up to date version of UnZip in the current directory for the check. There should be a way to override the system version of UnZip for the -T test. zip.c (Ed) ---------------------- July 12th 2006 version 3.0f14 ---------------------- 1. Change crypt version from 2.10 to 2.91 to match Zip 2.32 and avoid confusion. crypt.h (Cosmin) 2. Add abbrevmatch() to handle option values that can be abbreviated like compression method. util.c, zip.h, zip.c (Ed) 3. Change USE_BZIP2 to BZIP2_SUPPORT as USE_BZIP2 implies it replaces deflation maybe. zip.c, zip.h, zipup.c (Ed) 4. Update man page. man/zip.1, zip.txt (Ed) 5. Add bzip2 to VMS. vms/build_zip.com, vms/bzlib.h, vms/cmdline.c, vms/descrip.mms, vms/descrip_src.mms, vms/find_bzip2_lib.com, vms/install_vms.txt, vms/zip_cli.cld (SMS) 6. Remove zipfile parameter from bzfilecompress(). Add unsigned cast for EOF in bzip2 code. Add bzip2 version information. zipup.c, zip.c (SMS) 7. Add bzip2 to Unix. unix/configure (SMS) 8. Add and update bzip2 descriptions. INSTALL, README, WhatsNew, bzip2/install.txt (SMS, Ed) 9. Add vc6bz2 projects for compiling bzip2 code into zip (not the best approach perhaps). win32/vc6/readmevc.txt, win32/vc6bz2/readvcbz.txt, win32/vc6bz2/zip.dsp, win32/vc6bz2/zip.dsw, win32/vc6bz2/zipcloak.dsp, win32/vc6bz2/zipnote.dsp, win32/vc6bz2/zipsplit.dsp (Ed) 10. Add support for VC++ 2005 by disabling deprecation. win32/osdep.h (Cosmin) 11. Update instructions for makefile. unix/Makefile (Ed) 12. Update todo list. todo30.txt (Ed) 13. Reduce #if 0 block to now allow extra data message. zipfile.c (Ed) 14. Add note that readlocal() reads local headers. zipfile.c (Ed) 15. Archive comment was not being read by new scanzipf_regew(). Added. zipfile.c (Ed) 16. Handle reading and writing OEM comments. zipfile.c (Ed) 17. Update Zip64 data descriptor note. zipfile.c (Ed) 18. Format filetypes() check. zipup.c (Ed) 19. Update note to remember to force deflation for descriptors by release. zipup.c (Ed) 20. In compression code using libraries, enable dots for noisy also. zipup.c (Ed) 21. Update extended help to add more of the basic options and compression method. zip.c (Ed) 22. Add additional lines bz_opt_ver2 and bz_opt_ver3 to bzip2 version to give credit to bzip2. zip.c (Ed) 23. Add descriptions to version information for USE_EF_UT_TIME, NTSD_EAS, WILD_STOP_AT_DIR, WIN32_OEM, LARGE_FILE_SUPPORT, ZIP64_SUPPORT, and UNICODE_SUPPORT similar to how UnZip does. zip.c (Ed) 24. Add note that crypt is modified in Zip 3. zip.c (Ed) 25. Use abbrevmatch() and update warnings for compression method selection. zip.c (Ed) 26. Update config to handle either using IZ_BZIP2 to define the location of the bzip2 files or the bzip2 directory. unix/configure, zipup.c, zip.c (SMS, Ed) ---------------------- July 14th 2006 version 3.0f15 ---------------------- 1. Change USE_BZIP2 to BZIP2_SUPPORT in VMS. vms/descrip_src.mms, vms/build_zip.com (SMS) 2. Add SYS$DISK:. vms/descrip.mms, vms/build_zip.com (SMS) 3. Change vms/install.txt to [.vms]install.txt. bzip2/install.txt (SMS) 4. Change VMS files to lower case. vms/mod_dep.com, vms/install_vms.txt, vms/zip.opt, vms/hlp_lib_next.com, vms/notes.txt, vms/unixlib_gcc.h, vms/unixio_gcc.h (SMS) 5. Remove old VMS files. vms/descrip-old.mms (removed), vms/link_zip.com (removed), vms/make_zip.com (removed), vms/makefile.vms (removed) (SMS) ---------------------- July 24th 2006 version 3.0f16 ---------------------- 1. Fix global dots so can set with dot size. deflate.c, fileio.c (Ed) 2. Update License top line to refer only to license. License (Cosmin) 3. Update License. License (Ed) 4. Implement zero length UTF-8 path length as flag standard path is UTF-8 and should use that. This allows Zip to use the standard path as UTF-8 when the local character set is UTF-8. zipfile.c (Ed) 5. Update WhatsNew. WhatsNew (Ed) 6. Change case of bzip2/install.txt. INSTALL (Ed) 7. Change MANUAL.txt to ZIP.txt and update ftp site. README (Ed) 8. Update announcement. zip30f.ann (Ed) 9. Now also check if OS has bzip2 library and can use that. unix/configure, zip.c (Mark Adler, Ed) 10. Add fix from akt@m5.dion.ne.jp in Japan to recurse on doublebyte characters without processing in recmatch(). This should not be needed unless the rest of the code in there is broke for Japanese character sets in some way. Need to test. util.c (Ed) 11. Add note for bzip2. zip.c (Ed) 12. Do not do seek wrap test if ftell() returns -1 as from a pipe. Add output of last ftell() and current ftell() for zipfile too big seek error. zipup.c (Ed) 13. Add version to the options table. Remove the check to display version before the command line is processed. Add to option -v a check to display the version if that is the only argument. Can still enable verbose with piping by using zip -v - - format. zip.c (Ed) 14. Add abbrevmatch() for -UN option. zip.c (Ed) ---------------------- August 7th 2006 version 3.0f17 ---------------------- 1. Change license modifications to retain intent of copyright holders, as any major change in license conditions would require contacting all copyright holders. LICENSE (Greg, Ed) 2. Move debugging statement after zipstdout() where mesg is set to stderr. Add mesg and fflush() to sd messages where needed so that messages go to stderr when piping. zip.c (Ed) 3. Update encryption comment. zipup.c (Ed) 4. Do not use data descriptors for directories. zipup.c (Mark, Ed) 5. Update Q & A to match license. README (Ed) 6. Update WhatsNew. WHATSNEW (Ed) 7. Add ifndef around version_info() for dll. zip.c (Ed) 8. Add -TT (--unzip-path) to allow setting the unzip command to use with -T to test the archive. zip.c (Ed) 9. Add -DF (--difference-archive) which requires --out and turns off copying unchanged entries to the new archive creating an archive with just the changes and additions since the original archive was created. zip.c, globals.c, zip.h (Ed) 10. Update help. zip.c (Ed) ---------------------- September 7th 2006 version 3.0f18 ---------------------- 1. Split -t and -tt options and remove limitation that only one can be used to allow setting a date range. zip.c, WhatsNew (Ed) 2. Minor changes in comments. zipfile.c (Ed) 3. Add entries for format of Unicode Path and Unicode Comment extra fields. proginfo/extrafld.txt (Ed) 4. Change note at top of infozip.who, but needs to be updated with all new contributors. proginfo/infozip.who (Ed) 5. Note Zip 3 and UnZip 6 now support Zip64. proginfo/ziplimit.txt (Ed) 6. Add note on Unicode. README (Ed) 7. Update WHATSNEW. WHATSNEW (Ed) 8. Update help. zip.c (Ed) 9. Add {} support to -TT option, allowing insertion of temp archive path into the command string to -TT similar to Unix find does. zip.c (Ed) 10. Start changes for -F fix option. Add checks when reading input archive and skip bad central directory entries and bad local entries. Currently -F requires the central directory to be intact (except for bad CD entries that will be skipped) and local entries and data to be where the central directory say they are. This allows all recovered entries to be complete with all central directory information. Calculate CRC of input entry and compare to CRC from central directory. Allow skipping split disks the user may not have. Store state of output archive before each local entry and data are read, allowing seeking back and restoring state to skip bad entries. fileio.c, global.c, zipfile.c, zip.h (Ed) 11. Started changes for fixfix. fileio.c (Ed) 12. Update help on -t and -tt. zip.c (Ed) 13. Add note on Unicode support, but may change if add handling of names with characters not supported in current character set. README (Ed) 14. Combined ToDo30.txt and ToDo but more to be done. TODO (Ed) 15. Update ToDo list. ToDo30.txt (Ed) 16. Add -F and -FF to help. zip.c (Ed) 17. Run fix mode in copy mode, as it is copying from one archive to another, and use those checks. zip.c (Ed) 18. Add Try -F and Try -FF warnings in places. zipfile.c (Ed) 19. Allow reading version 4.6 (bzip2) archives. zipfile.c (Ed) 20. Add Unicode Path and Unicode Comment extra field descriptions. proginfo/extrafld.txt (Ed) 21. First attempt at updating the Who file. proginfo/infozip.who (Ed) 22. Add note to top of ziplimit.txt. proginfo/ziplimit.txt (Ed) 23. Add possible fix for paths returned by the Win32 directory scan with '?' in the name. These are characters in the Unicode name stored on disk but not represented in the multi-byte character set used by zip for the scan. In this case, return the short name in 8.3 format so directory scan can continue. Could put the Unicode name in the Unicode extra field, but not done. Add warning when long name is replaced by short name. Not fully tested. win32/win32zip.c, zip.h, zip.c, fileio.c (Ed) 24. If archive name and -sf are the only parameters, list archive contents. zip.c (Ed) ---------------------- September 8th 2006 version 3.0f19 ---------------------- 1. Fix error message. zipfile.c (SMS, Ed) 2. Put crc32() in ifndef UTIL as only needed for fix. fileio.c (SMS, Ed) ---------------------- November 3rd 2006 version 3.0f20 ----------------------- 1. Fix comment. vms/vmszip.c (SMS) 2. Include oem_to_local_string() if UNICODE_SUPPORT. win32/win32.c, zip.h (Ed) 3. Modify procname_win32() to flag a path not supported by the local character set so can get Unicode for it. Check Unicode names. win32/win32zip.c (Ed) 4. Add matching of escaped Unicode names to proc_archive_name() that reads entries from an archive. Add sorted zlist zusort. globals.c, fileio.c, zip.h, zipfile.c (Ed) 5. Add support for non-local character set names and paths for WIN32, getting and storing the UTF-8 path when needed. Use 8.3 name when normal name has characters not supported in current local character set. Note when short name used. zip.c, fileio.c (Ed) 6. Add support for fix = 2 which reads local headers first to bfcopy(). fileio.c, zip.h (Ed) 7. Allow selection of .zip split in ask_for_split_read_path() when reading a split archive that has no end records giving the total split count. fileio.c (Ed) 8. Add zoff_t casts to dot counts. fileio.c (Ed) 9. Comment changes for Unicode. fileio.c (Ed) 10. Call wide_to_local_string() separately in utf8_to_local_string() to free up temp value. fileio.c (Ed) 11. Support new AppNote bit 11 for forcing UTF-8, but needs finishing. globals.c (Ed) 12. Add to zlist struct zuname for the escaped version of the UTF-8 name in uname and add ouname for the display version of zuname. zip.c, zip.h, zipfile.c (Ed) 13. Add zipmessage_nl() that can output to the screen and to the log file like zipmessage(), but can write lines without a newline. zip.c, zip.h, zipcloak.c, zipnote.c, zipsplit.c (Ed) 14. Update help for -FF and Unicode. zip.c (Ed) 15. Change > to >= for byte message check to avoid -0 (negative zero). zip.c (Ed) 16. Add -su show unicode option which adds escaped unicode paths to -sf. Also uses show_files = 3. zip.c (Ed) 17. Update comments for -UN and -X. zip.c (Ed) 18. Add support for new AppNote bit 11 that says standard path and comment have UTF-8 when -UN=f is used. zip.c (Ed) 19. Fix zipfile name message by replacing value with zipfile. zip.c (Ed) 20. Add new code for -FF, which processes archives by trying to read the EOCDR to get split count, then starting with the local entries. This option does not use the standard code but does everything itself. Add scanzipf_fixnew(), which tries to read the EOCDR, then the local entries, then the central directory. zip.c, zipfile.c (Ed) 21. Update note for ZIP64_CENTRAL_DIR_TAIL_SIZE. zipfile.c (Ed) 22. Put read_Unicode_Path_entry() and read_Unicode_Path_local_entry() into UNICODE_SUPPORT ifdef. zipfile.c (Ed) 23. Add zuqcmp() and zubcmp() to support Unicode sorted list of paths. zipfile.c (Ed) 24. Update zsearch() to also search unicode paths. zipfile.c (Ed) 25. Split out iname in read_Unicode_Path_entry() for debugging. Should put it back. Update Unicode mismatch warning. zipfile.c (Ed) 26. Update Unicode in readlocal(). zipfile.c (Ed) 27. Add more Unicode support to scanzipf_regnew(). zipfile.c (Ed) 28. Add support for fix = 2 to zipcopy(). Add checks and warnings, but allow scan to continue when can. Use local data to fill in central directory fields in case no central directory entry for local entry. zipfile.c (Ed) 29. Add get_win32_utf8path() to get UTF-8 from Windows if can. zipfile.c (Ed) ---------------------- November 7th 2006 version 3.0f21 ----------------------- 1. Add crude data descriptor support to -FF in bfcopy() that should be updated by release. fileio.c (Ed) 2. Change %d to %s and use zip_fzofft() to format zoff_t byte count. zipfile.c (SMS, Ed) 3. Call local_to_oem_string() for only WIN32 in zipcopy(). zipfile.c (SMS, Ed) ---------------------- November 29th 2006 version 3.0f22 ----------------------- 1. Change ' to " in extended help. zip.c (Ed) 2. Change -dv disk number display to indisk>outdisk. zip.c (Ed) 3. Finish -FF fix option. Move detailed output to require -v. zip.c (Ed) 4. Add note to help to use -v with -FF to see details. zip.c (Ed) 5. Add -sU option to view only Unicode names when exist. zip.c (Ed) 6. Change default dot size in verbose from every buffer to 10 MB. zip.c (Ed) 7. Exit if --out and in path same as out path. zip.c (Ed) 8. Remove verbose information when fixing archive. zip.c (Ed) 9. Initialize in disk to 0, but still problem with disk number of first entry for each disk lagging by 1. zip.c (Ed) 10. Consistently use ZE error codes for exit from ask_for_split_read_path. zipfile.c, zip.c (Ed) 11. Seek back when fix finds bad entries. Also skip last entry of split if next split is missing. Should check if entry completed. zip.c (Ed) 12. Add messages to -sd for writing the central directory, replacing the old zip file, and setting file type. zip.c (Ed) 13. Don't set file type on stdout. zip.c (Ed) 14. Increase errbuf from FNMAX + 81 to FNMAX + 4081. zip.h (Ed) 15. Add skip_this_disk, des_good, des_crc, des_csize, and des_usize globals for -FF and reading data descriptors. Change note on display_volume. Add global skip_current_disk. zip.h, globals.c (Ed) 16. BFWRITE_HEADER define now also does data descriptor. zip.h (Ed) 17. Skip zipoddities() if fix. Maybe can later add back. zipfile.c (Ed) 18. Update fix messages. zipfile.c (Ed) 19. Allow user to end archive early using ZE_EOF. zipfile.c, fileio.c (Ed) 20. Only show split numbers and offsets for -FF if verbose. zipfile.c (Ed) 21. Handle spanning signature at top of split archive. zipfile.c (Ed) 22. Only close in_file if open. zipfile.c (Ed) 23. Add note if no .zip and only splits suggest use -FF. zipfile.c (Ed) 24. In putlocal() and putcentral() only convert to OEM if z->vem == 20. zipfile.c (Ed) 25. Do not OEM convert archive comment as PKWare says this should be ASCII. zipfile.c (Ed) 26. Fix swap of siz and len and LOCSIZ and LOCLEN. zipfile.c (Ed) 27. Call read_Unicode_Path_local_entry() before OEM conversion so Unicode checksum checks iname before conversion. zipfile.c (Ed) 28. Only check if local and central crc match if not stream entry. zipfile.c (Ed) 29. Keep data descriptors if fix == 2, but need to look at this. zipfile.c (Ed) 30. Fix bug adding up header bytes in n by adding 4 for signature. zipfile.c (Ed) 31. If fix == 2 use local crc for central, otherwise use central crc for local. zipfile.c (Ed) 32. In zipcopy(), check data descriptor and skip if not correct one. zipfile.c (Ed) 33. Add SH, LG, and LLG macros from zipfile.c to allow reading the data in the data descriptor. fileio.c (Ed) 34. In bfcopy(), read and check the data descriptor if n == -2. If run out of bytes before find descriptor, return error. fileio.c (Ed) 35. In ask_for_split_read_path(), increase buf to SPLIT_MAX_PATH + 100, fix bug by adding "- 1", set split_dir = "" if current directory, and update prompts to add skip and end choices. Add skip and end choices. fileio.c (Ed) 36. Increase buffer for fgets to SPLIT_MAXPATH. fileio.c (Ed) 37. Update WhatsNew. WhatsNew (Ed) ---------------------- December 10th 2006 version 3.0f23 ----------------------- 1. Handle additional ODS5 issues by upper casing many symbols and file names. vms/build_zip.com, vms/collect_deps.com, vms/descrip.mms, vms/descrip_mkdeps.mms, vms/descrip_src.mms, vms/find_bzip2_lib.com (SMS) 2. Update VMS Find Help Library code. vms/hlp_lib_next.com (SMS) 3. Instead of tempname use temp_name as parameter to avoid function tempname(). zipsplit.c, zipnote.c, zipcloak.c, zip.c (Ed) 4. If fixing archive with -FF and no EOCDR to get disk count, see if top of archive has spanning signature or local header and guess if it is single-disk archive, then ask user to confirm. zipfile.c (Ed) 5. For Unix where NO_MKSTEMP is not defined, replace mktemp() with mkstemp() that avoids a race condition. zip.c, zipcloak.c, zipnote.c, fileio.c (Ed) 6. Eliminate mkstemp() warning by using mkstemp() instead of mktemp() for Unix. Only for UNIX and if NO_MKSTEMP is not defined. Many OS do not have mkstemp(). zipcloak.c, zipnote.c, zip.c, fileio.c (Ed) 7. If UNICODE_SUPPORT and UNIX then try to switch to UTF-8 locale to allow displaying of Unicode, otherwise just get escapes. This results in some characters displaying as whitespace if needed fonts, such as East Asian, are not installed. zip.c (Ed) 8. If new global unicode_escape_all is set, then escape all non-ASCII characters when converting Unicode file path. This allows viewing paths as escapes on Unix that would otherwise be white space. If not set, any characters that map to the current locale are returned as is. Can only display if either supported as base by the OS or fonts installed. Set using -UN=escape option. zip.c, fileio.c, zip.h, globals.c (Ed) 9. Update extended help for Unicode. zip.c (Ed) 10. All variables used by Win32 in global.c should now be initialized at start so dll is initialized each call. zip.c (Ed) ---------------------- January 1st 2007 version 3.0f24 ----------------------- 1. Fix a problem when building with (old, obsolete) IM attribute encoding combined with bzip2 support. vms/descrip_src.mms (SMS) 2. Update WHATSNEW. WhatsNew (Ed) 3. Update README. ReadMe (Ed) 4. Remove in_crc code. Too involved to implement but may look at later. fileio.c, globals.c, zip.c (Ed) 5. Use 0x50 and 0x4b for 'P' and 'K' in signatures to handle EBCDIC case. zipfile.c, fileio.c (Ed) 6. Implement new -FS file sync option that deletes entries missing on the file system from an archive being updated. globals.c, zip.c (?, Ed) 7. Update help. zip.h, zip.c (Ed) 8. Include scanning files dots when update small but new file scan long. zip.c (Ed) 9. Ask if single-file archive when using -FF and can't tell. zipfile.c (Ed) 10. Display message when entry would be truncated. zipfile.c (Ed) 11. Check for VMS_IM_EXTRA. Update bzip2 support for VMS. Change destination directory if large-file enabled. vms/build_zip.com, vms/descrip_src.mms (SMS) 12. Change parameters for VMS bzip2 search. vms/find_bzip2_lib.com (SMS) ---------------------- January 12th 2007 version 3.0f25 ----------------------- 1. Incorporate faster crc32.c including the Rodney Brown changes (originally implemented in the zlib project) from UnZip, which includes the IZ_CRC_BE_OPTIMIZ and IZ_CRC_LE_OPTIMIZ optimizations when those symbols are defined. These modifications include: - enlarge unrolling of loops to do 16 bytes per turn - use offsets to access each item - add support for "unfolded tables" optimization variant crc32.c (Christian) 2. As the crc32.c module now includes crc table generation, remove crctab.c. crctab.c (remove) (Christian) 3. Update crc i386 assembler code from UnZip (details see above). win32/crc_lcc.asm, win32/crc_i386.asm, win32/crc_i386.c, crc_i386.S (Christian) 4. Guard against redefinition of symbols @CodeSize and @DataSize in memory model setup section to work around Open Watcom (version 1.6) wasm assembler problem. msdos/crc_i86.asm (Christian) 5. Change type of keys[] array for new crc, add IZ_CRC_BE_OPTIMIZ, and use new crypt crc table. Use header buffer instead of buf for header. crypt.c, crypt.h (Christian) 6. Update version and remove crc table. crypt.h (Christian) 7. Add crc32.h, change sprintf() format for disk number from d to lu as can go over 16-bit, remove crc32u(). fileio.c (Christian) 8. Update to use new crc. msdos/makefile.bor, msdos/makefile.dj1, msdos/makefile.dj2, msdos/makefile.emx, msdos/makefile.msc, msdos/makefile.tc, msdos/makefile.wat, unix/Makefile, vms/build_zip.com, vms/descrip_deps.mms, vms/descrip_src.mms, vms/osdep.h, win32/makefile.bor, win32/makefile.dj, win32/makefile.emx, win32/makefile.gcc, win32/makefile.ibm, win32/makefile.lcc, win32/makefile.w10, win32/makefile.w32, win32/makefile.wat, win32/makenoas.w32, win32/vc6/zip.dsp, win32/vc6/zipcloak.dsp, win32/vc6/zipnote.dsp, win32/vc6/zipsplit.dsp, win32/vc6bz2/zip.dsp, win32/vc6bz2/zipcloak.dsp, win32/vc6bz2/zipnote.dsp, win32/vc6bz2/zipsplit.dsp, windll/visualc/dll/zip32.dsp, windll/visualc/dll/zip32.mak, windll/visualc/lib/zip32.dsp, win32/visualc/lib/zip32.mak (Christian) 9. Include crc32.h. Make variable uname local in proc_archive_name(). Remove unused num and new_base_path. Change %02d to %02l2 for disk number in print format. Remove crc32u() as now use crc32(). Add parentheses around conditions in loops. Use 0 instead of NULL for zwchar. fileio.c (Christian) 10. Add z_uint4 defines from crypt.c to tailor.h. Move uch, ush, and ulg typedefs before tailor.h include which needs them. tailor.h, zip.h (SMS) 11. Include crc32.h. change add_name() to return not int but long since number of command line arguments can exceed 16 bits. Cast variable option to (int) for subtraction. Change 0x400 to 0x400L. Add braces to show_files print block. zip.c (Christian) 12. Add warning if use -F or -FF without --out. Change defined(NO_MKSTEMP) to !defined(NO_MKSTEMP). zip.c (Ed) 13. Define EC64LOC and EC64REC for size of Zip64 EOCD Locator and Zip64 EOCD Record. Add extern for crc_32_tab. Move crc32() to crc32.h. zip.h (Christian) 14. Add crc.h. zipcloak.c (Christian) 15. Include crc32.h. Comment out scanzipf_reg() and scanzipf_fix() as no longer used, which are left in for now for comparison. Cast blocksize to extent for malloc(). Instead of 0x10000 malloc 0xFFFF for extra field block so fits in 16 bits. Instead of crc32u() use crc32(). Only do lflg != flg check for fix == 2. Add comments to various #endif. Indent comment. Comment out copy_sig() which is not used. Reduce size of SCAN_BUFSIZE to EC64REC for MEMORY16. Use ENDHEAD for EOCDR size. Change %u to %lu in print formats for disk count. Use EC64LOC for size of Zip64 EOCD Locator. Use EC64REC for size of Zip64 EOCD Record. Add streaming and was_zip64 to ZIP64_SUPPORT. Remove lflg != flg check in zipcopy(). zipfile.c (Christian) 16. Add note that z-flg & ~0xf check will fail if new bit 12 for UTF-8 paths and comments is set. Update -FF warning. zipfile.c (Ed) 17. Include crc32.h. Modify tempzn update. Fix comment. Set z->lflg = z->flg after deflate as deflate may have set bits in z->flg [Ed, Christian]. Include BZIP2_SUPPORT block in !UTIL block. zipup.c (Christian) 18. Changes to use crc32.c. acorn/gmakefile, acorn/makefile, amiga/lmkfile, amiga/makefile.azt, amiga/smakefile, aosvs/make.cli, atari/makefile, atheos/makefile, beos/makefile, cmsmvs/cczip.exec, cmsmvs/mvs.mki, cmsmvs/zip.makefile, cmsmvs/zipmvsc.job, cmsmvs/zipvmc.exec, human68k/makefile, human68k/makefile.gcc, novell/makefile, novell/zip.lnk, os2/makefile.os2, qdos/makefile.qdos, qdos/makefile.qlzip, tandem/history, tandem/macros, tandem/tandem.h, theos/makefile, tops20/make.mic, unix/configure, unix/makefile, win32/makefile.a64 (Christian) 19. Add note to use BZ_NO_STDIO. bzip2/install.txt (Ed) 20. Remove crctab. cmsmvs/zipvmc.exec (Ed) 21. Update comment. macos/source/pathname.c (Christian) 22. Start of manual update. Zip.1 (Ed) 23. Changes to use crc32.c. vms/descrip.mms, vms/descrip_deps.mms, vms/descrip_mkdeps.mms, vms/descrip_src.mms, vms/vms.c (SMS) ---------------------- January 17th 2007 version 3.0f26 ----------------------- 1. Add note for UnZip. crypt.c (Christian) 2. Change current_disk and disk_number from int to ulg. Change num from int to unsigned int. [Even though a 16-bit system likely won't see more than 64k disks, it probably should be ulg - Ed] Remove unused mbsize. Change match from long to int as the number of possible options should always fit in that. fileio.c, globals.c (Christian) 3. Use -Gt to force some data into separate data segments so all data fits. msdos/makefile.msc (Christian) 4. Move some copyright constants to far to save near space. revision.h (Christian) 5. Change u for character from int to unsigned int. util.c (Christian) 6. Move include of crc32.h from vms/vms.c to vms/vms_pk.c. vms/vms.c, vms/vms_pk.c (Christian) 7. Update crci386_.o. win32/makefile.gcc (Christian) 8. Use NOASM=1 to disable assembler and clear variables when do not. win32/makefile.w32 (Christian) 9. Remove unused totalslashes and returnslashes from get_win32_utf8path(). win32/win32zip.c (Christian) 10. Remove local versions of tempzip and tempzf. zip.c (Christian) 11. Make options[] far. Change cd_start_disk from int to ulg. Cast -1 to (ulg) for cd_start_disk. Put here = zftello() in DEBUG defines. zip.h, zip.c (Christian) 12. Change length of zipfile comment parameter from ush to extent. Change disk numbers from int to ulg in close_split(), ask_for_split_read_path(), ask_for_split_write_path(), get_in_split_path(), find_in_split_path(), get_out_split_path(). Add Far to longopt and name strings in option_struct. zip.h (Christian) 13. Add far to options[]. zipcloak.c (Christian, Ed) 14. Define write_string_to_mem() only for UNICODE_SUPPORT. Change ulg to extent for append to mem memory offset and blocksize parameters. Make at_signature() local. Cast usValue to char. Remove unused oname in read_Unicode_Path_local_entry(). Remove local definitions of zip64_entry as Zip is always processing one entry at a time and this is a global flag for the current entry. Make find_next_signature() and find_signature() local. Add ZCONST to signature parameter. Make is_signature() and at_signature() local. Change m, result of fread(), from int to extent. Reduce SCAN_BUFSIZE from 0x40000 to the size of the largest header being read. As find_next_signature() is used to scan for the next signature and that reads a byte at a time, the scan buf is only used to read in the found headers. Since we skip the extra parts of the Zip64 EOCDR, all headers are a fixed size. Remove unused variables from scanzipf_fixnew(). Use ENDCOM for end comment offset. Instead of 64 KB seek back 128 KB to find EOCDR. Use ENDOFF and ENDTOT for offsets in EOCDR. Remove tabs. Merge versions of putend(). Update Amiga SFX. Remove unused offset in zipcopy(). Make size local in zipcopy(). zipfile.c (Christian) 15. Update putend() comment. zipfile.c (Ed) 16. Add far to options[]. zipnote.c, zipsplit.c (Christian) 17. Add NO_ASM versions of Win32 zipnote, zipsplit, and zipcloak projects. Add crc32.h and crc32.c to zipsplit and zipnote projects. win32/vc6/zipsplit.dsp, win32/vc6/zipnote.dsp, win32/vc6/zipcloak.dsp (Ed) 18. Add NO_ASM versions of Win32 bzip2 zipnote, zipsplit, and Zipcloak projects. Add crc32.h and crc32.c. win32/vc6bz2/zipsplit.dsp, win32/vc6bz2/zipnote.dsp, win32/vc6bz2/zipcloak.dsp (Ed) 19. Update Win32 dll and lib projects and make files. windll/visualc/lib/zip32.dsp, windll/visualc/lib/zip32.mak, windll/visualc/dll/zip32.dsp, windll/visualc/dll/zip32.mak (Ed) 20. Remove space in front of #ifdef and other conditionals that slipped in. zipfile.c, zipup.c (SMS) 21. Updates for bzip2. vms/bzlib.h, vms/install_vms.txt (SMS) 22. Updates. vms/notes.txt (SMS) 23. Update copyrights. crc32.c, deflate.c, globals.c, revision.h, ziperr.h, trees.c, win32/nt.c, win32/win32.c, win32/win32i64.c, win32/win32zip.h, win32/zipup.h (Ed) 24. Update WhatsNew. WHATSNEW (Ed) ---------------------- February 4th 2007 version 3.0f27 ----------------------- 1. Fix array sizes and loop lengths in wide_to_escape_string(). fileio.c (Johnny, Ed) 2. Fix escape_string_to_wide() to handle hex strings, then comment out as not used. zip.h, fileio.c (Ed) 3. Use ZIPERRORS() macro instead of ziperrors[] array. zip.c, zipcloak.c, zipnote.c, zipsplit.c (SMS) 4. Add VMS-compatible "severity" values, add new ZE_SEV_PERR define to set when perror() needs to be called, add ZIPERRORS() macro, change PERR() to use ZE_SEV_PERR, change ziperrors[] to new structure array to hold error strings, add new VMS facility names and severity codes assigned by HP to ziperrors[] array, and add new official VMS_MSG_IDENT. ziperr.h (SMS) 5. Change ZE_SEV defines to ZE_S to save space and reformat ziperrors[]. ziperr.h (Ed) 6. Update install.txt to include generic Unix case. bzip2/install.txt (Ed) 7. Add creation of message file and add NOMSG message. vms/build_zip.com, vms/descrip.mms, vms/install_vms.txt (SMS) 8. Update notes.txt to add changes to program exit status values and changes to messages. vms/notes.txt (SMS) 9. Include crc32.h, include ssdef.h, instead of FAB_OR_NAM use FAB_OR_NAML, add status code summary note detailing old versus new error codes, and if CTL_FAC_IZ_ZIP is 0x7FFF and OLD_STATUS is defined use old VMS error codes. vms/vms.c (SMS) 10. Change FAB_OR_NAM to FAB_OR_NAML and remove NAME_DNA, NAME_DNS, NAME_FNA, and NAME_FNS. vms/vms.h (SMS) 11. Change FAB_OR_NAM to FAB_OR_NAML. vms/vms_im.c, vms/vms_pk.c, vms/vmszip.c (SMS) 12. Fix compile warning on VC 2005. win32/makefile.w32 (Johnny) 13. Update readmevb.txt and readvb64.txt. windll/vb/readmevb.txt, windll/vbz64/readvb64.txt (Ed) 14. Change tch from int to ulg in utf8_from_ucs4_char(). Move comments to keep line lengths to 80 characters. fileio.c (Christian) 15. Update comment for total_cd_entries. global.c, zip.c, zip.h (Christian) 16. Comment out unused Adler-16 code. util.c, zip.h (Christian) 17. Add InterlockedExchangePointer() macro if not defined. Update Initialize() to use macro. nt.c (Christian) 18. Move zip64 eocd disk and offset variables next to input archive variables. zip.c (Ed) 19. Remove zipbegset from scanzipf_fixnew() as offsets are ignored when this is fixing archives. Add comment to cd_total_entries. Remove local cd_start_disk and cd_start_offset as these are already global. Use ZIP_UWORD16_MAX when disk number exceeds this to flag use of Zip64. zipfile.c (Christian) 20. Some comment changes. zipfile.c (Ed) 21. Fix indentation in places. zipsplit.c (Christian) 22. Remove unused variable zfile. zipup.c (Christian) 23. Update manual. zip.1, zip.txt, zipsplit.txt (Ed) ---------------------- February 22nd 2007 version 3.0f28 ---------------------- 1. Update notes. vms/notes.txt (SMS) 2. Add stream_lf.fdl to specify carriage control. vms/stream_lf.fdl (SMS) 3. Update License to also refer to www.info-zip.org and to hopefully provide an example of misrepresentative use. LICENSE (Ed) 4. Update Readme. README (Ed) 5. Update WhatsNew. WHATSNEW (Ed) 6. Change output archive cd_start_disk and cd_start_offset to input archive local in_cd_start_disk and in_cd_start_offset in scanzipf_fixnew() and scanzipf_regnew() to avoid mixing in and out. zipfile.c (Ed) 7. Update copyright. Remove crc32.h include. vms/vms.c (Christian) 8. Changes for new crc32. Remove CRC32. Add CRCA_0 and CRCAUO. Add compiling of crc_i386.S. win32/makefile.emx. (Christian) 9. Add handlers for better RSXNT and Windows OEM conversions. Add detailed comments on conversions. win32/osdef.h (Christian) 10. Define CP_UTF8. win32/rsxntwin.h (Christian) 11. Define WIN32_LEAN_AND_MEAN to reduce size of Windows includes. win32/win32.c, win32/win32zip.c, zip.c (Christian) 12. Use only standard FAT attributes if OEM. win32/win32zip.c (Christian) 13. Add use of INTERN_TO_OEM() and related OEM changes. Add console comment. zip.c (Christian) 14. Change severity from char to int. Update macros. ziperror.h. (Christian) 15. Update Visual Basic project to clarify some of the code. windll/vbz64/vbzip.vbp, windll/vbz64/vbzipbas.bas, windll/vbz64/vbzipfrm.frm (Ed) 16. Update copyright. api.c (Ed) 17. Update format for duplicate entry warning. fileio.c (Ed) 18. Instead of ifdef __RSXNT__ use ifdef WIN32. Define WIN32_LEAN_AND_MEAN. Use WIN32_CRT_OEM. Change OEM check from vem == 20 to vem & 0xff00 == 0 and instead of local_to_oem_string() use _INTERN_OEM(). Remove unused first_CD in scanzipf_fixnew(). Instead of oem_to_local_string() use Ext_ASCII_TO_Native(). Instead of local_to_oem_string() use INTERN_TO_OEM(). zipfile.c (Christian) 19. Replace escape from zipsplit man page with '. zipsplit.txt (Christian) 20. Instead of using 20 every time, account for dosify when setting vem. Update FAT comment. zipup.c (Christian) ------------------------ March 3rd 2007 version 3.0f29 ------------------------- 1. Remove crctab.c. vms/build_zip.com (SMS) 2. Add LFLAGS_ARCH. vms/descrip.mms (SMS) 3. Remove redundant includes descrip.h, rms.h, and atrdef.h. vms/vmsmunch.c (SMS) 4. Remove includes descrip.h and rms.h. vms/vmszip.c (SMS) 5. Only define NO_UNISTD_H if __VAX defined or __CRTL_VER is less than 70301000, allowing support of the new symbolic links in VMS. Also use unlink instead of delete if version above 70000000. vms/osdep.h (SMS) 6. Formatting changes. vms/notes.txt, vms/install_vms.txt (Christian) 7. Remove spaces before tabs. win32/makefile.emx (Christian) 8. Formatting change. win32/osdep.h (Christian) 9. If -y on VMS open the link not the target file. vms/vms_im.c (SMS) 10. If -y on VMS search for the link, not the target file. vms/vms_pk.c (SMS) 11. Change default for Unicode path mismatch from error to warning, so processing will continue. zip.c, globals.c (Ed) ------------------------ March 12th 2007 version 3.0f30 ------------------------ 1. Add bzip2 support for the reduced no stdio bzip2 library for VMS and Unix. Use libbz2_ns_.olb for VMS bzip2 library which is compiled from the VMS version of bzip2 with the BZ_NO_STDIO flag set. This flag removes most standard bzip2 stdio support and enables using a callback routine for errors. zbz2err.c, unix/Makefile, vms/build_zip.com, vms/descrip.mms, vms/descrip_deps.mms, vms/descrip_src.mms (SMS) 2. Add zbz2err.c to Win32 vc6bz2 project for support of BZ_NO_STDIO for bzip2. Modify zbz2err.c to handle different ports. zbz2err.c (Ed) 3. Update license. zip.h (Ed) 4. Update copyright. zip.c, zipfile.c, zipup.c, zbz2err.c, revision.h (Ed) 5. Fix bug where directories got set to ver 4.6 in local headers instead of ver 1.0 when using bzip2. zipfile.c, zipup.c (Ed) 6. Minor updates to INSTALL. INSTALL (Ed) 7. Minor updates to README. README (Ed) 8. Add BZ_NO_STDIO to vc6bz2 projects. Error routine seems to work. win32/vc6bz2 (Ed) 9. Set bit FAB$M_BIO (.fab$v_bio) in the FAB when using sys$open() on a symlink. vms/vms_im.c (SMS) 10. Change sys$disk to SYS$DISK. vms/build_zip.com (SMS) 11. Update extended help. zip.c (Ed) 12. Update bzip2 install. bzip2/install.txt (Ed) ------------------------ March 19th 2007 version 3.0f31 ------------------------ 1. Define bz2_olb as LIBBZ2_NS.OLB. Change LIBBZ2.OLB to bz2_olb. Use ZZBZ2ERR.C error callback for bzip2. vms/build_zip.com (SMS) 2. Change NO_SYMLINK to NO_SYMLINKS to be consistent with UnZip. tailor.h, acorn/osdep.h, macos/osdep.h, tops20/osdep.h, vms/osdep.h (SMS) 3. Minor note changes. Add section on Symbolic Links. vms/notes.txt (SMS) 4. Update copyright. globals.c (Ed) 5. Update License with official copy. LICENSE (Greg, Ed) 6. Update Readme. README (Ed) 7. Add support for NO_BZIP2_SUPPORT. tailor.h (Ed) 8. Add common compiler flags to Install. INSTALL (Ed) 9. Remove SPLIT_FILE define. zip.c (Ed) 10. Minor updates to extended help. zip.c (Ed) 11. Modify Makefile to also build bzip2 library if found. Split $MAKE ("make -f unix/Makefile") into $MAKE and $MAKEF, leaving $MAKE as defined by Make and defining $MAKEF to "-f unix/Makefile". Add clean_bzip2 target. unix/Makefile (SMS) 12. Modify configure to handle compiling bzip2. unix/configure (SMS) 13. Remove linking bzip2 with utilities. Other changes. unix/Makefile (Ed) 14. Change bzip2 wrong library errors to warnings. Put back OS bzip2 library check. Only compile bzip2 if in bzip2 directory. unix/configure (Ed) 15. More modifications to Makefile and configure to only allow compiling in the bzip2 directory. unix/Makefile, unix/configure (Ed) ------------------------ March 27th 2007 version 3.0f32 ------------------------ 1. Modify configure and Makefile to only allow compiling bzip2 in the Zip bzip2 source directory. unix/Makefile, unix/configure (SMS, Ed) 2. Update bzip2 installation instructions. bzip2/install.txt (SMS, Ed) 3. Remove need for BZIP2_USEBZIP2DIR define by using an appropiate include dir specification (-I ../../bzip2) when needed. zip.c, win32/vc6bz2/zip.dsp, unix/configure (SMS, Ed, Christian) 4. Update VC6 readme. win32/readmeVC.txt (Christian, Ed) 5. Add crc32.h to VC projects. Add assembler group to zipcloak, zipnote, and zipsplit projects. Add BZ_NO_STDIO to all configurations with bzip2 so reduced bzip2 code is used. win32/vc6/zip.dsp, win32/vc6/zipcloak.dsp, win32/vc6/zipnote.dsp, win32/vc6/zipsplit.dsp (Christian) 6. Update VC6bz2 readme. win32/readVCBZ.txt (Christian, Ed) 7. Modify bzip2 VC6 workspace to use standard zipcloak, zipnote, and zipsplit projects as they don't need bzip2. win32/vc6bz2/zip.dsw (Christian) 8. Fix zlib flag problem by properly setting and clearing deflInit flag to initialize and release resources. zipup.c (Bill Brinzer, Christian) 9. Update copyright. crypt.h, api.c, tailor.h, fileio.c, ziperr.h, zipsplit.c, zipnote.c, zipcloak.c, util.c (Ed) ------------------------ April 25th 2007 version 3.0f33 ------------------------ 1. Fix -dd display_dots option for VMS. Fix adding value for -ds to command line. Fix /NAMES = AS_IS for older header files. cmdline.c (SMS) 2. Add Win32 wide scan support. In fileio.c add Win32 wide functions lastw(), msnamew(), newnamew(), wchar_to_wide_string(), is_ascii_stringw(), wchar_to_local_string(), and wchar_to_utf8_string(). In globals.c add no_win32_wide that is true if the wide versions of calls like GetFileAttributesW() do not work as on Win9x without the Unicode kit. In tailor.h define zwstat for stats that use wchar_t strings and defines SSTATW and LSSTATW. In util.c add isshexpw() and recmatchw() and dosmatchw() for matching using wchar_t strings. In win32.c add FSusesLocalTimeW(), IsFileSystemOldFATW(), GetFileModeW(), GetLongPathEAW(), and zstat_zipwin32w(). In win32zip.c add zdirscanw structure, GetDirAttribsW(), zDIRSCANW, readdw(), wild_recursew(), procname_win32w(), OpenDirScanW(), GetNextDirEntryW(), CloseDirScanW(), procnamew(), local_to_wchar_string(), wchar_to_utf8_string(), in wild() code to check if W versions are supported and send zip down byte or wide path, ex2inw(), in2exw(), and filetimew(). In zipup.h define zwopen to use wide paths. In zipup.c if supported use filetimew() and zwopen(). In zip.h add namew, inamew, and znamew to zlist and flist. In zip.c remove duplicate initialization of use_wide_to_mb_default, force_zip64, zip64_entry, and zip64_archive. Use filetimew() if UNICODE_SUPPORT and using wide paths for directory scan. Remove old 8.3 path Unicode fix as now use wide paths and get all where the 8.3 kluge missed paths where characters in path needed multiple code pages. Changes to bit 11 Unicode but still not ready. fileio.c, globals.c, tailor.h, util.c, zipup.h, win32/win32.c, win32/win32zip.c, win32/win32.h, zipup.c, zip.c (Ed) 3. Update copyright. Don't define UNICODE_SUPPORT if already defined. Define MATCHW and zstat_zipwin32w(). win32/osdep.h (Ed) ------------------------ April 29th 2007 version 3.0f34 ------------------------ 1. Add temporary option -sC to test Unicode file creation enabled with UNICODE_TEST define. zip.c, fileio.c (Ed) 2. On Unix display control characters as ^X as UnZip. (SMS) fileio.c 3. Update extended help. zip.c (Ed) 4. Fix bugs in Unicode changes. zip.c, fileio.c (SMS, Ed) 5. Add NAMES AS_IS support. Handle root dir [000000]. zip.h, vms/install_vms.txt, vms/vmszip.c, vms/vmsmunch.c (SMS) 6. Add global zipfile_exists to handle missing zipfile errors better. zip.h, globals.c, zip.c (Ed) 7. Add functions utf8_to_escape_string(), wide_to_escape_string(), local_to_escape_string(), utf8_to_wchar_string(), and rename wide_to_escape_string() to wide_char_to_escape_string(). fileio.c, win32/win32zip.c, zip.h (Ed) 9. Free f->inamew in fexpel(). Use zuname for matching. fileio.c (Ed) 10. Fix memory bug by setting z->namew, z->inamew, and z->znamew to NULL. Set f->namew, f->inamew, and f->znamew to NULL for new file in newname(). Free wide_string in local_to_utf8(). Other Unicode fixes. Add namew, inamew, and znamew to freeup(). fileio.c, win32/win32zip.c, zip.h (Ed) 11. Move wchar functions only used by Windows to win32zip.c. fileio.c, zip.h (Ed) 12. Fix spelling in manual. zip.1 (SMS, Ed) 13. Add zuebcmp() for Unicode. zipfile.c 14. Open files to read using wide name as input path. zipup.c (Ed) 15. Update help. zip.c (Ed) 16. Change -TT long option from --unzip-path to --unzip-command. zip.c (Ed) 17. Update Manual to include section on Unicode, add -TT option, make some changes to Unicode in other sections, update copyright at bottom, and some small changes to wording and examples. man/zip.1, zip.txt (Ed) 18. Put #ifdef WIN32 around WIN32 blocks. zipfile.c (Ed) ------------------------- May 14th 2007 version 3.0f35 ------------------------- 1. Update VMS to include new options. vms/cmdline.c, vms/zip_cli.cld (SMS) 2. Update VMS help. vms/vms_zip.rnh (SMS) 3. Minor updates to VMS help. vms/vms_zip.rnh (Ed) 4. Create global filter_match_case that defaults to 1 (case-sensitive). zip.c zip.h, globals.c (Ed) 5. Add option -fc to fold case for case-insensitive matching in filter(). Currently enabled only for WIN32. zip.c, win32/osdep.h (Ed) 6. Change (action == DELETE || action == FRESHEN) to filter_match_case in PROCNAME() define. I just couldn't figure out what was going on here and why the case flag was controlled by this. zip.c (Ed) 7. Update WhatsNew. WHATSNEW (Ed) ------------------------- May 17th 2007 version 3.0f36 ------------------------- 1. Touch date on generated file. vms/ZIP_MSG.MSG (SMS, Ed) 2. Update Betas readme to include Release Candidates. Betas_Readme.txt (Ed) 3. Update Zip 3.0f announcement. zip30f.ann (Ed) 4. Minor updates to VMS help. vms/cvthelp.tpu, vms/vms_zip.rnh (SMS) 5. Major changes to VMS CLI help. vms/zip_cli.help (SMS, Ed) 6. Update license. revision.h (Ed) ------------------------- May 21st 2007 version 3.0f37 ------------------------- 1. Rename -fc (fold case) to -ic (ignore case) which may be more intuitive. zip.c (Ed) 2. VMS CLI updates for new options. vms/cmdline.c, vms/vms_zip.rnh, vms/zip_cli.cld, vms/zip_cli.help (SMS) 3. Updates to support Watcom C, mingw, djgppv2 and msc-16-bit, including supporting wide stat and compare calls and work-around for problem with "no symlink support" detection. tailor.h, util.c, zip.c, win32/osdep.h, win32/win32.c, win32/win32/zipup.h (Christian) ------------------------- May 29th 2007 version 3.0f38 ------------------------- 1. Update description. file_id.diz (Ed) 2. Handle better when not splitting and run out of disk space. Also, for split method 1 (automatically write all splits to same place) exit if run out of space instead of filling available space with near empty splits. For split method 2 require splits to be at least 64K bytes (the minimum split size). fileio.c (Ed) 3. Add line break in ziperr() if message line has been started. zip.c (Ed) 4. In ziperr() don't close output handle y if same as current_local_file handle and just closed that. zip.c (Ed) 5. Change default definition of PROCNAME() to handle new filter_match_case flag and restore backward compatibility. zip.c (Christian, Ed) 6. Add note detailing definition of PROCNAME(). zip.c (Ed) 7. Remove nonlocalpath parameter from procname_win32() and procname_win32w() and variables nonlocal_path and nonlocal_name as this is not used now that unicode is implemented in WIN32 using the wide calls. 8. Enable ignore case option for VMS. zip.c (SMS) 9. Update -v and other updates in manual. man/zip.1 (Christian, Ed) 10. Updates for Watcom C and Win32 symlinks. win32/osdep.h (Christian) 11. Fix historic problem with VAX seeking. zipfile.c (SMS) 12. Add NAM_M_EXP_DEV. Add determination if device is in file specification. If device name in file specification do ODS2 and ODS5 down-casing. Define explicite_dev(). vms/vms.h, vms/vmszip.c (SMS) ------------------------- June 4th 2007 version 3.0f39 ------------------------- 1. Update osdep.h to use new filter_match_case flag. vms/osdep.h (SMS) 2. Fix unterminated string bug and trim extra allocated space in local_to_display_string(). fileio.c (Ed) 3. Updated extended help for -u and -ic options. zip.c (Ed) 4. Update Manual. man/zip.1, zip.txt (Ed) ------------------------- June 15th 2007 version 3.0f40 ------------------------- 1. Update Unicode Path and Unicode Comment descriptions based on suggestions from WinZip. proginfo/extrafld.txt (Steve Gross, Ed) 2. Update descriptions for Add, Update, and Freshen in the manual. man/zip.1 (Christian) 3. Update default definition of PROCNAME() to use filter_case_match flag to turn off case matching in filter(). zip.c (Christian) 4. Update WhatsNew. WHATSNEW (Ed) 5. Update announcement. zip30f.ann (Ed) 6. Update manual. man/zip.1, zip.txt (Ed) ------------------------- July 7th 2007 version 3.0f41 ------------------------- 1. Use File Name as Unicode path if UTF-8 flag is set in header. zip.c, globals.c, zipfile.c, zip.h (Ed) 2. Update ToDo. TODO (Ed) 3. Update WhatsNew. WHATSNEW (Ed) 4. Update ReadMe. README (Ed) 5. Fix problems with incompatible stat types on Win32. fileio.c, tailor.h, zip.h, win32/win32.c, win32/win32zip.c, win32/osdep.h (Ed) 6. Define NO_STREAMING_STORE to turn off storing while streaming. INSTALL, zipup.c (Ed) 7. Define UNICODE_ALLOW_FORCE to enable -UN=force option which is now disabled and would need work. globals.c, zip.h (Ed) 8. Add global using_utf8 to flag when OS current character set is UTF-8. If an existing entry has the UTF-8 flag set the flag is kept. If a new entry needs Unicode and on a UTF-8 system assume the strings are UTF-8 and set the UTF-8 flag. globals.c, zip.h (Ed) 9. Update Unicode extra field descriptions. proginfo/extrafld.txt (Ed) 10. Add include directory so can find bzip2 header file when using bzip2 directory. unix/configure (Ed) 11. Fix wide character wild(), wild_recursew() and OpenDirScanW() for Win32 so work like the regular versions. win32/win32zip.c (Ed) 12. Update Unicode in manual. Update -W description in manual zip.1 13. Flush logfile writing. zip.c (Ed) 14. Update extended help for -UN option. Update help for Update to note it updates files where the OS has a later date. Chance -UN=Exit to -UN=Quit so can abbreviate to first letter. zip.c (Ed) 15. Fix a bug in readzipfile() when zip used in pipe. Other pipe fixes. zip.c, zipfile.c (Ed) ------------------------ August 10th 2007 version 3.0f42 ----------------------- 1. Update error message for -DF. zip.c (Ed) 2. Add bzipped message to write to log file. zipup.c (Ed) 3. Update bzip2 install instructions. bzip2/install.txt (Ed) 4. Move local.h include to tailor.h to fix compiler multiple define. tailor.h, zip.c (SMS) 5. Add additional C compiler checks for GNU and HP. unix/configure (SMS) 6. Fix to build libbz2.a. unix/Makefile (SMS) 7. Update copyright. acorn/osdep.h, macos/osdep.h, tops20/osdep.h, vms/vmszip.c, vms/vmsmunch.c, vms/vms_pk.c, vms/vms_im.c, vms/vms.h, vms/vms.c, vms/osdep.h, win32/rsxntwin.h, win32/osdep.h, win32/nt.c (Ed) 8. Change zfeeko(file, 0, SEEK_SET) to rewind(file) in ffile_size() so EOF is always reset. This was creating problems in WIN32 when NO_ZIP64_SUPPORT was set but LARGE_FILE_SUPPORT was set. zipfile.c (Ed) 9. Update compile -v descriptions for LARGE_FILE_SUPPORT and ZIP64_SUPPORT to be more specific as to what each does. zip.c (Ed) 10. Fix bug that added the local header size to the next entry compressed size giving a wrong compressed size error if splitting and the split occurs when writing a local header. fileio.c (Ed) 11. Remove UNICODE_TEST define from VC 6 projects. win32/vc6/zip.dsp, win32/vc6/zipcloak.dsp, win32/vc6/zipnote.dsp, win32/vc6/zipsplit.dsp (Ed) 12. Update extended help. zip.c (Ed) 13. Only output -FF central directory messages in verbose mode. zipfile.c (Ed) 14. Add note about possible bug when copying entries from a split archive. WHATSNEW (Ed) ------------------------ August 11th 2007 version 3.0f43 ----------------------- 1. Display locale inside check to avoid NULL locale. zip.c (SMS, Ed) 2. Add include wchar.h to tailor.h. tailor.h (SMS) ------------------------ August 21st 2007 version 3.0f44 ----------------------- 1. Remove verbose messages when setting locale as verbose flag is not set yet. zip.c (SMS, Ed) 2. Change reading splits message "abort archive" to "abort archive - quit" and change selection letter from a to q so q quits consistently. For quit, don't confirm as more annoying than helpful. fileio.c (Ed) 3. In bfwrite() handle case where a split ends at the end of one entry and trying to write the next local header forces opening next split. This caused copying entries from one archive to another to fail if this came up. Also handle case where a new split is needed while writing central directory entries. Now close last split and update pointers to point to the new split. fileio.c (Ed) 4. Update use of mesg_line_started and add new logfile_line_started to account for line ends in logfile. fflush() output. zip.c, zip.h, globals.c (Ed) 5. Move setting split size if input archive is split and split_size not set to after archive is read. zipfile.c, zip.c (Ed) 6. Update Manual to describe Unicode as implemented and note that old splits are not automatically excluded. man/zip.1, zip.txt (Ed) 7. Update WhatsNew to remove note that creating and copying split archives is broke as it seems fully working now. WHATSNEW (Ed) 8. Update announcement. zip30f.ann (Ed) ------------------------ August 31st 2007 version 3.0f45 ----------------------- 1. Unicode fix for VMS. tailor.h (SMS) 2. Add member current to zlist structure to flag when an archive entry is current with the matching OS file using file time and size. This is used by File Sync to copy current entries from archive. zip.h, zip.c (Ed) 3. Comment out zip info verbose extra data message as this message does not seem to add much. zipfile.c (Ed) 4. Add local and central directory Version Needed To Extract to mismatch warning. Update warning text. zipfile.c (Ed) 5. Add function BlankRunningStats() to output blanks for the running stats part of the line to use when displaying stats for entries not on the mark list so all output lines up. zip.c 6. Add -FS to extended help as new mode. zip.c (Ed) 7. Update description of -FF to remove Assume Worst. zip.c (Ed) 8. Add all_current flag that is set if all entries in archive are current and skip updating archive if -FS and all entries are current. zip.c (Ed) 9. Change argv[] to args[] for "try: zip" error message as message depends on new argument order in args where options are now at beginning. zip.c (Ed) 10. For File Sync, copy entries to new archive if file time and size are the same. If verbose, output ok when copying current entries, otherwise no message when current_entry. Set all_current to 0 if an entry not marked or a file not on OS as need to avoid the All Current message in these cases to catch only deletions. zip.c (Ed) 11. Initialize variables excluding zipstate and setjmp() if USE_ZIPMAIN defined to fix bug when recall zipmain(). zip.c (Ed) 12. Update Manual. zip.1, zip.txt (Ed) 13. Update WhatsNew. WHATSNEW (Ed) 14. Update announcement. zip30f.ann (Ed) ----------------------- September 5th 2007 version 3.0f46 ---------------------- 1. Move write of local header after when GPB11 UTF-8 bit set in putlocal(). zipfile.c (Ed) 2. Change to uppercase for compatibility. vms/install_vms.txt (SMS) 3. Set cenbeg and bytes_this_split to fix grow. Check if grow split archive. zipfile.c, zip.c (Ed) ----------------------- September 14th 2007 version 3.0f47 -------------------- 1. Include address for new Info-ZIP forum. Add note on 16-bit OS support. Add note about text file line ends. README (Ed) 2. Update WhatsNew to include latest on Unicode. Add section on plans for Zip 3.1. WHATSNEW (Ed) 3. Minor change in note for Unicode in extended help. zip.c (Ed) 4. Modify definitions of Unicode extra fields based on discussions with PKWare and WinZip. proginfo/extrafld.txt (Ed) 5. Add note on UTF-8 flag. INSTALL (Ed) 6. Minor updates to ToDo list. Needs more work. TODO (Ed) 7. Update announcement. zip30f.ann (Ed) 8. Change definition of IZ_OUR_BZIP2_DIR to be compatible with Configure and to work with HP-UX. unix/Makefile (SMS) ------------------------ September 24th 2007 version 3.0f --------------------- 1. Update extended help Unicode description. zip.c (Ed) 2. Update Readme. README (Ed) 3. Fix case of define identifying IA64. vms/vms.c (SMS) 4. Update announcement date. zip30f.ann (Ed) 5. Update Unicode extra field definitions based on changes proposed for AppNote. extrafld.txt (Ed) ------------------------ October 17th 2007 version 3.0g01 --------------------- 1. Can get stuck on open Unix FIFO so default to skip and add option -FI to enable reading FIFO. Add global allow_fifo. zip.c, zip.h, globals.c (Willus 0, Ed) 2. As problems with MinGW with wide-character paths, disable wide-character Unicode support. zip.c, unix/unix.c (Willus 0, Ed) 3. Update manual installs to include zipcloak.1, zipnote.1, and zipsplit.1 pages. unix/Makefile (Ed) 4. Update Solaris packages. unix/Packaging/pkginfo.in, unix/Packaging/postinstall, unix/Packaging/preinstall.in, unix/Packaging/prototype (SMS) ------------------------ October 30th 2007 version 3.0g02 --------------------- 1. Fix bug in get_in_split_path() where look for .zip split when attempting to open archives without a .zip extension, even when a single file archive like jar file. fileio.c (Gabriele (balducci@units.it), Ed) 2. Fix bug where temp file got created in current working directory on Unix by giving entire archive path to mkstemp() as template. fileio.c, zip.c (Willus, Ed) 3. Use 64-bit output functions for bits_sent. trees.c (SMS) 4. Add -FF to fixfix -sd messages to make different from identical main messages. zip.c (SMS, Ed) 5. If quiet do not ask for splits and all splits must be in same location. zipfile.c (Ed) 6. Clean up making zip manuals. unix/Makefile (Ed, SMS) 7. Add clean_exe to make. unix/Makefile (SMS) 8. Update to VMS Notes, including adding details on symlinks, -V, and UTC dates times. vms/notes.txt (SMS) 9. Fix bug in wild() when calling wile_recursew() where qw should be pointing inside pw. win32/win32zip.c (Willus, Ed) 10. Fix bug where is_ascii_string() fails when passed a NULL string. This may fix problem where the CentOS mbstowcs() function is returning -1 when trying to convert a file name with a bad character (0xe6), causing local_to_wide_string() and then local_to_utf8_string() to return NULL, so f->uname gets NULL and so is_ascii_string() fails with SIGSEGV. fileio.c (Willus, Ed) ------------------------ October 31st 2007 version 3.0g03 --------------------- 1. Add handling of -b temp directory when opening splits in bfwrite() using mkstemp(). fileio.c (SMS, Ed) ------------------------ November 3rd 2007 version 3.0g04 --------------------- 1. Move show_files to global so can avoid split warning for -sf. zip.c, globals.c, zip.h, zipfile.c (Ed) 2. Account for -b tempath when opening temp file. zip.c, zipnote.c, zipcloak.c (SMS, Ed) ------------------------ November 4th 2007 version 3.0g05 --------------------- 1. Minor fixes to fdopen calls. zipcloak.c, zipnote.c (SMS, Ed) ------------------------ November 4th 2007 version 3.0g06 --------------------- 1. Add negation to -db, -dc, -dd, -dg, -du, -dv display options. zip.c (Ed) 2. Put back UNICODE_SUPPORT no_win32_wide code left out in previous fix. win32/win32zip.c (Willus, Ed) ------------------------ November 21st 2007 version 3.0g07 --------------------- 1. Fix bug preventing newline in some cases in zipmessage(). zip.c (Ed) 2. Update Unicode help. zip.c (Ed) 3. Update -sd messages. zip.c (Ed) 4. Add filetimew() for Unicode case. zip.c (Ed) 5. Add ClearArchiveBitW() for Win32 wide. zip.c, zip.h, win32/win32.c (Ed) 6. Only ask for .zip split if path ends in .znn or .znnn where n 0 to 9. This allows -FF to work on .exe sfx files without adding .zip. zipfile.c (Ed) 7. Fix bug where only backed up 20 bytes to find Z64 EOCD Locator. Now back up 24 bytes to include size of Z64 EOCD Locator signature. This prevented reading and updating archives greater than 4 GB. zipfile.c (Ed) 8. If -FF on Win32 initialize wide strings namew, inamew, and znamew to NULL. zipfile.c (Ed) 9. Add #include to support towupper(). tailor.h (SMS) ------------------------ December 4th 2007 version 3.0g08 --------------------- 1. Update dot_size comment. globals.c (Ed) 2. Update Compression in extended help. zip.c (Ed) 3. Add extended help on self extractor -A and -J. zip.c (Ed) 4. Update VMS SYMLINK version information. zip.c (SMS) 5. Remove not final from Unicode version information as final now. zip.c (Ed) 6. Remove apparently not needed WINDLL variable retcode. zip.c (Ed) 7. Fix -A to calculate sfx offset and adjust offsets as it should. zip.c (Ed) 8. Split -F and -FF used with -A warning to separate warnings. zip.c (Ed) 9. Add adjusting to can't to that to split archive error. zip.c (Ed) 10. Fix bug for -A that tries to open split by asking for disk 0 instead of disk 1. Add adjust_offset and cd_total_size variables. Calculate sfx offset by determining offset of start of central directory. Archives larger than 4 GB are not supported as sfx archives but these don't seem to work anyway. Add adjust_offset to Zip64 EOCDR offset and central directory offsets. zip.c, zipfile.c (Ed) 11. Comment out here debug variable in find_next_signature(). zipfile.c (Ed) 12. Change %2x to %02x as format for parts of a signature in error messages. zipfile.c (SMS) 13. Add warning adjusting split archives not yet supported. zipfile.c (Ed) 14. Add period to central directory comment. zipfile.c (Ed) 15. Update readme for vb Zip64 project. windll/vbz64/readvb64.txt (Ed) 16. Update comments of VB for Zip64 example. Add SplitSize to VB Zip64 example. windll/vbz64/vbzipbas.bas, windll/vbz64/vbzipfrm.frm (Ed) 17. Add SourceForge to comment noting where can get the source code. windll/vbz64/vbzipfrm.frm (Ed) 18. Update WhatsNew. WHATSNEW (Ed) ------------------------ December 12th 2007 version 3.0g09 -------------------- 1. A few minor changes to extended help. zip.c (Ed) 2. Uppercase beginning of most -sd messages. zip.c (Ed) 3. Add spaces between options in some error messages. zip.c (Ed) 4. Update comments in scanzipf_regnew(). zipfile.c (Ed) 5. Update scanzipf_regnew() to figure out sfx offset. (Ed) 6. Uppercase VMS RUNOFF file as apparently needed. VMS_ZIP.RNH (SMS) 7. Add comments to zipmessage(). zip.c (Ed) 8. Update extended help and option descriptions. zip.c (Ed) ------------------------ December 20th 2007 version 3.0g10 -------------------- 1. Fix -F to include -A adjustment check. zipfile.c (Ed) 2. Change -FF message when find EOCDR. zipfile.c (Ed) 3. For -FF, reset first CD entry flag in_central_directory when a local entry is found after CD entries so that another CD entry forces sorting of all local entries to that point. This allows files with multiple archives in them to be processed. zipfile.c (Ed) 4. Add message when a local entry is found after a central directory. zipfile.c (Ed) 5. Remove word offset from disk offset location messages. zipfile.c (Ed) 6. Make Adjust offset message more descriptive. zipfile.c (SMS, Ed) 7. In scanzipf_regnew(), if adjustment to offsets, add it to in_cd_start_offset. zipfile.c (Ed) 8. Allocate cextra only if localz->ext not 0 in zipcopy(). zipfile.c (Ed) ------------------------ December 28th 2007 version 3.0g11 -------------------- 1. Include definitions of zip64_eocdr_start and z64eocdl_offset in ZIP64_SUPPORT ifdef block. Add comments for End Of CD Record (EOCDR). Update comments for adjust offset detection. zipfile.c (Ed) 2. Change ((uzoff_t)1 << 32) to 0xFFFFFFFF. zipfile.c (SMS, Ed) 3. Leave off local header detection as not useful when searching for start of central directory to get adjust offset. Looks like all expected cases are now covered as long as archive is intact. zipfile.c (Ed) 4. Update some warning messages. Simplify adjust offset information message. zipfile.c (Ed) 5. Add braces to unicode_mismatch if block. zipfile.c (Christian) 6. Add (void *) cast in InterlockedExchangePointer() mutex calls to fix compile warnings in MinGW (GCC 3.4.4). win32/nt.c (Christian) 7. Remove unused nonlocalpath variable. win32/win32zip.c (Christian) 8. Update betas readme file. betas_readme.txt (Ed) 9. Partial update to Who list of contributors. proginfo/infozip.who (Ed) 10. Update ReadMe. Create Announcement. README, zip30g.ann (Ed) 11. Update WhatsNew. WHATSNEW (Ed) ------------------------ January 7th 2008 version 3.0g12 -------------------- 1. Convert Scanning files message to use standard zipmessage_nl() so line ends are generated when needed. fileio.c (Ed) 2. Add line ends in DisplayRunningStats() if a display line has been started. zip.c (Ed) 3. For the command line listed at the top of the log file, add double quotes around any arguments that have spaces in them. zip.c (Ed) 4. Instead of stdout use standard mesg output stream for show files. Output new line for show files for display and log file if there was output on the current line. zip.c (Ed) 5. Comment out new line output code after zipup() and replace with call to zipmessage_nl("", 1) to output new line if needed. zip.c (Ed) 6. In GetFileMode() and GetFileModeW() when get attributes fails instead of fprintf(mesg, ...) use zipwarn() so error goes in log file and new lines are displayed when needed. win32/win32.c (Ed) 7. In GetSD(), change cbytes from long to ulg. Check cbytes (the compressed size of the security descriptor) and issue warning if the compressed security descriptor is greater than 0x7FFF (32k) as the entire header this extra field is in needs to fit in the 64k header. Should be a check on the running size of the header so the actual space remaining is tracked. Maybe in Zip 3.1. If cbytes OK cast to ush and store. win32/win32zip.c (Ed) 8. Use zipmessage_nl() for bytes security message so new lines are handled and message goes in log file. win32/win32zip.c (Ed) 9. Add new option -RE to enable [list] (regex) matching in DOS and WIN32 but disable [list] matching otherwise. Default behavior is restored if ALLOW_REGEX is defined. globals.c, util.c, zip.h, zip.c (Ed) ------------------------ January 20th 2008 version 3.0g13 -------------------- 1. Update copyrights to 2008. zip.c, zipcloak.c, zipfile.c, zipnote.c, zipsplit.c, zipup.c, README (Ed) 2. Update Who. proginfo/infozip.who (Ed) ------------------------ January 30th 2008 version 3.0g14 -------------------- 1. Update copyrights. fileio.c, globals.c, revision.h, util.c, zip.h, win32/win32.c, win32/win32zip.c (Ed) 2. Updates. README, proginfo/infozip.who (Ed) 3. Update announcement and WhatsNew. zip30g.ann, WHATSNEW (Ed) 4. Add ALLOW_REGEX to INSTALL define list. INSTALL (Ed) 5. Change -sd message. zip.c (Ed) 6. For bzip2 check for binary and set binary/text flag. Handle -l and -ll line end conversions for bzip2. zipup.c (Ed) ------------------------ February 3rd 2008 version 3.0g -------------------- 1. Change && to || to fix logic bug in show files. zip.c (Johnny) 2. Add CLEAN and CLEAN_ALL VMS targets. vms/descrip_mkdeps.mms (SMS) ----------------------- February 22nd 2008 version 3.0h01 -------------------- 1. Update some echo statements to use CFLAGS_OPT. Add GNUC check. unix/configure (SMS) 2. Only store UID and GID if 16 bit. unix/unix.c (Ed) ----------------------- March 21st 2008 version 3.0h02 -------------------- 1. Change long Unicode escapes from 8 characters to 6 characters based on change in UnZip 6.0. fileio.c (Ed) 2. Put zuebcmp() declaration in #if 0 block as definition already is. This function would be used to allow Unicode escapes on the command line without using the -UN=escape option, but the utility of this is still being determined. zipfile.c (SMS, Ed) 3. Remove declaration for unused bz_deflate_init(). zipup.c (SMS, Ed) 4. Add release announcement file, anticipating the long-awaited release. zip30.ann (Ed) 5. Update WhatsNew. WHATSNEW (Ed) ----------------------- March 24th 2008 version 3.0h03 -------------------- 1. Update Unix configure script to better test for modern HP-UX compiler. unix/configure (SMS) 2. Updated Beta Readme. betas_readme.txt (Ed) 3. Update Install. INSTALL (Ed) 4. Update ReadMe. README (Ed) 5. Small change to main help screen. zip.c (Ed) 6. Small update to top of ToDo list. Actual updating of items still needs to be done. TODO (Ed) ----------------------- April 2nd 2008 version 3.0h04 -------------------- 1. Update copyright. crc32.h (Christian) 2. Remove zip.h include. crc32.h (Christian) 3. Add local prototypes for Unicode functions. Add cast for split size check. Make many Unicode functions local. #if 0 out currently unused utf8_chars(). Fix memory leak in wide_to_local_string() by adding free() for buffer on error return. Fix memory leak in copy_args() on error return by adding free-args(). Add ZCONST to arg in insert_arg(). Shorten some lines to less than 80 characters. Add free() to get_longopt() to fix memory leak. fileio.c (Christian) 4. Create Win32 versions of wide_to_local_string() and local_to_wide_string() so can use Win32 conversion functions. fileio.c, win32/win32.c (Christian) 5. Update comments for get_option(). fileio.c (Ed) 6. Update encryption code readme. README.cr (Ed) 7. Add prototype for recmatchw(). util.c (Christian) 8. Change count_args() from static to local. util.c (Christian) 9. Change ifdefs for includes for prototypes for version_info(), zipstdout(), and check_zipfile() for WINDLL and MACOS and add check_unzip_version(). zip.c (Christian) 10. Change ifndef NO_SYMLINKS to ifdef S_IFLNK for determining compiler information. zip.c (Christian) 11. Change UTF-8 locale from en_GB.UTF-8 to .UTF-8. zip.c (Christian) 12. Change cast of -1 for dot_size from uzoff_t to zoff_t. zip.c (Christian) 13. Change prototype for set_filetype to include parameter char *. Change prototype of has_win32_wide to include parameter void. zip.h (Christian) 14. Add prototypes for find_next_signature(), find_signature(), and is_signature(). Change duplicate prototype scanzipf_regnew() to missing prototype scanzipf_fixnew(). Change comment for Adler-16 checksum to CRC-32 checksum as that is being used at that point in the code. Move multiple uname assignments to common assignment. Add inameLocal for WIN32_OEM and use define for inameLocal if not to save memory allocation when not not using WIN32_OEM. Also change _INTERN_OEM(str1) to INTERN_TO_OEM(src, dst) for OEM conversion. Format comment for vem to fit in 80 character lines. zipfile.c (Christian) 15. Change variable a from buffer to a pointer and add abf as the buffer for zgetline() to handle NULL case. zipnote.c (Christian) 16. Change comments to zipentry comments and zipfile comment in messages. zipnote.c (Ed) 17. Use uidgid_16bit as flag variable instead of uid_size. Modify size check that prevents saving Unix UIDs and GIDs in the old Unix extra field if they are not 16 bits. Change memory allocation based on uidgid_16bit. Delete unused code for memory copy for extra field. unix/unix.c (Christian, Ed) 18. Change compiler flag from -zp8 to -Zp8 for LCC Win32. win32/makefile.lcc (Christian) 19. Add ifndef debug. Add bzip2 support. Add additional compiler flags. win32/makenoas.w32 (Christian) ----------------------- April 10th 2008 version 3.0h05 -------------------- 1. Fix bug found by forum poster where Zip stops recursing down a tree when option -AS is set and a directory without the Windows archive bit is reached. Now Zip continues down the tree to include files with the bit set. win32/win32zip.c (forum poster, Ed) 2. Update comments. win32/osdep.h (Ed) 3. Update VMS notes to better organize and add information about file name case. Additional small updates. vms/notes.txt (SMS) 4. Fix bugs from previous changes to unix. unix/unix.c (SMS, Christian, Ed) 5. Add unix IBM support. unix/unix.c (SMS) 6. Update INSTALL to account for new distribution structure and other changes. INSTALL (SMS, Ed) 7. Update bzip2 install readme. bzip2/install.txt (SMS, Ed) 8. Fix bug noted in forum where -@ and -x generated a "nothing to select from error" by also checking filelist variable populated by -@ for entries. zip.c (forum poster, Ed) ----------------------- April 20th 2008 version 3.0h06 -------------------- 1. Start announcement for Zip 3.0h public beta. zip30h.ann (Ed) 2. Update beta readme. betas_readme.txt (Ed) 3. Update case of README.CR. INSTALL (Ed) 4. Change -W to -ws for option to stop wildcards from scanning directory boundaries in path. This frees up -W for later use, maybe as extendted option introducer. zip.c, man/zip.1 (Ed) 5. Updated date in announcement to May 4th. zip30.ann (Ed) 6. Added announcement for public beta Zip 3.0h. zip30h.ann (Ed) 7. Fix large file support for MinGW by checking for compiler environments before the check for (generic) gcc. zipup.c, win32/osdep.h (Will, Christian) 8. Fix large file support for bzip2. Additionally, the "dot printout" code has also been adapted for LARGE_FILE support. zipup.c (Will, Christian) 9. Add comments to top of configure. unix/configure (Ed) 10. Move comment and comment out value size check for UID/GID extra field. unix/unix.c (Ed) 11. Change case of file ToDo to TODO for consistency and to work with Unix package. TODO (SMS, Ed) ----------------------- April 26th 2008 version 3.0h07 -------------------- 1. For -AS, which for Windows only includes files with the archive bit set, exclude directory entries (by setting -D) as some directories may not have any files with the archive bit set and so the directory would be empty. zip.c (Ed) 2. Fix UID/GID size detection to use byte sizes and remove data fit test. unix/unix.c (Ed) 3. Update announcement. zip30h.ann (Ed) 4. Add new unix extra field with tag 'ux' that stores UIDs/GIDs of 1 to 4 bytes (8 to 32 bits). unix/unix.c (Ed) 5. Update VB readme. windll/vbz64/readVB64.txt (Ed) 6. For Unicode escaped output also show escape for ASCII 7-bit if isprintable() is false. fileio.c (Ed) 7. Use locale "en_US.UTF-8" for Unix. zip.c (Ed) 8. Also show escaped Unicode for new files in found list. zip.c (Ed) 9. Update manual. man/zip.1, zip.txt (Ed) ------------------------ May 4th 2008 version 3.0h08 ----------------------- 1. Handle when a bad Unicode string in archive forces utf8_to_wide_string() to return a NULL string. Give warning if UTF-8 in existing archive is bad. Put WIN32 wide local header initializations in UNICODE_SUPPORT block. fileio.c, zipfile.c (Ed) 2. Leave out Unicode escape code if not Unicode enabled. zip.c (Ed) 3. Enable oem_to_local_string() and local_to_oem_string() for WIN32 even if no Unicode. zip.h, win32/win32.c (Christian, Ed) 4. Update comment about encryption code. zipcloak.c (Ed) 4. Update zipmessage_nl() and zipmessage() from zip.c. zipcloak.c, zipnote.c, zipsplit.c (Ed) 5. Add Mac OS X library check. unix/configure (SMS) 6. Add 16-bit UID/GID check. unix/configure (Christian, Ed) 7. Format echo and comment statements a bit. unix/configure (Ed) 8. Only compile in old 16-bit UID/GID code if new define UIDGID_NOT_16BIT from unix configure script is not defined. unix/unix.c (Christian) 9. A couple changes to updated 16-bit UID/GID code. Add 64-bit UID/GID support to new Unix extra field. unix/unix.c (Ed) 10. Remove redundant "license" from options table. zipcloak.c (Ed) 11. Remove old unix build files. unix/configure-orig, unix/Makefile-orig (Christian) 12. Add -O (--output-file) option to ZipCloak. Fix bug by setting out_path. zipcloak.c (Ed) ------------------------ May 8th 2008 version 3.0h09 ----------------------- 1. Update copyright. Add check for NO_UNICODE_SUPPORT. tailor.h (Ed) 2. Fix bug where Unicode General Purpose Bit Flag 11 should force keeping the old name field but it was being overwritten by the escaped name in the central directory header. Fixed some ZIPERR() calls in putcentral() that referred to putlocal(). zipfile.c (Ed) 3. Add comment about OCRCU8 and OCRCTB. unix/configure (Ed) 4. Change line in instructions to note that manuals should be made after Zip is made. Change OCRTB to OCRCTB. Add $(OCRCTB) to rule for zipcloak$E so crc32_.o is linked in. Add comment for NO_UNICODE_SUPPORT flag. unix/makefile (Ed) 5. Update WhatsNew. Add additional items to the Zip 3.1 list. Add note about Zip 2.4. WHATSNEW (Ed) 6. Update Zip 3.0h announcement. zip30h.ann (Ed) 7. Update manual pages. man/zip.1, man/zipsplit.1, man/zipnote.1, man/zipcloak.1 (Ed) 8. Add noted for UTF-8 locale. zip.c (Ed) 9. Set UTF-8 locale for Unix in utilities if UNICODE_SUPPORT enabled so can display and process paths in archives correctly. zipsplit.c, zipcloak.c, zipnote.c (Ed) ------------------------ May 12th 2008 version 3.0h10 ---------------------- 1. Add use of new Unix UID/GID extra field and of old Unix 16-bit UID/GID extra field when system uses 16-bit UIDs/GIDs to version information. zip.c (SMS, Ed) 2. Add Unicode Path and Unicode Comment extra fields to extra fields list. Update new Unix extra field revision date. proginfo/extrafld.txt (Ed) 3. Add Mac hardware platform to version information. unix/unix.c (SMS) ------------------------ May 19th 2008 version 3.0h11 ---------------------- 1. Initialize f->namew when streaming stdin to fix bug. fileio.c (Ed) 2. Change force_zip64 to start as -1 as unset, then use 1 for forcing use of Zip64 and 0 for disabling use of Zip64. Add negation of -fz to prevent use of Zip64 during streaming from stdin to a non-seekable output where data descriptors will be used, which allows creating archives with the old stream format but will fail if a large file is streamed. Default is still to force Zip64 data descriptors when streaming, which covers all cases but requires a Zip64 compatible unzip. zip.c, globals.c, zipfile.c (Ed) 3. Handle case of bad Unicode in archive. zipfile.c (Ed) ------------------------ May 22nd 2008 version 3.0h12 ---------------------- 1. Fix bug introduced last beta that prevented streaming large files. Use separate error message depending on if -fz- was used. zipfile.c (Ed) 2. Change non existent to nonexistent. unix/configure (SMS) 3. Don't output blank line when zipmessage_nl() gets passed an empty string. This removes blank lines for skipped entries when -FS used. zip.c (Ed) ------------------------ May 27th 2008 version 3.0h13 ---------------------- 1. Change UNICODE_ALLOW_FORCE to UNICODE_SUPPORT, -UN=force to -UN=UTF8, and unicode_force to utf8_force. This option now standard with Unicode support and forces Zip to save UTF-8 paths and comments, when not ASCII, as if UTF-8 were the native character set. globals.c, zip.c, zip.h (Ed) 2. Add note to Todo that it's out of date. TODO (Ed) 3. Update WhatsNew. WHATSNEW (Ed) 4. Update Unicode help in extended help. zip.c (Ed) 5. Update announcements. zip30h.ann, zip30.ann (Ed) 6. Fix bug with -UN=UTF8. zip.c, zipfile.c (Ed) 7. Update Zip manual. man/zip.1, zip.txt (Ed) 8. Attempt an update to zip limits document. proginfo/ziplimit.txt (Ed) 9. Update README regarding forum postings. README (Ed) 10. Remove duplicate initialization lines for found and fnxt. zip.c (SMS) ------------------------ May 28th 2008 version 3.0h14 ---------------------- 1. Remove >= 0 check from wide character check as value is unsigned. fileio.c (SMS) 2. In putlocal(), move nam and use_uname to UNICODE_SUPPORT block. If no UNICODE_SUPPORT use z->nam instead of nam. zipfile.c (SMS, Ed) 3. Update announcement date for beta. zip30h.ann (Ed) ------------------------ May 31st 2008 version 3.0h ------------------------ 1. In putlocal() if using UTF-8 bit then also set UTF-8 bit in z->lflg so is set in local header for streaming. zipfile.c (Ed) 2. Update announcement date for beta. zip30h.ann (Ed) 3. Rename lib and dll projects to zip32z64 and update project files so project name is same as lib and dll libraries. Export make files. windll/visualc/dll/zip32z64.dsp, windll/visualc/dll/zip32z64.dsw, windll/visualc/dll/zip32z64.mak, windll/visualc/libzip32z64.dsp, windll/visualc/libzip32z64.dsw, windll/visualc/libzip32z64.mak (Ed) ------------------------ June 7th 2008 version 3.0i01 ---------------------- 1. Update Mac ReadMe to note Mac OS X uses Unix port. macos/readme.1st (Ed) 2. Change UNIX to Unix in manual. Update dates in manual and add note about Mac OS X. Change switch to switches. zip.1 (SMS, Ed) 3. Add version information under Windows by adding a version resource. win32/vc6/zip.dsp, win32/vc6bz2/zip.dsp, win32/zip.rc (Ed) ------------------------ June 15th 2008 version 3.0i02 ---------------------- 1. Update Install instructions. INSTALL (Ed) 2. Update ReadMe. README (Ed) 3. Update ToDo list. TODO (Ed) 4. Update WhatsNew. WHATSNEW (Ed) 5. Add note to WHERE. WHERE (Ed) 6. Update announcement. zip30.ann (Ed) 7. Review man pages and update Zip man page. Compile text files from man pages. man/zip.1, zip.txt, zipnote.txt, zipsplit.txt, zipcloak.txt (Ed) 8. Update extended help. zip.c (Ed) ------------------------ June 17th 2008 version 3.0i03 ---------------------- 1. Fix bug where UTF-8 flag was not being set when using_utf8 was set as result of UTF-8 being current character set. zipfile.c (Ed) 2. Update man page globbing description. man/zip.1, zip.txt (SMS, Ed) 3. Update web address to bzip2 package for VMS. vms/install_vms.txt (SMS) ------------------------ June 21st 2008 version 3.0i04 ---------------------- 1. Update comments. zbz2err.c (Christian) 2. Put use_uname in UNICODE_SUPPORT block. zipfile.c (Christian) 3. Increase st to 0x1400. msdos/makefile.msc (Christian) 4. Update copyright and put @CodeSize and @DataSize into ifndef blocks for Huge, Large, Compact, Medium, and Small. msdos/match.asm (Christian) 5. Add check to disable symbolic links. msdos/osdep.h (Christian) 6. Put Mac OS X compiler check into if Mac OS X block to avoid problems on some other Unix ports with the check. unix/configure (SMS) 7. Move set_extra_field() to fix compile problem. unix/unix.c (SMS) 8. Update USEBZIP2 to USEBZ2 and -DUSE_BZIP2 to -DBZIP2_SUPPORT. Drop -DMSDOS compile flag. win32/makefile.w32 (Christian) 9. Change BZIP2_SUPPORT to USEBZ2. win32/makenoas.w32 (Christian) ------------------------ June 23rd 2008 version 3.0i05 ---------------------- 1. Update and unify resources. Remove any MFC dependencies from the resource files zip.rc and windll.rc. win32/zip.rc and windll/windll.rc now read the version info from revision.h. windll.rc internal flags modified to "32-bit dll". zip.rc internal flags liberated from "winnt 32-bit" to "generic 32-bit windows". Win32 zip.exe also supported on Win9x (32-bit). Update makefiles for Borland, MSC, GCC(mingw32), Watcom to support inclusion of zip.rc version resources into zip.exe binary. revision.h, msdos/osdep.h, win32/makefile.bor, win32/makefile.gcc, win32/makefile.w10, win32/makefile.w32, win32/makefile.wat, win32/makenoas.w32, win32/zip.rc, windll/windll.rc (Christian) 2. Remove unused files. win32/resource.h, windll/resource.h, windll/windll.aps, windll/zipver.h, windll/visualc/dll/zip32z64.mak, windll/visualc/lib/zip32z64.mak (Christian) 3. Update VMS. vms/descrip_deps.mms (SMS) ------------------------ June 26th 2008 version 3.0i06 ---------------------- 1. Update Install and Readme in preparation for release. Update WhatsNew. INSTALL, README, WHATSNEW (Ed) 2. Update announcement. zip30.ann (Ed) 3. Update original Visual Basic project comments and documentation. windll/vb/readmevb.txt, windll/vb/vbzip.vbp, windll/vb/vbzip.vbw, windll/vb/vbzipbas.bas, windll/vb/vbzipfrm.frm (Ed) 4. Add bzip2 version of djgpp 2.x makefile thanks to Robert. Assumes a standard djgpp installation. msdos/makebz2.dj2 (Robert Riebisch, Ed) ------------------------ June 27th 2008 version 3.0i07 ---------------------- 1. Add DJGPP to bzip2 install instructions. bzip2/install.txt, msdos/makebz2.dj2 (Robert, Ed) ------------------------- July 5th 2008 version 3.0 ------------------------- 1. Add -sd to extended help. zip.c (Will, Ed) 2. Fix memory bug when rebuilding Zip64 central directory extra field which can crash MinGW and other ports when processing large files. zipfile.c (Will) 3. Fix -v bug preventing display of version information when options in environment variables. zip.c (Ed) 4. Update WhatsNew. WHATSNEW (Ed) 5. Update announcement. zip30.ann (Ed) zip30/cmsmvs/0040755000076400000060000000000011033727770011303 5ustar ediskzip30/cmsmvs/cczip.exec0100644000076400000060000000556410550046506013262 0ustar edisk/* CCZIP EXEC Compile zip for VM/CMS */ /* Author: George Petrov, 11 Apr 1995 (VMCOMPIL EXEC) */ /* Modified for IBM C V3R1 by Ian E. Gorman, 2 Nov 1998 Facilities for compiling and testing were provided by OmniMark Technologies Corporation, Ottawa, Canada */ Address Command Signal On Error /* Allow longnames, compile re-entrant code. globals.c and cmsmvs.c require EXTENDED features */ CCopts = 'LONGNAME RENT LANGLVL(EXTENDED) NOEXECOPS' /* ZIP options -- VM_CMS, REENTRANT */ CCopts = CCopts 'DEFINE(VM_CMS,REENTRANT)' /* Link the load module to run in more or less than 16MB memory */ LINKopts = 'AMODE ANY RMODE ANY RLDSAVE' /* resources needed to build */ 'GLOBAL TXTLIB SCEELKED CMSLIB' 'GLOBAL LOADLIB SCEERUN' /* produce the TEXT (object) files */ linklist='' modname='ZIP' Say 'Building' modname 'MODULE...' Call Compile 'ZIP' Call Compile 'CRC32' Call Compile 'CRYPT' Call Compile 'DEFLATE' Call Compile 'FILEIO' Call Compile 'GLOBALS' Call Compile 'TREES' Call Compile 'TTYIO' Call Compile 'UTIL' Call Compile 'ZIPUP' Call Compile 'ZIPFILE' Call Compile 'CMSMVS' Call Compile 'CMS' Say 'Linking...' 'EXEC CMOD' linklist '(MODNAME' modname LINKopts Say modname 'built successfully.' /*---------------------------------------------------------------------*/ /* Build utility programs */ /*---------------------------------------------------------------------*/ CCopts = CCopts 'DEFINE(UTIL)' linklist='' modname='ZIPNOTE' Say Say 'Building' modname 'MODULE...' Call Compile 'ZIPNOTE' Call Compile 'ZIPFILE' Call Compile 'FILEIO' Call Compile 'UTIL' Call Compile 'GLOBALS' Call Compile 'CMSMVS' Say 'Linking...' 'EXEC CMOD' linklist '(MODNAME' modname LINKopts Say modname 'built successfully.' linklist='' modname='ZIPSPLIT' Say Say 'Building' modname 'MODULE...' Call Compile 'ZIPSPLIT' Call Compile 'ZIPFILE' Call Compile 'FILEIO' Call Compile 'UTIL' Call Compile 'GLOBALS' Call Compile 'CMSMVS' Say 'Linking...' 'EXEC CMOD' linklist '(MODNAME' modname LINKopts Say modname 'built successfully.' linklist='' modname='ZIPCLOAK' Say Say 'Building' modname 'MODULE...' Call Compile 'ZIPCLOAK' Call Compile 'ZIPFILE' Call Compile 'FILEIO' Call Compile 'UTIL' Call Compile 'GLOBALS' Call Compile 'CRC32' Call Compile 'CRYPT' Call Compile 'TTYIO' Call Compile 'CMSMVS' Say 'Linking...' 'EXEC CMOD' linklist '(MODNAME' modname LINKopts Say modname 'built successfully.' Say 'Done.' Exit rc error: Say 'Error' rc 'during compilation!' Say 'Error in line' sigl':' Say ' 'Sourceline(sigl) Exit rc Compile: Procedure Expose CCopts LINKopts linklist Parse arg filename filetype filemode . If filetype='' Then filetype='C' linklist = linklist filename Say 'Compiling' filename filetype filemode '...' 'EXEC CC' filename filetype filemode '('CCopts Return rc zip30/cmsmvs/cms.c0100644000076400000060000000166710154331750012230 0ustar edisk/* Copyright (c) 1990-1999 Info-ZIP. All rights reserved. See the accompanying file LICENSE, version 1999-Oct-05 or later (the contents of which are also included in zip.h) for terms of use. If, for some reason, both of these files are missing, the Info-ZIP license also may be found at: ftp://ftp.cdrom.com/pub/infozip/license.html */ /* * VM/CMS specific things. */ #include "zip.h" int procname(n, caseflag) char *n; /* name to process */ int caseflag; /* true to force case-sensitive match */ /* Process a name or sh expression to operate on (or exclude). Return an error code in the ZE_ class. */ { FILE *stream; if (strcmp(n, "-") == 0) /* if compressing stdin */ return newname(n, 0, caseflag); else { if ((stream = fopen(n, "r")) != (FILE *)NULL) { fclose(stream); return newname(n, 0, caseflag); } else return ZE_MISS; } return ZE_OK; } zip30/cmsmvs/cmsmvs.c0100644000076400000060000002557410154331750012761 0ustar edisk/* Copyright (c) 1990-1999 Info-ZIP. All rights reserved. See the accompanying file LICENSE, version 1999-Oct-05 or later (the contents of which are also included in zip.h) for terms of use. If, for some reason, both of these files are missing, the Info-ZIP license also may be found at: ftp://ftp.cdrom.com/pub/infozip/license.html */ /* * routines common to VM/CMS and MVS */ #include "zip.h" #include #include #include #ifndef MVS /* MVS has perfectly good definitions of the following */ int stat(const char *path, struct stat *buf) { if ((buf->fp = fopen(path, "r")) != NULL) { fldata_t fdata; if (fldata( buf->fp, buf->fname, &fdata ) == 0) { buf->st_dev = fdata.__device; buf->st_mode = *(short *)(&fdata); } strcpy( buf->fname, path ); fclose(buf->fp); } return (buf->fp != NULL ? 0 : 1); } #endif /* MVS */ #ifndef UTIL /* the companion #endif is a bit of ways down ... */ #define PAD 0 #define PATH_END '/' /* Library functions not in (most) header files */ #ifdef USE_ZIPMAIN int main OF((void)); #endif int utime OF((char *, ztimbuf *)); extern char *label; local ulg label_time = 0; local ulg label_mode = 0; local time_t label_utim = 0; #ifndef MVS /* MVS has perfectly good definitions of the following */ int fstat(int fd, struct stat *buf) { fldata_t fdata; if ((fd != -1) && (fldata( (FILE *)fd, buf->fname, &fdata ) == 0)) { buf->st_dev = fdata.__device; buf->st_mode = *(short *)(&fdata); buf->fp = (FILE *)fd; return 0; } return -1; } #endif /* MVS */ char *ex2in(x, isdir, pdosflag) char *x; /* external file name */ int isdir; /* input: x is a directory */ int *pdosflag; /* output: force MSDOS file attributes? */ /* Convert the external file name to a zip file name, returning the malloc'ed string or NULL if not enough memory. */ { char *n; /* internal file name (malloc'ed) */ char *t; /* shortened name */ int dosflag; char mem[10] = ""; /* member name */ char ext[10] = ""; /* extension name */ dosflag = dosify; /* default for non-DOS non-OS/2 */ /* Find starting point in name before doing malloc */ for (t = x; *t == '/'; t++) ; /* Make changes, if any, to the copied name (leave original intact) */ if (!pathput) t = last(t, PATH_END); /* Malloc space for internal name and copy it */ if ((n = malloc(strlen(t) + 1)) == NULL) return NULL; strcpy(n, t); #ifdef MVS /* strip quotes from name, non-OE format */ if (*n == '\'' && (t = strrchr(n, '\'')) != n) { if (!*(t+1)) { /* yes, it is a quoted name */ int l = strlen(n) - 2; memmove(n, n+1, l); *(n+l) = '\0'; } } /* Change member names to fn.ext */ if (t = strrchr(n, '(')) { *t = '\0'; strcpy(mem,t+1); /* Save member name */ if (t = strchr(mem, ')')) *t = '\0'; /* Set end of mbr */ /* Save extension */ if (t = strrchr(n, '.')) t++; else t = n; strcpy(ext,t); /* Build name as "member.ext" */ strcpy(t,mem); strcat(t,"."); strcat(t,ext); } /* Change all but the last '.' to '/' */ if (t = strrchr(n, '.')) { while (--t > n) if (*t == '.') *t = '/'; } #else /* On CMS, remove the filemode (all past 2nd '.') */ if (t = strchr(n, '.')) if (t = strchr(t+1, '.')) *t = '\0'; t = n; #endif strcpy(n, t); if (isdir == 42) return n; /* avoid warning on unused variable */ if (dosify) msname(n); /* msname() needs string in native charset */ strtoasc(n, n); /* Returned malloc'ed name */ if (pdosflag) *pdosflag = dosflag; return n; } char *in2ex(n) char *n; /* internal file name */ /* Convert the zip file name to an external file name, returning the malloc'ed string or NULL if not enough memory. */ { char *x; /* external file name */ if ((x = malloc(strlen(n) + 1 + PAD)) == NULL) return NULL; strtoebc(x, n); return x; } void stamp(f, d) char *f; /* name of file to change */ ulg d; /* dos-style time to change it to */ /* Set last updated and accessed time of file f to the DOS time d. */ { ztimbuf u; /* argument for utime() */ /* Convert DOS time to time_t format in u.actime and u.modtime */ u.actime = u.modtime = dos2unixtime(d); utime(f, &u); } ulg filetime(f, a, n, t) char *f; /* name of file to get info on */ ulg *a; /* return value: file attributes */ long *n; /* return value: file size */ iztimes *t; /* return value: access, modific. and creation times */ { FILE *stream; time_t ltime; if (strcmp(f, "-") != 0) { /* if not compressing stdin */ Trace((mesg, "opening file '%s' with '%s'\n", f, FOPR)); if ((stream = fopen(f, FOPR)) == (FILE *)NULL) { return 0; } else { if (n != NULL) { /* With byteseek, this will work */ fseek(stream, 0L, SEEK_END); *n = ftell(stream); Trace((mesg, "file size = %lu\n", *((ulg *)n))); } fclose(stream); } } else { /* Reading from stdin */ if (n != NULL) { *n = -1L; } } /* Return current time for all the times -- for now */ time(<ime); if (t != NULL) t->atime = t->mtime = t->ctime = ltime; /* Set attributes (always a file) */ if (a != NULL) *a = 0; return unix2dostime(<ime); } int set_extra_field(z, z_utim) struct zlist far *z; iztimes *z_utim; /* create extra field and change z->att if desired */ { fldata_t fdata; FILE *stream; char *eb_ptr; #ifdef USE_EF_UT_TIME extent ef_l_len = (EB_HEADSIZE+EB_UT_LEN(1)); #else /* !USE_EF_UT_TIME */ extent ef_l_len = 0; #endif /* ?USE_EF_UT_TIME */ int set_cmsmvs_eb = 0; /*translate_eol = 0;*/ if (aflag == ASCII) { z->att = ASCII; } else { if (bflag) z->att = BINARY; else z->att = __EBCDIC; ef_l_len += sizeof(fdata)+EB_HEADSIZE; set_cmsmvs_eb = 1; } if (ef_l_len > 0) { z->extra = (char *)malloc(ef_l_len); if (z->extra == NULL) { printf("\nFLDATA : Unable to allocate memory !\n"); return ZE_MEM; } z->cext = z->ext = ef_l_len; eb_ptr = z->cextra = z->extra; if (set_cmsmvs_eb) { if (bflag) /*** stream = fopen(z->zname,"rb,type=record"); $RGH$ ***/ stream = fopen(z->name,"rb"); else stream = fopen(z->name,"r"); if (stream == NULL) { printf("\nFLDATA : Could not open file : %s !\n",z->name); printf("Error %d: '%s'\n", errno, strerror(errno)); return ZE_NONE; } fldata(stream,z->name,&fdata); /*put the system ID */ #ifdef VM_CMS *(eb_ptr) = EF_VMCMS & 0xFF; *(eb_ptr+1) = EF_VMCMS >> 8; #else *(eb_ptr) = EF_MVS & 0xFF; *(eb_ptr+1) = EF_MVS >> 8; #endif *(eb_ptr+2) = sizeof(fdata) & 0xFF; *(eb_ptr+3) = sizeof(fdata) >> 8; memcpy(eb_ptr+EB_HEADSIZE,&fdata,sizeof(fdata)); fclose(stream); #ifdef USE_EF_UT_TIME eb_ptr += (sizeof(fdata)+EB_HEADSIZE); #endif /* USE_EF_UT_TIME */ } #ifdef USE_EF_UT_TIME eb_ptr[0] = 0x55; /* ascii[(unsigned)('U')] */ eb_ptr[1] = 0x54; /* ascii[(unsigned)('T')] */ eb_ptr[2] = EB_UT_LEN(1); /* length of data part of e.f. */ eb_ptr[3] = 0; eb_ptr[4] = EB_UT_FL_MTIME; eb_ptr[5] = (char)(z_utim->mtime); eb_ptr[6] = (char)(z_utim->mtime >> 8); eb_ptr[7] = (char)(z_utim->mtime >> 16); eb_ptr[8] = (char)(z_utim->mtime >> 24); #endif /* USE_EF_UT_TIME */ } return ZE_OK; } int deletedir(d) char *d; /* directory to delete */ /* Delete the directory *d if it is empty, do nothing otherwise. Return the result of rmdir(), delete(), or system(). For VMS, d must be in format [x.y]z.dir;1 (not [x.y.z]). */ { return 0; } #ifdef USE_ZIPMAIN /* This function is called as main() to parse arguments */ /* into argc and argv. This is required for stand-alone */ /* execution. This calls the "real" main() when done. */ int main(void) { int argc=0; char *argv[50]; int iArgLen; char argstr[256]; char **pEPLIST, *pCmdStart, *pArgStart, *pArgEnd; /* Get address of extended parameter list from S/370 Register 0 */ pEPLIST = (char **)__xregs(0); /* Null-terminate the argument string */ pCmdStart = *(pEPLIST+0); pArgStart = *(pEPLIST+1); pArgEnd = *(pEPLIST+2); iArgLen = pArgEnd - pCmdStart + 1; /* Make a copy of the command string */ memcpy(argstr, pCmdStart, iArgLen); argstr[iArgLen] = '\0'; /* Null-terminate */ /* Store first token (cmd) */ argv[argc++] = strtok(argstr, " "); /* Store the rest (args) */ while (argv[argc-1]) argv[argc++] = strtok(NULL, " "); argc--; /* Back off last NULL entry */ /* Call "real" main() function */ return zipmain(argc, argv); } #endif /* USE_ZIPMAIN */ #endif /* !UTIL */ /******************************/ /* Function version_local() */ /******************************/ void version_local() { char liblvlmsg [50+1]; char *compiler = "?"; char *platform = "?"; char complevel[64]; /* Map the runtime library level information */ union { unsigned int iVRM; struct { unsigned int pd:4; /* Product designation */ unsigned int vv:4; /* Version */ unsigned int rr:8; /* Release */ unsigned int mm:16; /* Modification level */ } xVRM; } VRM; /* Break down the runtime library level */ VRM.iVRM = __librel(); sprintf(liblvlmsg, "Using runtime library level %s V%dR%dM%d", (VRM.xVRM.pd==1 ? "LE" : "CE"), VRM.xVRM.vv, VRM.xVRM.rr, VRM.xVRM.mm); /* Note: LE = Language Environment, CE = Common Env. (C/370). */ /* This refers ONLY to the current runtimes, not the compiler. */ #ifdef VM_CMS platform = "VM/CMS"; #ifdef __IBMC__ compiler = "IBM C"; #else compiler = "C/370"; #endif #endif #ifdef MVS platform = "MVS"; #ifdef __IBMC__ compiler = "IBM C/C++"; #else compiler = "C/370"; #endif #endif #ifdef __COMPILER_VER__ VRM.iVRM = __COMPILER_VER__; sprintf(complevel," V%dR%dM%d", VRM.xVRM.vv, VRM.xVRM.rr, VRM.xVRM.mm); #else #ifdef __IBMC__ sprintf(complevel," V%dR%d", __IBMC__ / 100, (__IBMC__ % 100)/10); #else complevel[0] = '\0'; #endif #endif printf("Compiled with %s%s for %s%s%s.\n\n", /* Add compiler name and level */ compiler, complevel, /* Add platform */ platform, /* Add timestamp */ #ifdef __DATE__ " on " __DATE__ #ifdef __TIME__ " at " __TIME__ #endif #endif ".\n", liblvlmsg ); } /* end function version_local() */ zip30/cmsmvs/cmsmvs.h0100644000076400000060000000600407443002536012755 0ustar edisk/* Copyright (c) 1990-1999 Info-ZIP. All rights reserved. See the accompanying file LICENSE, version 1999-Oct-05 or later (the contents of which are also included in zip.h) for terms of use. If, for some reason, both of these files are missing, the Info-ZIP license also may be found at: ftp://ftp.cdrom.com/pub/infozip/license.html */ /* Include file for VM/CMS and MVS */ /* This is normally named osdep.h on most systems. Since CMS */ /* generally doesn't support directories, it's been given a unique */ /* name to avoid confusion. */ #ifndef __cmsmvs_h /* prevent multiple inclusions */ #define __cmsmvs_h #ifdef MVS # define _POSIX_SOURCE /* tell MVS we want full definitions */ # include #endif /* MVS */ #include /* the usual non-BSD time functions */ /* cstat.h is not required for MVS and actually gets in the way. Is it * needed for CMS? */ #ifdef MVS # include # include #else /* !MVS */ # include "cstat.h" #endif /* Newer compiler version defines something for us */ #if defined(__VM__) && !defined(VM_CMS) # define VM_CMS #endif #define CMS_MVS #define EBCDIC #ifndef MVS /* MVS has perfectly good definitions for the following */ # define NO_UNISTD_H # define NO_FCNTL_H #endif /*MVS */ /* If we're generating a stand-alone CMS module, patch in */ /* a new main() function before the real main() for arg parsing. */ #ifdef CMS_STAND_ALONE # define USE_ZIPMAIN #endif #ifndef NULL # define NULL 0 #endif #define PASSWD_FROM_STDIN /* Kludge until we know how to open a non-echo tty channel */ /* definition for ZIP */ #define getch() getc(stdin) #define MAXPATHLEN 128 #define NO_RMDIR #define NO_MKTEMP #define USE_CASE_MAP #define isatty(t) 1 #ifndef MVS /* MVS has perfectly good definitions for the following */ # define fileno(x) (char *)(x) # define fdopen fopen # define unlink remove # define link rename # define utime(f,t) #endif /*MVS */ #ifdef ZCRYPT_INTERNAL # define ZCR_SEED2 (unsigned)3141592654L /* use PI as seed pattern */ #endif #ifdef MVS # if defined(__CRC32_C) # pragma csect(STATIC,"crc32_s") # elif defined(__DEFLATE_C) # pragma csect(STATIC,"deflat_s") # elif defined(__ZIPFILE_C) # pragma csect(STATIC,"zipfil_s") # elif defined(__ZIPUP_C) # pragma csect(STATIC,"zipup_s") # endif #endif /* MVS */ /* end defines for ZIP */ #if 0 /*$RGH$*/ /* RECFM=F, LRECL=1 works for sure */ #define FOPR "rb,recfm=fb" #define FOPM "r+" #define FOPW "wb,recfm=fb,lrecl=1" #define FOPWT "w" #endif /* Try allowing ZIP files to be RECFM=V with "byteseek" for CMS, recfm=U for MVS */ #define FOPR "rb,byteseek" #define FOPM "r+,byteseek" #ifdef MVS #define FOPW "wb,recfm=u,byteseek" #else /* !MVS */ #define FOPW "wb,recfm=v,lrecl=32760,byteseek" #endif /* MVS */ #if 0 #define FOPW_TMP "w,byteseek" #else #define FOPW_TMP "w,type=memory(hiperspace)" #endif #define CBSZ 0x40000 #define ZBSZ 0x40000 #endif /* !__cmsmvs_h */ zip30/cmsmvs/cstat.h0100644000076400000060000000371407011110646012561 0ustar edisk/* Copyright (c) 1990-1999 Info-ZIP. All rights reserved. See the accompanying file LICENSE, version 1999-Oct-05 or later (the contents of which are also included in zip.h) for terms of use. If, for some reason, both of these files are missing, the Info-ZIP license also may be found at: ftp://ftp.cdrom.com/pub/infozip/license.html */ /* cstat.h Definitions used for file status functions */ #ifndef __STAT_H #define __STAT_H #include #define S_IFMT 0xF000 /* file type mask */ #define S_IFDIR 0x4000 /* directory */ #define S_IFIFO 0x1000 /* FIFO special */ #define S_IFCHR 0x2000 /* character special */ #define S_IFBLK 0x3000 /* block special */ #define S_IFREG 0x8000 /* or just 0x0000, regular */ #define S_IREAD 0x0100 /* owner may read */ #define S_IWRITE 0x0080 /* owner may write */ #define S_IEXEC 0x0040 /* owner may execute */ struct stat { short st_dev; /* Drive number of disk containing the */ /* file or file handle if the file is */ /* on device */ short st_ino; /* Not meaningfull for VM/CMS */ short st_mode; /* Bit mask giving information about */ /* the file's mode */ short st_nlink; /* Set to the integer constant 1 */ int st_uid; /* Not meaningfull for VM/CMS */ int st_gid; /* Not meaningfull for VM/CMS */ short st_rdev; /* Same as st_dev */ long st_size; /* Size of the file in bytes */ long st_atime; /* Most recent access */ long st_mtime; /* Same as st_atime */ long st_ctime; /* Same as st_atime */ FILE *fp; char fname[FILENAME_MAX]; }; int stat(const char *path, struct stat *sb); int fstat(int fd, struct stat *sb); #endif /* __STAT_H */ zip30/cmsmvs/mc.exec0100644000076400000060000000612606254362764012561 0ustar edisk/* MAKECPIP EXEC Make program to build a C/370 module */ /* Author: George Petrov, 29 Sep 1994 */ arg fn . '(' cparms /* Filter name */ 'pipe (end ?) < 'fn' makefile', /* get all source files from */ '| frlab GLOBALS:'||, '| drop', '| strip', '| var globals' cparms = cparms globals say '' say 'Compile options : 'cparms say '' if pos('REB',cparms) > 0 then do parse var cparms cp1 'REB' . ' ' cp2 /* REBuild options specified ? */ cparms = cp1||cp2 pipe1=, 'pipe (end ?) < 'fn' makefile', /* get all source files from */ '| nfind *'||, /* the makefile and compile */ '| frlab TEXT:'||, /* only the those who are */ '| r: tolab MODULE:'||, /* changed or never compiled */ '| drop', '| o: fanout', '| chop before str /(/', '| statew', '| c: fanout', /* compiled */ '| specs /Compiling / 1 w1-3 n / .../ n', '| cons' end else do pipe1=, 'pipe (end ?) < 'fn' makefile', /* get all source files from */ '| nfind *'||, /* the makefile and compile */ '| frlab TEXT:'||, /* only the those who are */ '| r: tolab MODULE:'||, /* changed or never compiled */ '| drop', '| o: fanout', '| specs w1 1 /C/ nw w3 nw write w1 1 /TEXT A/ nw', '| chop before str /(/', '| statew', '| change (57 66) / /0/', '| sort 1.8 d', /* sort the date and time */ '| uniq 1-17 singles', /* if the first is a source */ '| sort 1.8 d 64.2 d 57.2 d 60.2 d 66.8 d', /* sort the date */ '| uniq 1-8 first', /* if the first is a source */ '| locate 9.8 /C /', /* program then it has to be */ '| c: fanout', /* compiled */ '| specs /Compiling / 1 w1-3 n / .../ n', '| cons' end pipe2= '?', 'r:', '| drop', '| specs w1 1', /* save the module name in var */ '| var module', '?', 'o:', '| specs w1 1', '| join * / /', '| var texts', /* save all the text file names */ '?', /* for later include */ 'c:', '| specs /CC / 1 w1-3 n /(NOTERM 'cparms'/ nw', /* compile! */ '| err: cms | cons', '?', 'err:', '| strip both', '| nfind 0'||, '| var err', '| specs /----> Errors found! RC=/ 1 1-* n', '| cons' /* '| g: gate'*/ pipe1 pipe2 say '' if symbol('err') = 'VAR' & err ^= 0 then do say 'Errors found in source files - link aborted! RC = 'err exit err end say 'Generating module 'module 'pipe cms cmod' fn texts' DMSCSL | > 'fn' LINK A' 'set cmstype ht' 'state 'fn' LINK A' rcc = rc 'set cmstype rt' if rcc = 0 then do say '' say 'ERRORS discovered during linking!' say 'See: 'fn' LINK A for more info' end exit rc error: say 'Error in REXX detected!' Say 'Syntax error on line' Sigl':' Sourceline(Sigl) Say 'Error was:' Errortext(RC) return rc zip30/cmsmvs/mvs.c0100644000076400000060000001427010154331750012245 0ustar edisk/* Copyright (c) 1990-1999 Info-ZIP. All rights reserved. See the accompanying file LICENSE, version 1999-Oct-05 or later (the contents of which are also included in zip.h) for terms of use. If, for some reason, both of these files are missing, the Info-ZIP license also may be found at: ftp://ftp.cdrom.com/pub/infozip/license.html */ /* * MVS specific things */ #include "zip.h" #include "mvs.h" #include static int gen_node( DIR *dirp, RECORD *recptr ) { char *ptr, *name, ttr[TTRLEN]; int skip, count = 2; unsigned int info_byte, alias, ttrn; struct dirent *new; ptr = recptr->rest; while (count < recptr->count) { if (!memcmp( ptr, endmark, NAMELEN )) return 1; name = ptr; /* member name */ ptr += NAMELEN; memcpy( ttr, ptr, TTRLEN ); /* ttr name */ ptr += TTRLEN; info_byte = (unsigned int) (*ptr); /* info byte */ if ( !(info_byte & ALIAS_MASK) ) { /* no alias */ new = malloc( sizeof(struct dirent) ); if (dirp->D_list == NULL) dirp->D_list = dirp->D_curpos = new; else dirp->D_curpos = (dirp->D_curpos->d_next = new); new->d_next = NULL; memcpy( new->d_name, name, NAMELEN ); new->d_name[NAMELEN] = '\0'; if ((name = strchr( new->d_name, ' ' )) != NULL) *name = '\0'; /* skip trailing blanks */ } skip = (info_byte & SKIP_MASK) * 2 + 1; ptr += skip; count += (TTRLEN + NAMELEN + skip); } return 0; } DIR *opendir(const char *dirname) { int bytes, list_end = 0; DIR *dirp; FILE *fp; RECORD rec; fp = fopen( dirname, "rb" ); if (fp != NULL) { dirp = malloc( sizeof(DIR) ); if (dirp != NULL) { dirp->D_list = dirp->D_curpos = NULL; strcpy( dirp->D_path, dirname ); do { bytes = fread( &rec, 1, sizeof(rec), fp ); if (bytes == sizeof(rec)) list_end = gen_node( dirp, &rec ); } while (!feof(fp) && !list_end); fclose( fp ); dirp->D_curpos = dirp->D_list; return dirp; } fclose( fp ); } return NULL; } struct dirent *readdir(DIR *dirp) { struct dirent *cur; cur = dirp->D_curpos; dirp->D_curpos = dirp->D_curpos->d_next; return cur; } void rewinddir(DIR *dirp) { dirp->D_curpos = dirp->D_list; } int closedir(DIR *dirp) { struct dirent *node; while (dirp->D_list != NULL) { node = dirp->D_list; dirp->D_list = dirp->D_list->d_next; free( node ); } free( dirp ); return 0; } local char *readd(d) DIR *d; /* directory stream to read from */ /* Return a pointer to the next name in the directory stream d, or NULL if no more entries or an error occurs. */ { struct dirent *e; e = readdir(d); return e == NULL ? (char *) NULL : e->d_name; } int procname(n, caseflag) char *n; /* name to process */ int caseflag; /* true to force case-sensitive match */ /* Process a name or sh expression to operate on (or exclude). Return an error code in the ZE_ class. */ { char *a; /* path and name for recursion */ DIR *d; /* directory stream from opendir() */ char *e; /* pointer to name from readd() */ int m; /* matched flag */ char *p; /* path for recursion */ struct stat s; /* result of stat() */ struct zlist far *z; /* steps through zfiles list */ int exists; /* 1 if file exists */ if (strcmp(n, "-") == 0) /* if compressing stdin */ return newname(n, 0, caseflag); else if (!(exists = (LSSTAT(n, &s) == 0))) { #ifdef MVS /* special case for MVS. stat does not work on non-HFS files so if * stat fails with ENOENT, try to open the file for reading anyway. * If the user has no OMVS segment, stat gets an initialization error, * even on external files. */ if (errno == ENOENT || errno == EMVSINITIAL) { FILE *f = fopen(n, "r"); if (f) { /* stat got ENOENT but fopen worked, external file */ fclose(f); exists = 1; memset(&s, '\0', sizeof(s)); /* stat data is unreliable for externals */ s.st_mode = S_IFREG; /* fudge it */ } } #endif /* MVS */ } if (! exists) { /* Not a file or directory--search for shell expression in zip file */ p = ex2in(n, 0, (int *)NULL); /* shouldn't affect matching chars */ m = 1; for (z = zfiles; z != NULL; z = z->nxt) { if (MATCH(p, z->iname, caseflag)) { z->mark = pcount ? filter(z->zname, caseflag) : 1; if (verbose) fprintf(mesg, "zip diagnostic: %scluding %s\n", z->mark ? "in" : "ex", z->name); m = 0; } } free((zvoid *)p); return m ? ZE_MISS : ZE_OK; } /* Live name--use if file, recurse if directory */ if (!S_ISDIR(s.st_mode)) { /* add or remove name of file */ if ((m = newname(n, 0, caseflag)) != ZE_OK) return m; } else { /* Add trailing / to the directory name */ if ((p = malloc(strlen(n)+2)) == NULL) return ZE_MEM; if (strcmp(n, ".") == 0) { *p = '\0'; /* avoid "./" prefix and do not create zip entry */ } else { strcpy(p, n); a = p + strlen(p); if (a[-1] != '/') strcpy(a, "/"); if (dirnames && (m = newname(p, 1, caseflag)) != ZE_OK) { free((zvoid *)p); return m; } } /* recurse into directory */ if (recurse && (d = opendir(n)) != NULL) { while ((e = readd(d)) != NULL) { if (strcmp(e, ".") && strcmp(e, "..")) { if ((a = malloc(strlen(p) + strlen(e) + 1)) == NULL) { closedir(d); free((zvoid *)p); return ZE_MEM; } strcat(strcpy(a, p), e); if ((m = procname(a, caseflag)) != ZE_OK) /* recurse on name */ { if (m == ZE_MISS) zipwarn("name not matched: ", a); else ziperr(m, a); } free((zvoid *)a); } } closedir(d); } free((zvoid *)p); } /* (s.st_mode & S_IFDIR) == 0) */ return ZE_OK; } zip30/cmsmvs/mvs.h0100644000076400000060000000204407011110662012241 0ustar edisk/* Copyright (c) 1990-1999 Info-ZIP. All rights reserved. See the accompanying file LICENSE, version 1999-Oct-05 or later (the contents of which are also included in zip.h) for terms of use. If, for some reason, both of these files are missing, the Info-ZIP license also may be found at: ftp://ftp.cdrom.com/pub/infozip/license.html */ /* definitions */ #define NAMELEN 8 struct dirent { struct dirent *d_next; char d_name[NAMELEN+1]; }; typedef struct _DIR { struct dirent *D_list; struct dirent *D_curpos; char D_path[FILENAME_MAX]; } DIR; DIR * opendir(const char *dirname); struct dirent *readdir(DIR *dirp); void rewinddir(DIR *dirp); int closedir(DIR *dirp); char * readd(DIR *dirp); #define ALIAS_MASK (unsigned int) 0x80 #define SKIP_MASK (unsigned int) 0x1F #define TTRLEN 3 #define RECLEN 254 typedef _Packed struct { unsigned short int count; char rest[RECLEN]; } RECORD; char *endmark = "\xFF\xFF\xFF\xFF\xFF\xFF\xFF\xFF"; zip30/cmsmvs/mvs.mki0100644000076400000060000000644610550046604012612 0ustar edisk# Makefile for the MVS (OS/390 Base) version of ZIP 2.3 # Produced for C/C++ V3R2 in OS/390 1.2.0 by Ian E. Gorman, 2 Nov 1998 # Facilities for compiling and testing were made available by # OmniMark Technologies Corporation, Ottawa, Canada # NOTES # # The only tabs in this file are in the first character of each recipe # line, where they are required by make. # # Run this makefile in OpenMVS (OS/390 POSIX) using source files in the # HFS file system. You can write the load module to either HFS file # system or to a PDS in the native MVS file system. The PDS must have # sufficient free space to hold the load module. # # To compile to a member of a PDS: # make # or # make zip.mvs # # To compile a test version into the HFS file system: # make hfs # ZIP options -- MVS, REENTRANT ZIPOPTS=-DMVS -DREENTRANT # directories # generic source code SRC=.. SRC_P=$(SRC)/ # source code for MVS CMSMVS=../cmsmvs CMSMVS_P=$(CMSMVS)/ # include files INCLS=-I$(SRC) -I$(CMSMVS) # object files and load modules BLD_P=../mvs/ # Other options # Suffixes (E and O must be different) E= O=.o # Need EXTENDED features for global.c and vmvms.c, so not using c89 CC=cc CFLAGS=-D_OPEN_SYS $(ZIPOPTS) $(INCLS) LD=cc LDFLAGS= # Files # object (TEXT) files OBJECTS= $(BLD_P)zip$(O) $(BLD_P)trees$(O) \ $(BLD_P)crypt$(O) $(BLD_P)ttyio$(O) $(BLD_P)deflate$(O) \ $(BLD_P)fileio$(O) $(BLD_P)globals$(O) $(BLD_P)util$(O) \ $(BLD_P)crc32$(O) $(BLD_P)zipfile$(O) \ $(BLD_P)zipup$(O) $(BLD_P)cmsmvs$(O) $(BLD_P)mvs$(O) # Header files HFILES= $(SRC_P)api.h $(SRC_P)crc32.h $(SRC_P)crypt.h $(SRC_P)ebcdic.h \ $(SRC_P)revision.h $(SRC_P)tailor.h $(SRC_P)ttyio.h \ $(SRC_P)zip.h $(SRC_P)ziperr.h $(CMSMVS_P)cmsmvs.h \ $(CMSMVS_P)cstat.h $(CMSMVS_P)mvs.h $(CMSMVS_P)zipup.h # Rules all: $(BLD_P)zip.mvs$(E) hfs: $(BLD_P)zip$(E) # link $(BLD_P)zip.mvs$(E): $(OBJECTS) $(LD) -o "//INFOZIP.LOAD(ZIP)" $(LDFLAGS) $^ echo "tso call \"infozip(zip)\" \"'\"\"""$$""@""\"\"'\"" > $% chmod a+x $% $(BLD_P)zip$(E): $(OBJECTS) $(LD) -o $% $(LDFLAGS) $^ # compile $(BLD_P)trees$(O): $(SRC_P)trees.c $(HFILES) $(CC) -c -o $% $(CFLAGS) $(SRC_P)trees.c $(BLD_P)crypt$(O): $(SRC_P)crypt.c $(HFILES) $(CC) -c -o $% $(CFLAGS) $(SRC_P)crypt.c $(BLD_P)ttyio$(O): $(SRC_P)ttyio.c $(HFILES) $(CC) -c -o $% $(CFLAGS) $(SRC_P)ttyio.c $(BLD_P)deflate$(O): $(SRC_P)deflate.c $(HFILES) $(CC) -c -o $% $(CFLAGS) $(SRC_P)deflate.c $(BLD_P)fileio$(O): $(SRC_P)fileio.c $(HFILES) $(CC) -c -o $% $(CFLAGS) $(SRC_P)fileio.c $(BLD_P)globals$(O): $(SRC_P)globals.c $(HFILES) $(CC) -c -o $% $(CFLAGS) $(SRC_P)globals.c $(BLD_P)zip$(O): $(SRC_P)zip.c $(HFILES) $(CC) -c -o $% $(CFLAGS) $(SRC_P)zip.c $(BLD_P)util$(O): $(SRC_P)util.c $(HFILES) $(CC) -c -o $% $(CFLAGS) $(SRC_P)util.c $(BLD_P)crc32$(O): $(SRC_P)crc32.c $(HFILES) $(CC) -c -o $% $(CFLAGS) $(SRC_P)crc32.c $(BLD_P)zipfile$(O): $(SRC_P)zipfile.c $(HFILES) $(CC) -c -o $% $(CFLAGS) $(SRC_P)zipfile.c $(BLD_P)zipup$(O): $(SRC_P)zipup.c $(HFILES) $(CC) -c -o $% $(CFLAGS) $(SRC_P)zipup.c $(BLD_P)cmsmvs$(O): $(CMSMVS_P)cmsmvs.c $(HFILES) $(CC) -c -o $% $(CFLAGS) $(CMSMVS_P)cmsmvs.c $(BLD_P)mvs$(O): $(CMSMVS_P)mvs.c $(HFILES) $(CC) -c -o $% $(CFLAGS) $(CMSMVS_P)mvs.c zip30/cmsmvs/pipzip.rexx0100644000076400000060000000046406254362764013536 0ustar edisk/* PIPZIP REXX Rexx filter to use ZIP */ /* Author : George Petrov, 8 May 1995 */ parse arg opts 'callpipe *:', '| specs w1 1 /./ n w2 n', '| join * / /', '| specs /zip 'opts'/ 1 1-* nw', '| cms', '| *:' exit rc zip30/cmsmvs/README.CMS0100644000076400000060000004063606524205166012611 0ustar ediskUsing ZIP and UNZIP on VM/CMS ============================= Installing executables ---------------------- The following CMS MODULEs are available: ZIP ZIPNOTE ZIPCLOAK ZIPSPLIT UNZIP In addition to these, each MODULE file also has an EXEC with the same name. These EXECs are front-ends to the MODULES that will attempt to set up the required runtime libraries before running the MODULE. All the EXECs are identical. Only their names are different. They are stored as plain text files. The CMS MODULE files have been packed using the COPYFILE command to allow their file format to be properly restored, since variable length binary files will not currently unzip properly (see below for details). The MODULEs are shipped with a filetype or extension of CMO (for CMS MODULE). Their names may vary on the distribution disk to indicate their level, etc. To restore them to executable MODULEs on CMS, do the following: 1. Upload them to CMS with a Fixed record length with LRECL 1024. Example, from a DOS or OS/2 window, type this: SEND unzip.cmo A:unzip module a (RECFM F LRECL 1024 Example, using FTP from CMS, type this: BINARY FIXED 1024 GET unzip.cmo unzip.module.a Note: Replace "unzip.cmo" with the actual name. 2. Use COPYFILE to unpack the file. Example, in CMS type this: COPYFILE UNZIP MODULE A (UNPACK REPLACE OLDDATE 3. Repeat steps 1-2 for each of the programs. 4. Build the ZIPINFO module by typing this: COPYFILE UNZIP MODULE A ZIPINFO MODULE A (OLDDATE 5. Upload the EXECs to CMS as text files (with ASCII-to-EBCDIC translation). Example, from a DOS or OS/2 window, type this: SEND unzip.exc A:unzip exec a (CRLF Example, using FTP from CMS, type this: GET unzip.exc unzip.exec.a 6. Repeat steps 4 for each of the EXECs. Preparing the environment ------------------------- The executables provided were compiled with IBM C 3.1.0 and require the the Language Environment (LE) runtime libraries. To provide access to the runtime libraries: 1. Link to the disk containing the Language Environment files, if necessary. 2. Use the command "GLOBAL LOADLIB SCEERUN" These commands can be placed in your PROFILE EXEC. Note: EXECs have been provided called ZIP, UNZIP, etc. that issue the GLOBAL LOADLIB statement. This was done to alleviate frustration of users that don't have the GLOBAL LOADLIB statement in their PROFILE EXEC. These EXECs may require changing for your system. Unfortunately, there is no way, using IBM C, to produce a MODULE that doesn't require a runtime library. Testing ------- To test the MODULEs, just type ZIP or UNZIP. They should show help information on using the commands. If you see something like this: DMSLIO201W The following names are undefined: CEEEV003 DMSABE155T User abend 4093 called from 00DCD298 reason code 000003EB Then you don't have access to the proper runtime libraries, as described above. Here is additional information on the ZIP and UNZIP programs that may assist support personnel: - Compiled with IBM C V3R1M0 on VM/ESA 2.2.0 with CMS level 13 Service Level 702. - Require the SCEERUN LOADLIB runtime library. This is part of the Language Environment (LE). - Linked with options RMODE ANY AMODE ANY RLDSAVE. If you continue to have trouble, report the problem to Zip-Bugs (see the bottom of this document). Compiling the source on VM/CMS ------------------------------ The source has been successfully compiled previously using C/370 2.1 and 2.2. The source has been recently compiled using IBM C 3.1.0 on VM/ESA 2.2.0 with CMS level 13. I don't have access to an MVS system so the code hasn't been tested there in a while. 1. Unzip the source files required for CMS. The root-level files inside the ZIP file and the files in the CMSMVS subdirectory are needed. Example (use both commands): unzip -aj zip23.zip -x */* -dc unzip -aj zip23.zip cmsmvs/* -dc This example unzips the files to the C-disk, while translating character data and ignoring paths. If you don't already have a working UNZIP MODULE on CMS you will have to unzip the files on another system and transport them to CMS. All the required files are plain text so they can be transferred with ASCII-to-EBCDIC translations. 2. Repeat step 1 with the zip file containing the UNZIP code. Unzip the files to a different disk than the disk used for the ZIP code. 3. To compile the ZIP code, run the supplied CCZIP EXEC. To compile the UNZIP code, run the supplied CCUNZIP EXEC. NOTE: Some of the ZIP and UNZIP source files have the same name. It is recommended that you keep the source from each on separate disks and move the disk you are building from ahead of the other in the search order. For example, you may have a 192 disk with the ZIP source code and a 193 disk with the UNZIP source code. To compile ZIP, access the 192 disk as B, then run CCZIP. This will create the following modules: ZIP, ZIPNOTE, ZIPSPLIT, ZIPCLOAK. To compile UNZIP, access 193 as B, then run CCUNZIP. This will create the following modules: UNZIP, ZIPINFO (a copy of UNZIP). ========================================================================= Using ZIP/UNZIP --------------- Documentation for the commands is in MANUAL NONAME (for ZIP) and in UNZIP DOC UNZIP. INFOZIP DOC describes the use of the -Z option of UNZIP. The rest of this section explains special notes concerning the VM/CMS version of ZIP and UNZIP. Filenames and directories ------------------------- 1. Specifying filenames a. When specifying CMS files, use filename.filetype.filemode format (separate the three parts of the name with a period and use no spaces). Example: profile.exec.a Unfortunately, this prevents you from using ZIP from FILELIST. To unzip a zip file, however, you can type something like this next to it in FILELIST: unzip /n -d c This will unzip the contents of the current file to a C-disk. b. It is possible to use DD names with ZIP and UNZIP on CMS, though it can be cumbersome. Example: filedef out disk myzip zip a zip dd:out file1.txt file2.txt While you can also use a DD name for the input files, ZIP currently does not correctly resolve the filename and will store something like "dd:in" inside the ZIP file. A file stored in this manor cannot easily be unzipped, as "dd:in" is an invalid filename. c. In places where a directory name would be used on a PC, such as for the ZIP -b (work path) option or the UNZIP -d (destination path) options, use a filemode letter for CMS. For example, to unzip files onto a C-disk, you might type something like this: unzip myzip.zip -d c Currently, ZIP uses the A-disk for work files. When zipping large files, you may want to specify a larger disk for work files. This example will use a C-disk for work files. zip -b C myzip.zip.c test.dat.a 2. Filename conversions a. Filemode letters are never stored into the zip file or take from a zip file. Only the filename and filetype are used. ZIP removes the filemode when storing the filename into the zip file. UNZIP assumes "A" for the filemode unless the -d option is used. b. When unzipping, any path names are removed from the fileid and the last two period-separated words are used as the filename and filetype. These are truncated to a maximum of eight characters, if necessary. If the filetype (extension) is missing, then UNZIP uses "NONAME" for the filetype. Any '(' or ')' characters are removed from the fileid. c. All files are created in upper-case. Files in mixed-case cannot currently be stored into a ZIP file. d. Shared File System (SFS) directories are not supported. Files are always accessed by fn.ft.fm. To use an SFS disk, Assign it a filemode, then it can be used. 3. Wildcards in file names a. Wildcards are not supported in the zip filename. The full filename of the zip file must be given (but the .zip is not necessary). So, you can't do this: unzip -t *.zip b. Wildcards CAN be used with UNZIP to select (or exclude) files inside a zip file. Examples: unzip myzip *.c - Unzip all .c files. unzip myzip *.c -x z*.c - Unzip all .c files but those starting with Z. c. Wildcards cannot currently be used to select files with ZIP. So, you can't do this: zip -a myzip *.exec I expect to fix this for CMS in the future. 4. File timestamps a. The dates and times of files being zipped or unzipped are not currently read or set. When a file is zipped, the timestamp inside the zip file will always be the current system date and time. Likewise, when unzipping, the date and time of files being unzipped will always be the current system date/time. b. Existing files are assumed to be newer than files inside a zip file when using the -f freshen option of UNZIP. This will prevent overwriting files that may be newer than the files inside the zip file, but also effectively prevents the -f option from working. 5. ASCII, EBCDIC, and binary data Background ---------- Most systems create data files as just a stream of bytes. Record breaks happen when certain characters (new line and/or carriage return characters) are encountered in the data. How to interpret the data in a file is up to the user. The system must be told to either notice new line characters in the data or to assume that the data in the file is binary data and should be read or written as-is. CMS and MVS are record-based systems. All files are composed of data records. These can be stored in fixed-length files or in variable length files. With fixed-length files, each record is the same length. The record breaks are implied by the LRECL (logical record length) attribute associated with the file. With variable-length files, each record contains the length of that record. The separation of records are not part of the data, but part of the file structure. This means you can store any type of data in either type of file structure without having to worry about the data being interpreted as a record break. Fixed-length files may have padding at the end of the file to make up a full record. Variable-length files have no padding, but require extra record length data be stored with the file data. Storing fixed-length files into a zip file is simple, because all the data can just be dumped into the zip file and the record format (RECFM) and logical record length (LRECL) can be stored in the extra data area of the zip file so they can be restored when UNZIP is used. Storing variable-length data is harder. There is no place to put the record length data needed for each record of the file. This data could be written to the zip file as the first two bytes of each record and interpreted that way by UNZIP. That would make the data unusable on systems other than CMS and MVS, though. Currently, there isn't a solution to this problem. Each record is written to the zip file and the record length information is discarded. Binary data stored in variable-length files can't be put into a zip file then later unzipped back into the proper records. This is fine for binary data that will be read as a stream of bytes but not OK where the records matter, such as with CMS MODULEs. If the data is text (character data), there is a solution. This data can be converted into ASCII when it's stored into a zip file. The end of each record is now marked in the file by new line characters. Another advantage of this method is that the data is now accessible to non-EBCDIC systems. When the data is unzipped on CMS or MVS, it is converted back into EBCDIC and the records are recreated into a variable-length file. So, here's what we have... a. To store readable text data into a zip file that can be used on other platforms, use the -a option with ZIP to convert the data to ASCII. These files will unzip into variable-length files on CMS and should not contain binary data or corruption may occur. b. Files that were zipped on an ASCII-based system will be automatically translated to EBCDIC when unzipped. To prevent this (to unzip binary data on CMS that was sent from an ASCII-based system), use the -B option with UNZIP to force Binary mode. To zip binary files on CMS, use the -B option with ZIP to force Binary mode. This will prevent any data conversions from taking place. c. When using the ZIP program without specifying the "-a" or "-B" option, ZIP defaults to "native" (EBCDIC) mode and tries to preserve the file information (RECFM, LRECL, and BLKSIZE). So when you unzip a file zipped with ZIP under CMS or MVS, UNZIP restores the file info. The output will be fixed-length if the original was fixed and variable-length if the original was variable. If UNZIP gives a "write error (disk full?)" message, you may be trying to unzip a binary file that was zipped as a text file (without using the -B option) Summary ------- Here's how to ZIP the different types of files. RECFM F text Use the -a option with ZIP to convert to ASCII for use with other platforms or no options for use on EBCDIC systems only. RECFM V text Use the -a option with ZIP to convert to ASCII for use with other platforms or no options for use on EBCDIC systems only. RECFM F binary Use the -B option with ZIP (upper-case "B"). RECFM V binary Use the -B option with ZIP. Can be zipped OK but the record structure is destroyed when unzipped. This is OK for data files read as binary streams but not OK for files such as CMS MODULEs. 6. Character Sets If you are used to running UNZIP on systems like UNIX, DOS, OS/2 or Windows, you will may have some problems with differences in the character set. There are a number of different EBCDIC code pages, like there are a number of different ASCII code pages. For example, there is a US EBCDIC, a German EBCDIC, and a Swedish EBCDIC. As long as you are working with other people who use the same EBCDIC code page, you will have no trouble. If you work with people who use ASCII, or who use a different EBCDIC code page, you may need to do some translation. UNZIP translates ASCII text files to and from Open Systems EBCDIC (IBM-1047), which may not be the EBCDIC that you are using. For example, US EBCDIC (IBM-037) uses different character codes for square brackets. In such cases, you can use the ICONV utility (supplied with IBM C) to translate between your EBCDIC character set and IBM-1047. If your installation does not use IBM-1047 EBCDIC, messages from UNZIP may look a little odd. For example, in a US EBCDIC installation, an opening square bracket will become an i-acute and a closing square bracket will become a u-grave. The supplied ZIP and UNZIP EXECs attempt to correct this by setting CMS INPUT and OUTPUT translations to adjust the display of left and right brackets. You may need to change this if brackets don't display correctly on your system. 7. You can unzip using VM/CMS PIPELINES so unzip can be used as a pipeline filter. Example: 'PIPE COMMAND UNZIP -p test.zip george.test | Count Lines | Cons' Please report all bugs and problems to: Zip-Bugs@lists.wku.edu ----------------------------------------------------------------------- Original CMS/MVS port by George Petrov. e-mail: c888090@nlevdpsb.snads.philips.nl tel: +31-40-781155 Philips C&P Eindhoven The Netherlands ----------------------------------------------------------------------- Additional fixes and README re-write (4/98) by Greg Hartwig. e-mail: ghartwig@ix.netcom.com ghartwig@vnet.ibm.com ----------------------------------------------------------------------- Additional notes from Ian E. Gorman. e-mail: ian@iosphere.net zip30/cmsmvs/README.MVS0100644000076400000060000000542506421312420012615 0ustar ediskThank you for trying this first port of ZIP for VM/CMS and MVS! Using under MVS: --------------------------- 1. To use the Info-ZIP's ZIP under MVS you need: - C/370 ver 2.1 compiler or another compatible compiler supporting long names for function/variable names. 2. To compile the program under MVS do : - unzip all the files from zip22.zip file. They are stored as ASCII format so you have to unzip them first on PC or other system that already have UNZIP, and then upload them to the mainframe with ASCII to EBCDIC conversion. - Copy all the .C files in the PDS called youruserid.ZIP.C - Copy all the .H files in the PDS called youruserid.ZIP.H - adjust the job ZIPMVSC.JOB to work on your size. Change my userid - C888090 to yours - execute the job ZIPMVSC to compile and link all the sources. - maybe you have to preallocate PDS datasets named: youruserid.ZIP.OBJ and youruserid.ZIP.LOAD - execute ZIPVMC to compile and link all the sources. - if everything is ok you will get an ZIP MODULE - the warnings about the duplicated ASCII and EBCDIC symbols are OK :-) 3. Using ZIP - Just read MANUAL - A few exceptions concerning MVS 3.1. if you want to make a portable zip file that is to be unzipped on ASCII based systems use the -a option 3.2. If you want to zip the input files as binary ebcdic files use the -B (capital letter) option 3.3. The date/end the time of the input files is set in the zip's dir to the current system date/time 3.4. Without specifying the "-a" or "-B" option, the ZIP program defaults to "native" (EBCDIC) mode and tries to preserve the file information (LRECL,BLKSIZE..) So when you UNZIP a file zipped with ZIP under VM/MVS it restores the file info. There currently some problems with file with RECFM=V* I don't save the length of each record yet :-) 3.5. No wildcards are supported as input file names: So you CAN'T use things like: zip myzip *.c 3.6. You can use DD names for zipfilename for example: under tso/rexx: "alloc fi(input) da('myzip.zip')" "zip dd:input file1.txt file2.txt ..." under Batch: //MYZIP JOB (account) //STEP1 EXEC PGM=ZIP,PARM='dd:input file1.txt file2.txt' //STEPLIB DD DSN=userid.UNZIP.LOAD,DISP=SHR //INPUT DD DSN=userid.MYZIP.ZIP,DISP=NEW, // SPACE=(15000,(15000,10000),RLSE), // DCB=(LRECL=80,RECFM=F) //SYSPRINT DD SYSOUT=* Please report all bugs and problems to : zip-bugs@lists.wku.edu That's all for now. Have fun! George Petrov zip30/cmsmvs/README.MVS.LE0100644000076400000060000003013506615016016013117 0ustar ediskNotes on Zip under MVS Language Environment (LE). First see README.MVS. This note describes just one beta test on OS/390 V2R5 using IBM's C compiler (5647A01), V2R4. The major difference is the use of LE on the beta site, together with some MVS native mode fixes. Changes have not been tested on CMS. Some of the notes are to clarify things that were not clear from the MANUAL or README.MVS. 1. By default, IBM C generates the same csect name for each input source. The prelink stage does not rename them and the linkage editor throws away all but the first occurrence of each duplicate. Oops, my code just disappeared :(. To get around this "feature", compile with the CSECT option to force sensible names on the code and data sections of each csect. The name of the static data csect defaults to the source name in lower case, the code csect defaults to the source name in upper case. These csect names still have to be unique, they cannot be the same as function names. Of course, several csects have a function which is the same name as the source in lower case, not exactly an unusual occurrence. Therefore to make the csect name unique, some of the sources have #ifdef MVS # pragma csect(STATIC,xxxx_s) #endif Where xxxx is an abbreviation of the source name. There has to be a better way! 2. The prelink step always gets cond code 4. It complains about unresolved references, ignore it unless the linker also complains. Prelink also complains about duplicate @@PPA2 sections and so does the linker, but it seems to do no harm. Compile and link steps should get 0, just prelink gets 4. See JCL at the bottom. 3. Under MVS native mode (not Open Edition), tmpnam() returns a quoted name of 5 qualifiers. The first is a HLQ chosen according to the MVS LE algorithm (see below), the other qualifiers are time stamps. If running on MVS and tmpnam() returns a quoted name with at leat one '.', it is only safe to let the user change the high level qualifier. Therefore -b insists on a single qualifier without '.' in the MVS native environment. 4. In Open Edition (OE) mode, the manual says that tmpnam() returns a fully qualified name in directory TMPDIR or /tmp if TMPDIR is not set. There is no point in zip trying to override that name so -b is ignored in MVS OE mode (untested). The user should specify environment variable TMPDIR instead. 5. The MVS LE algorithm for choosing the high level qualifier for native filenames is interesting, as in "May you live in interesting times". The HLQ varies according to the environment the program is running in, sometimes it is userid, sometimes it is TSO prefix. See OS/390 C/C++ Programming Guide, Using a Data Set Name, somewhere around section 2.9. If in doubt, use fully qualified and quoted names. Instead of archive.zip, use 'prefix.archive.zip'. For input files, instead of filename, use 'prefix.filename'. For PARM= in JCL, double up the quotes. You even have to quote filenames in stdin. 6. If your PARM includes any '/', make sure the PARM starts with '/'. LE assumes anything before the first '/' is LE run time parameters. It does no harm to always code a leading '/' for LE parms. 7. JCL limits a PARM= to 100 characters total with approx. 65 on a single line. Alas the syntax for continuing PARM= always embeds an extra ',' somewhere in the parameters that the program finally gets. No workaround, limit your PARM to a single line. With the extra quotes around filenames, that does not leave much room. In most cases, you will have to use '-@' to read the list of filenames from SYSIN (stdin), it will not fit on a single PARM line. 8. Filenames can be dataset names or you can refer to a ddname with 'DD:name', case insensitive for external files, case sensitive for OE files. You can even specify 'dd:name(mem)'. No wildcards, to zip a complete pds you have to specify each member individually. Directory recursion in OE does not appear to work at the moment. 9. Zip attempts to map MVS filenames to Unix style names. It did not work correctly for quoted names, fixed. Although you can pick up an external (non-OE) file with a name using any case, be aware that the mapping to a Unix style name faithfully follows the case you supply. 10. The archive file was being created with recfm=V and lrecl=32760. 32760 is not valid for recfm=V under MVS, I originally changed it to lrecl=32756. Then zip broke trying to fseek() over a record boundary, I do not know whether this was a zip or LE bug. Trial and error showed that recfm=U with byteseek seems to work on MVS. No BDW or RDW, just a byte stream. The blocksize is always 6144. NOTE: This is an incompatible change from the previous beta, archive files used to be recfm=V. That should not matter because we just transfer the data, ignoring BDW and RDW anyway. 11. Zip used to complain about preallocated but empty archives, wrong length records, no signature etc. The usual IBM/360 problem of no end of file marker in a new, unopened dataset. Fixed, see routine readzipfile in zipfile.c for the gory details. PARM= works fine. 12. Several source files have records that are more than 80 bytes long. It works if you transfer to mainframe datasets with a larger lrecl, I used recfm=fb,lrecl=120 for the .C and .H files. To compile with anything longer than 72 bytes, you need MVS C options NOMARGINS and NOSEQUENCE (NOMAR,NOSEQ). 13. cmsmvs was still using zname instead of name for open. Fixed. 14. zip has to jump through a lot of hoops to see if an existing zipfile actually contains data. A side effect of this is that creating a zipfile with the RLSE parameter is a waste of time. Keith Owens . Not a maintainer, just a beta tester. Mon Sep 14 19:31:30 EST 1998 Sample JCL to compile Zip under MVS LE. You might need a large region, I used REGION=128M on the job card. Also watch the output lines, 75,000 with OPT(2), 100,000+ with OPT(2) replaced with DEF(DEBUG). You need to allocate prefix.ZIP.C.OBJ (recfm=FB, lrecl=80) and prefix.ZIP.LOAD (recfm=U, blksize is site defined). //CBC JCLLIB ORDER=CBC.SCBCPRC //ZIP EXEC EDCC,COND=(0,NE),CREGSIZ='4M', // INFILE='prefix.ZIP.C(ZIP)', // OUTFILE='prefix.ZIP.C.OBJ(ZIP),DISP=SHR', // CPARM='LONG,NOTERM,LIST,XREF,SOURCE', // CPARM2='OPT(2),DEF(MVS),NOMAR,NOSEQ,CSECT' //COMPILE.USERLIB DD DSN=prefix.ZIP.H,DISP=SHR //CRYPT EXEC EDCC,COND=(0,NE),CREGSIZ='4M', // INFILE='prefix.ZIP.C(CRYPT)', // OUTFILE='prefix.ZIP.C.OBJ(CRYPT),DISP=SHR', // CPARM='LONG,NOTERM,LIST,XREF,SOURCE', // CPARM2='OPT(2),DEF(MVS),NOMAR,NOSEQ,CSECT' //COMPILE.USERLIB DD DSN=prefix.ZIP.H,DISP=SHR //TTYIO EXEC EDCC,COND=(0,NE),CREGSIZ='4M', // INFILE='prefix.ZIP.C(TTYIO)', // OUTFILE='prefix.ZIP.C.OBJ(TTYIO),DISP=SHR', // CPARM='LONG,NOTERM,LIST,XREF,SOURCE', // CPARM2='OPT(2),DEF(MVS),NOMAR,NOSEQ,CSECT' //COMPILE.USERLIB DD DSN=prefix.ZIP.H,DISP=SHR //TREES EXEC EDCC,COND=(0,NE),CREGSIZ='4M', // INFILE='prefix.ZIP.C(TREES)', // OUTFILE='prefix.ZIP.C.OBJ(TREES),DISP=SHR', // CPARM='LONG,NOTERM,LIST,XREF,SOURCE', // CPARM2='OPT(2),DEF(MVS),NOMAR,NOSEQ,CSECT' //COMPILE.USERLIB DD DSN=prefix.ZIP.H,DISP=SHR //DEFLATE EXEC EDCC,COND=(0,NE),CREGSIZ='4M', // INFILE='prefix.ZIP.C(DEFLATE)', // OUTFILE='prefix.ZIP.C.OBJ(DEFLATE),DISP=SHR', // CPARM='LONG,NOTERM,LIST,XREF,SOURCE', // CPARM2='OPT(2),DEF(MVS),NOMAR,NOSEQ,CSECT' //COMPILE.USERLIB DD DSN=prefix.ZIP.H,DISP=SHR //FILEIO EXEC EDCC,COND=(0,NE),CREGSIZ='4M', // INFILE='prefix.ZIP.C(FILEIO)', // OUTFILE='prefix.ZIP.C.OBJ(FILEIO),DISP=SHR', // CPARM='LONG,NOTERM,LIST,XREF,SOURCE', // CPARM2='OPT(2),DEF(MVS),NOMAR,NOSEQ,CSECT' //COMPILE.USERLIB DD DSN=prefix.ZIP.H,DISP=SHR //GLOBALS EXEC EDCC,COND=(0,NE),CREGSIZ='4M', // INFILE='prefix.ZIP.C(GLOBALS)', // OUTFILE='prefix.ZIP.C.OBJ(GLOBALS),DISP=SHR', // CPARM='LONG,NOTERM,LIST,XREF,SOURCE', // CPARM2='OPT(2),DEF(MVS),NOMAR,NOSEQ,CSECT' //COMPILE.USERLIB DD DSN=prefix.ZIP.H,DISP=SHR //UTIL EXEC EDCC,COND=(0,NE),CREGSIZ='4M', // INFILE='prefix.ZIP.C(UTIL)', // OUTFILE='prefix.ZIP.C.OBJ(UTIL),DISP=SHR', // CPARM='LONG,NOTERM,LIST,XREF,SOURCE', // CPARM2='OPT(2),DEF(MVS),NOMAR,NOSEQ,CSECT' //COMPILE.USERLIB DD DSN=prefix.ZIP.H,DISP=SHR //CRC32 EXEC EDCC,COND=(0,NE),CREGSIZ='4M', // INFILE='prefix.ZIP.C(CRC32)', // OUTFILE='prefix.ZIP.C.OBJ(CRC32),DISP=SHR', // CPARM='LONG,NOTERM,LIST,XREF,SOURCE', // CPARM2='OPT(2),DEF(MVS),NOMAR,NOSEQ,CSECT' //COMPILE.USERLIB DD DSN=prefix.ZIP.H,DISP=SHR //CRCTAB EXEC EDCC,COND=(0,NE),CREGSIZ='4M', // INFILE='prefix.ZIP.C(CRCTAB)', // OUTFILE='prefix.ZIP.C.OBJ(CRCTAB),DISP=SHR', // CPARM='LONG,NOTERM,LIST,XREF,SOURCE', // CPARM2='OPT(2),DEF(MVS),NOMAR,NOSEQ,CSECT' //COMPILE.USERLIB DD DSN=prefix.ZIP.H,DISP=SHR //ZIPFILE EXEC EDCC,COND=(0,NE),CREGSIZ='4M', // INFILE='prefix.ZIP.C(ZIPFILE)', // OUTFILE='prefix.ZIP.C.OBJ(ZIPFILE),DISP=SHR', // CPARM='LONG,NOTERM,LIST,XREF,SOURCE', // CPARM2='OPT(2),DEF(MVS),NOMAR,NOSEQ,CSECT' //COMPILE.USERLIB DD DSN=prefix.ZIP.H,DISP=SHR //ZIPUP EXEC EDCC,COND=(0,NE),CREGSIZ='4M', // INFILE='prefix.ZIP.C(ZIPUP)', // OUTFILE='prefix.ZIP.C.OBJ(ZIPUP),DISP=SHR', // CPARM='LONG,NOTERM,LIST,XREF,SOURCE', // CPARM2='OPT(2),DEF(MVS),NOMAR,NOSEQ,CSECT' //COMPILE.USERLIB DD DSN=prefix.ZIP.H,DISP=SHR //CMSMVS EXEC EDCC,COND=(0,NE),CREGSIZ='4M', // INFILE='prefix.ZIP.C(CMSMVS)', // OUTFILE='prefix.ZIP.C.OBJ(CMSMVS),DISP=SHR', // CPARM='LONG,NOTERM,LIST,XREF,SOURCE', // CPARM2='OPT(2),DEF(MVS),NOMAR,NOSEQ,CSECT' //COMPILE.USERLIB DD DSN=prefix.ZIP.H,DISP=SHR //MVS EXEC EDCC,COND=(0,NE),CREGSIZ='4M', // INFILE='prefix.ZIP.C(MVS)', // OUTFILE='prefix.ZIP.C.OBJ(MVS),DISP=SHR', // CPARM='LONG,NOTERM,LIST,XREF,SOURCE', // CPARM2='OPT(2),DEF(MVS),NOMAR,NOSEQ,CSECT' //COMPILE.USERLIB DD DSN=prefix.ZIP.H,DISP=SHR //PLINK EXEC PROC=EDCPL, // OUTFILE='prefix.ZIP.LOAD(ZIP),DISP=SHR', // PREGSIZ=6M, // PPARM='NONCAL,MAP,MEMORY', // LPARM='LIST,MAP,XREF' //PLKED.SYSIN DD DISP=SHR,DSN=prefix.ZIP.C.OBJ(ZIP) // DD DISP=SHR,DSN=prefix.ZIP.C.OBJ(CRYPT) // DD DISP=SHR,DSN=prefix.ZIP.C.OBJ(TREES) // DD DISP=SHR,DSN=prefix.ZIP.C.OBJ(DEFLATE) // DD DISP=SHR,DSN=prefix.ZIP.C.OBJ(FILEIO) // DD DISP=SHR,DSN=prefix.ZIP.C.OBJ(GLOBALS) // DD DISP=SHR,DSN=prefix.ZIP.C.OBJ(UTIL) // DD DISP=SHR,DSN=prefix.ZIP.C.OBJ(CRC32) // DD DISP=SHR,DSN=prefix.ZIP.C.OBJ(CRCTAB) // DD DISP=SHR,DSN=prefix.ZIP.C.OBJ(ZIPFILE) // DD DISP=SHR,DSN=prefix.ZIP.C.OBJ(ZIPUP) // DD DISP=SHR,DSN=prefix.ZIP.C.OBJ(MVS) // DD DISP=SHR,DSN=prefix.ZIP.C.OBJ(CMSMVS) //LKED.SYSLIB DD DISP=SHR,DSN=CEE.SCEELKED //SYSUT1 DD UNIT=SYSDA,SPACE=(CYL,(2,2)) // Sample JCL to zip the mainframe .C and .H files as ASCII (-a). Delete any existing archive first, point the temporary file at a particular prefix (-b), use 'prefix.ARCHIVE.ZIP' for the archive file, read the list of files to zip from stdin (SYSIN). //DELETE EXEC PGM=IDCAMS //SYSPRINT DD SYSOUT=* //SYSIN DD * DELETE prefix.ARCHIVE.ZIP SET MAXCC = 0 //ZIP EXEC PGM=ZIP, // PARM='/-a -v -b temppref ''prefix.ARCHIVE.ZIP'' -@' //STEPLIB DD DSN=prefix.ZIP.LOAD,DISP=SHR //SYSPRINT DD SYSOUT=* //SYSOUT DD SYSOUT=* //CEEDUMP DD SYSOUT=* //ZIPC DD DISP=SHR,DSN=prefix.ZIP.C //ZIPH DD DISP=SHR,DSN=prefix.ZIP.H //SYSIN DD * dd:zipc(api) dd:zipc(cms) dd:zipc(cmsmvs) dd:zipc(crctab) dd:zipc(crc32) dd:zipc(crypt) dd:zipc(deflate) dd:zipc(fileio) dd:zipc(globals) dd:zipc(mktime) dd:zipc(mvs) dd:zipc(trees) dd:zipc(ttyio) dd:zipc(util) dd:zipc(zip) dd:zipc(zipcloak) dd:zipc(zipfile) dd:zipc(zipnote) dd:zipc(zipsplit) dd:zipc(zipup) dd:ziph(api) dd:ziph(cmsmvs) dd:ziph(crypt) dd:ziph(cstat) dd:ziph(ebcdic) dd:ziph(mvs) dd:ziph(revision) dd:ziph(stat) dd:ziph(tailor) dd:ziph(ttyio) dd:ziph(zip) dd:ziph(ziperr) dd:ziph(zipup) zip30/cmsmvs/zip.exec0100644000076400000060000000461306521205542012746 0ustar edisk/***********************************************************************/ /* */ /* Front-end EXEC to set up linkage to the C runtime libraries */ /* before executing a MODULE generated from C code. */ /* */ /* Copy this file as an EXEC with a filename matching the C MODULE. */ /* */ /* Greg Hartwig (ghartwig@vnet.ibm.com) 7/31/97, 4/24/98. */ /* */ /***********************************************************************/ Address Command Parse Arg argstring Parse Source . . myname . /* Set output and input character translation so brackets show up */ 'SET OUTPUT AD' 'BA'x 'SET OUTPUT BD' 'BB'x 'SET INPUT BA AD' 'SET INPUT BB BD' Call CLIB If rc<>0 Then Do Say 'The required C runtime libraries don''t appear to be available.' Say myname 'can not run.' Exit 12 End /* Run the command */ myname argstring Exit rc /* Contents of the CLIB EXEC, modified for RC checking. */ /* Removed TXTLIB setting. Only LOADLIB needed for execution. */ CLIB: /***************************************************/ /* SET UP LIBRARIES FOR LE for MVS & VM */ /***************************************************/ Address COMMAND loadlib ='EDCLINK' /* C/370 runtime */ loadlib ='SCEERUN' /* LE runtime */ theirs=queued() /* old stack contentsM068*/ 'QUERY LOADLIB ( LIFO' /* old setting M068*/ LoadlibList='' /* init list M068*/ rc=0 Do while queued()^=theirs /* all lines from cmdM068*/ Parse upper pull 'LOADLIB' '=' Ltemp /* get one line M068*/ LoadlibList= Ltemp Loadliblist /* was stacked LIFO M068*/ End /*M068*/ If loadlibList='NONE' , Then Do 'GLOBAL LOADLIB' Loadlib /* enforce what we need */ End Else Do Do xx=1 to Words(loadlib) If Find(loadliblist,word(loadlib,xx)) = 0 , then loadliblist = loadliblist word(loadlib,xx) End 'GLOBAL LOADLIB' loadliblist /* enforce what we need */ End Return zip30/cmsmvs/zip.makefile0100644000076400000060000000040610550046234013571 0ustar edisk* This is a comment * this makefile compiles filter ZIPME GLOBALS: long def(VM_CMS) TEXT: trees c crypt c ttyio c deflate c fileio c globals c zip c util c crc32.c zipfile c zipup c cmsmvs c cms c MODULE: zip module zip30/cmsmvs/zipcloak.exec0100644000076400000060000000461306521205544013762 0ustar edisk/***********************************************************************/ /* */ /* Front-end EXEC to set up linkage to the C runtime libraries */ /* before executing a MODULE generated from C code. */ /* */ /* Copy this file as an EXEC with a filename matching the C MODULE. */ /* */ /* Greg Hartwig (ghartwig@vnet.ibm.com) 7/31/97, 4/24/98. */ /* */ /***********************************************************************/ Address Command Parse Arg argstring Parse Source . . myname . /* Set output and input character translation so brackets show up */ 'SET OUTPUT AD' 'BA'x 'SET OUTPUT BD' 'BB'x 'SET INPUT BA AD' 'SET INPUT BB BD' Call CLIB If rc<>0 Then Do Say 'The required C runtime libraries don''t appear to be available.' Say myname 'can not run.' Exit 12 End /* Run the command */ myname argstring Exit rc /* Contents of the CLIB EXEC, modified for RC checking. */ /* Removed TXTLIB setting. Only LOADLIB needed for execution. */ CLIB: /***************************************************/ /* SET UP LIBRARIES FOR LE for MVS & VM */ /***************************************************/ Address COMMAND loadlib ='EDCLINK' /* C/370 runtime */ loadlib ='SCEERUN' /* LE runtime */ theirs=queued() /* old stack contentsM068*/ 'QUERY LOADLIB ( LIFO' /* old setting M068*/ LoadlibList='' /* init list M068*/ rc=0 Do while queued()^=theirs /* all lines from cmdM068*/ Parse upper pull 'LOADLIB' '=' Ltemp /* get one line M068*/ LoadlibList= Ltemp Loadliblist /* was stacked LIFO M068*/ End /*M068*/ If loadlibList='NONE' , Then Do 'GLOBAL LOADLIB' Loadlib /* enforce what we need */ End Else Do Do xx=1 to Words(loadlib) If Find(loadliblist,word(loadlib,xx)) = 0 , then loadliblist = loadliblist word(loadlib,xx) End 'GLOBAL LOADLIB' loadliblist /* enforce what we need */ End Return zip30/cmsmvs/zipmvsc.job0100644000076400000060000001036110550046346013464 0ustar edisk//CCZIP JOB (BI09255), // MSGLEVEL=(1,1),MSGCLASS=C,CLASS=D,NOTIFY=C888090 //PROCLIB JCLLIB ORDER=(SYS1.C370.PROCLIB.M24) //ZIP EXEC EDCC,COND=(12,LE),CREGSIZ='4M', // INFILE='C888090.ZIP.C(ZIP)', // OUTFILE='C888090.ZIP.C.OBJ(ZIP),DISP=SHR', // CPARM='LONG,NOTERM,LIST,XREF,SOURCE,OPT(2),DEF(MVS)' //COMPILE.USERLIB DD DSN=C888090.ZIP.H,DISP=SHR //CRYPT EXEC EDCC,COND=(12,LE),CREGSIZ='4M', // INFILE='C888090.ZIP.C(CRYPT)', // OUTFILE='C888090.ZIP.C.OBJ(CRYPT),DISP=SHR', // CPARM='LONG,NOTERM,LIST,XREF,SOURCE,OPT(2),DEF(MVS)' //COMPILE.USERLIB DD DSN=C888090.ZIP.H,DISP=SHR //TTYIO EXEC EDCC,COND=(12,LE),CREGSIZ='4M', // INFILE='C888090.ZIP.C(TTYIO)', // OUTFILE='C888090.ZIP.C.OBJ(TTYIO),DISP=SHR', // CPARM='LONG,NOTERM,LIST,XREF,SOURCE,OPT(2),DEF(MVS)' //COMPILE.USERLIB DD DSN=C888090.ZIP.H,DISP=SHR //TREES EXEC EDCC,COND=(12,LE),CREGSIZ='4M', // INFILE='C888090.ZIP.C(TREES)', // OUTFILE='C888090.ZIP.C.OBJ(TREES),DISP=SHR', // CPARM='LONG,NOTERM,LIST,XREF,SOURCE,OPT(2),DEF(MVS)' //COMPILE.USERLIB DD DSN=C888090.ZIP.H,DISP=SHR //DEFLATE EXEC EDCC,COND=(12,LE),CREGSIZ='4M', // INFILE='C888090.ZIP.C(DEFLATE)', // OUTFILE='C888090.ZIP.C.OBJ(DEFLATE),DISP=SHR', // CPARM='LONG,NOTERM,LIST,XREF,SOURCE,OPT(2),DEF(MVS)' //COMPILE.USERLIB DD DSN=C888090.ZIP.H,DISP=SHR //FILEIO EXEC EDCC,COND=(12,LE),CREGSIZ='4M', // INFILE='C888090.ZIP.C(FILEIO)', // OUTFILE='C888090.ZIP.C.OBJ(FILEIO),DISP=SHR', // CPARM='LONG,NOTERM,LIST,XREF,SOURCE,OPT(2),DEF(MVS)' //COMPILE.USERLIB DD DSN=C888090.ZIP.H,DISP=SHR //GLOBALS EXEC EDCC,COND=(12,LE),CREGSIZ='4M', // INFILE='C888090.ZIP.C(GLOBALS)', // OUTFILE='C888090.ZIP.C.OBJ(GLOBALS),DISP=SHR', // CPARM='LONG,NOTERM,LIST,XREF,SOURCE,OPT(2),DEF(MVS)' //COMPILE.USERLIB DD DSN=C888090.ZIP.H,DISP=SHR //UTIL EXEC EDCC,COND=(12,LE),CREGSIZ='4M', // INFILE='C888090.ZIP.C(UTIL)', // OUTFILE='C888090.ZIP.C.OBJ(UTIL),DISP=SHR', // CPARM='LONG,NOTERM,LIST,XREF,SOURCE,OPT(2),DEF(MVS)' //COMPILE.USERLIB DD DSN=C888090.ZIP.H,DISP=SHR //CRC32 EXEC EDCC,COND=(12,LE),CREGSIZ='4M', // INFILE='C888090.ZIP.C(CRC32)', // OUTFILE='C888090.ZIP.C.OBJ(CRC32),DISP=SHR', // CPARM='LONG,NOTERM,LIST,XREF,SOURCE,OPT(2),DEF(MVS)' //COMPILE.USERLIB DD DSN=C888090.ZIP.H,DISP=SHR //ZIPFILE EXEC EDCC,COND=(12,LE),CREGSIZ='4M', // INFILE='C888090.ZIP.C(ZIPFILE)', // OUTFILE='C888090.ZIP.C.OBJ(ZIPFILE),DISP=SHR', // CPARM='LONG,NOTERM,LIST,XREF,SOURCE,OPT(2),DEF(MVS)' //COMPILE.USERLIB DD DSN=C888090.ZIP.H,DISP=SHR //ZIPUP EXEC EDCC,COND=(12,LE),CREGSIZ='4M', // INFILE='C888090.ZIP.C(ZIPUP)', // OUTFILE='C888090.ZIP.C.OBJ(ZIPUP),DISP=SHR', // CPARM='LONG,NOTERM,LIST,XREF,SOURCE,OPT(2),DEF(MVS)' //COMPILE.USERLIB DD DSN=C888090.ZIP.H,DISP=SHR //CMSMVS EXEC EDCC,COND=(12,LE),CREGSIZ='4M', // INFILE='C888090.ZIP.C(CMSMVS)', // OUTFILE='C888090.ZIP.C.OBJ(CMSMVS),DISP=SHR', // CPARM='LONG,NOTERM,LIST,XREF,SOURCE,OPT(2),DEF(MVS)' //COMPILE.USERLIB DD DSN=C888090.ZIP.H,DISP=SHR //MVS EXEC EDCC,COND=(12,LE),CREGSIZ='4M', // INFILE='C888090.ZIP.C(MVS)', // OUTFILE='C888090.ZIP.C.OBJ(MVS),DISP=SHR', // CPARM='LONG,NOTERM,LIST,XREF,SOURCE,OPT(2),DEF(MVS)' //COMPILE.USERLIB DD DSN=C888090.ZIP.H,DISP=SHR //PLINK EXEC PROC=EDCPL,COND=(12,LE), // OUTFILE='C888090.ZIP.LOAD(ZIP),DISP=SHR', // PPARM='NONCAL,MAP', // LPARM='LIST,MAP,XREF' //SYSPRINT DD SYSOUT=* //PLKED.SYSIN DD DSN=C888090.ZIP.C.OBJ(ZIP),DISP=SHR // DD DSN=C888090.ZIP.C.OBJ(BITS),DISP=SHR // DD DSN=C888090.ZIP.C.OBJ(CRYPT),DISP=SHR // DD DSN=C888090.ZIP.C.OBJ(TREES),DISP=SHR // DD DSN=C888090.ZIP.C.OBJ(DEFLATE),DISP=SHR // DD DSN=C888090.ZIP.C.OBJ(FILEIO),DISP=SHR // DD DSN=C888090.ZIP.C.OBJ(GLOBALS),DISP=SHR // DD DSN=C888090.ZIP.C.OBJ(UTIL),DISP=SHR // DD DSN=C888090.ZIP.C.OBJ(CRC32),DISP=SHR // DD DSN=C888090.ZIP.C.OBJ(ZIPFILE),DISP=SHR // DD DSN=C888090.ZIP.C.OBJ(ZIPUP),DISP=SHR // DD DSN=C888090.ZIP.C.OBJ(CMSMVS),DISP=SHR // DD DSN=C888090.ZIP.C.OBJ(MVS),DISP=SHR //PLKED.SYSLIB DD DSN=SYS1.C370.SEDCBASE,DISP=SHR // DD DSN=SYS1.PL1.SIBMBASE,DISP=SHR //SYSUT1 DD UNIT=SYSDA,SPACE=(CYL,(2,2)),DISP=NEW zip30/cmsmvs/zipname.conven0100644000076400000060000001374606426263450014170 0ustar edisk Zip file/directories name convention under MVS --------------------------------------------------- Draft 1.1 1. Translating native file names to Zip filenames. 1.1 Zipping a PDS On MVS there are directories called PDS (Partition Data Set) which have the following format : name1.name2.name3(mname) for example: myuserid.unzip.c(unzip) So as you see the path delimiter is '.'. Each dir name can be max 8 chars long beginning with a number. Between '(' and ')' there is the so called member name - it is also 8 chars long. This is the actual file name. 1.1.1 Converting MVS PDS name to zip path/filename (status: not implemented) The PDS name is converted to zippath as follows: in the zip : name1/name2/mname.name3 becomes on MVS: name1.name2.name3(mname) 1.2 Unzipping as PDS (status: implemented) When you unzip the file name myuserid/unzip/unzip.c the same process is done backwards, so you get : myuserid.unzip.c(unzip) Notice that the file extension is used as last dirname! 1.2 Unzipping to a different PDS (status: implemented) You can also use -d option while unzipping for example: unzip mytest myuserid/unzip/unzip.c -dnewdest.test then the new name will become: newdest.test.myuserid.unzip.c(unzip) Second example: unzip mytest myuserid/unzip/*.c -dnewdest.test then you get a PDS: newdest.test.myuserid.unzip.c(...) with all *.c files in it. 1.3 Zipping a Sequential Dataset (status: not implemented) Sequential dataset is a dataset with NO members. Such a dataset is translated from native MVS to zip format by replacing the '.' (points) with '/' (backslash). Example: on MVS: name1.name2.name3 becomes in the zip : name1/name2/name3 NOTE : The new filename in the zip has NO extension this way it can be recognised as a Sequential dataset and not a PDS. But this also means that all files in the zip archive that have no extension will be unzipped as Sequential datasets! 1.4 Using a DDNAMES for input. (status: not implemented) To use DDNAMES as input file names put a 'dd:' before the ddname: example: zip myzip dd:name1 dd:name2 dd:sales In the Zip archive the ddnames are saved as name.DDNAME so if you try the example above you will get in your zip file (when listing it) : ..size .. date time .. crc .. NAME1.DDNAME ..size .. date time .. crc .. NAME2.DDNAME ..size .. date time .. crc .. SALES.DDNAME 1.4 Using a DDNAMES as zip name (status: implemented) It is allowed to use a DDNAME as zipfile, just put dd: before it example: unzip dd:myzip *.c this will unzip all .c files from ddname myzip example2: ZIP DD:MYZIP DD:MANE1 MYSOURCE.C MYDOC.TEXT(ZIPPING) this will zip ddname name1 file mysource.c and PDS mydoc.text(zipping) into as a zip file in the ddname myzip 2. Converting longer path names (unix like) (status: not implemented) to native MVS names. When in the zip archive there are dirnames longer that 8 chars they are chopped at the 8 position. For example MyLongZippath/WithLongFileName.text is translated to: MYLONGZI.TEXT(WITHLONG) Notice that all chars are converted to uppercase. 2.1 Using special characters (status: implemented) Also all '_' (underscore), '+' (plus), '-' (minus), '(' and ')' from the file name/path in the zip archive are skipped because they are not valid in the MVS filenames. 2.2 Numeric file names (status: not implemented) On MVS no name can begin with a number, so when a dir/file name begins with one, a leading letter 'N' is inserted. For example: Contents.512 becomes: CONTENTS.N512 Zip file/directories name convention under VM/CMS --------------------------------------------------- 1. Translating native file names to Zip filenames. On VM/CMS (not ESA ) there are NO directories so you got only disks and files. The file names are delimited with spaces. But for use with unzip/zip you have to use '.' points as delimiters. For example on your A disk you have file called PROFILE EXEC if you want to zip it type : zip myzip profile.exec If the same file is on your F disk you have to type: zip myzip profile.exec.f So as you can see the general format is fname.ftype.fmode In the zipfile the disk from which the file comes is not saved! So only the fname.ftype is saved. If you unzip and you want to give a different destination disk just use the -d option like: unzip mytest *.c -df This will unzip all *.c files to your F disk. 2. Converting longer path names (unix like) to native VM/CMS names. When in the zip archive there are dirnames longer that 8 chars they are chopped at the 8 position. Also the path is removed. For example Zippath/WithLongFileName.text is translated to: WITHLONG.TEXT Notice that all chars are converted to uppercase. Also all '+' (plus), '-' (minus), '(' and ')' from the file name/path in the zip archive are skipped because they are not valid in the VM/CMS filenames. If there is no extension for the file name in the zip archive, unzip will add .NONAME for example: mypath/dir1/testfile becomes: TESTFILE.NONAME 3. Future? There is also discussion for a new option on ZIP that you can give a virtual directory to be added before each file name that is zipped. For example you want to zip a few .c file and put them in the zip structure under the directory 'mydir/test', but you can't create dirs on VM/CMS so you have to the something like: ZIP myzip file1.c file2.c -dmydir/test and you get in the zip archive files: mydir/test/file1.c mydir/test/file2.c ------------------------------------------------------------------------- NOTE: Not all of those functions are implemented in the first beta release of VM/MVS UNZIP/ZIP. Every ideas/corrections/bugs will be appreciated. Mail to maillist: Info-ZIP@LISTS.WKU.EDU George Petrov zip30/cmsmvs/zipnote.exec0100644000076400000060000000461306521205544013636 0ustar edisk/***********************************************************************/ /* */ /* Front-end EXEC to set up linkage to the C runtime libraries */ /* before executing a MODULE generated from C code. */ /* */ /* Copy this file as an EXEC with a filename matching the C MODULE. */ /* */ /* Greg Hartwig (ghartwig@vnet.ibm.com) 7/31/97, 4/24/98. */ /* */ /***********************************************************************/ Address Command Parse Arg argstring Parse Source . . myname . /* Set output and input character translation so brackets show up */ 'SET OUTPUT AD' 'BA'x 'SET OUTPUT BD' 'BB'x 'SET INPUT BA AD' 'SET INPUT BB BD' Call CLIB If rc<>0 Then Do Say 'The required C runtime libraries don''t appear to be available.' Say myname 'can not run.' Exit 12 End /* Run the command */ myname argstring Exit rc /* Contents of the CLIB EXEC, modified for RC checking. */ /* Removed TXTLIB setting. Only LOADLIB needed for execution. */ CLIB: /***************************************************/ /* SET UP LIBRARIES FOR LE for MVS & VM */ /***************************************************/ Address COMMAND loadlib ='EDCLINK' /* C/370 runtime */ loadlib ='SCEERUN' /* LE runtime */ theirs=queued() /* old stack contentsM068*/ 'QUERY LOADLIB ( LIFO' /* old setting M068*/ LoadlibList='' /* init list M068*/ rc=0 Do while queued()^=theirs /* all lines from cmdM068*/ Parse upper pull 'LOADLIB' '=' Ltemp /* get one line M068*/ LoadlibList= Ltemp Loadliblist /* was stacked LIFO M068*/ End /*M068*/ If loadlibList='NONE' , Then Do 'GLOBAL LOADLIB' Loadlib /* enforce what we need */ End Else Do Do xx=1 to Words(loadlib) If Find(loadliblist,word(loadlib,xx)) = 0 , then loadliblist = loadliblist word(loadlib,xx) End 'GLOBAL LOADLIB' loadliblist /* enforce what we need */ End Return zip30/cmsmvs/zipsplit.exec0100644000076400000060000000461306521205546014026 0ustar edisk/***********************************************************************/ /* */ /* Front-end EXEC to set up linkage to the C runtime libraries */ /* before executing a MODULE generated from C code. */ /* */ /* Copy this file as an EXEC with a filename matching the C MODULE. */ /* */ /* Greg Hartwig (ghartwig@vnet.ibm.com) 7/31/97, 4/24/98. */ /* */ /***********************************************************************/ Address Command Parse Arg argstring Parse Source . . myname . /* Set output and input character translation so brackets show up */ 'SET OUTPUT AD' 'BA'x 'SET OUTPUT BD' 'BB'x 'SET INPUT BA AD' 'SET INPUT BB BD' Call CLIB If rc<>0 Then Do Say 'The required C runtime libraries don''t appear to be available.' Say myname 'can not run.' Exit 12 End /* Run the command */ myname argstring Exit rc /* Contents of the CLIB EXEC, modified for RC checking. */ /* Removed TXTLIB setting. Only LOADLIB needed for execution. */ CLIB: /***************************************************/ /* SET UP LIBRARIES FOR LE for MVS & VM */ /***************************************************/ Address COMMAND loadlib ='EDCLINK' /* C/370 runtime */ loadlib ='SCEERUN' /* LE runtime */ theirs=queued() /* old stack contentsM068*/ 'QUERY LOADLIB ( LIFO' /* old setting M068*/ LoadlibList='' /* init list M068*/ rc=0 Do while queued()^=theirs /* all lines from cmdM068*/ Parse upper pull 'LOADLIB' '=' Ltemp /* get one line M068*/ LoadlibList= Ltemp Loadliblist /* was stacked LIFO M068*/ End /*M068*/ If loadlibList='NONE' , Then Do 'GLOBAL LOADLIB' Loadlib /* enforce what we need */ End Else Do Do xx=1 to Words(loadlib) If Find(loadliblist,word(loadlib,xx)) = 0 , then loadliblist = loadliblist word(loadlib,xx) End 'GLOBAL LOADLIB' loadliblist /* enforce what we need */ End Return zip30/cmsmvs/zipup.h0100644000076400000060000000120307011110710012571 0ustar edisk/* Copyright (c) 1990-1999 Info-ZIP. All rights reserved. See the accompanying file LICENSE, version 1999-Oct-05 or later (the contents of which are also included in zip.h) for terms of use. If, for some reason, both of these files are missing, the Info-ZIP license also may be found at: ftp://ftp.cdrom.com/pub/infozip/license.html */ #define fhow "r,byteseek" #define fhowb "rb,byteseek" #define fbad NULL typedef FILE *ftype; #define zopen(n,p) (ftype)fopen((n),(p)) #define zread(f,b,n) fread((b),1,(n),(FILE*)(f)) #define zclose(f) fclose((FILE*)(f)) #define zerr(f) ferror((FILE*)(f)) #define zstdin stdin zip30/cmsmvs/zipvmc.exec0100644000076400000060000000211110551407226013444 0ustar edisk/* VMCOMPIL EXEC Unzip compile for VM/CMS */ /* Author : George Petrov, 11 Apr 1995 */ signal on error parms = '(long def(VM_CMS)' /* Add local parms */ parms = parms 'TARGET(COMPAT) SOURCE' say 'Compiling TREES C...' 'cc trees c 'parms say 'Compiling CRYPT C...' 'cc crypt c 'parms say 'Compiling TTYIO C...' 'cc ttyio c 'parms say 'Compiling DEFLATE C...' 'cc deflate c 'parms say 'Compiling FILEIO C...' 'cc fileio c 'parms say 'Compiling GLOBALS C...' 'cc globals c 'parms say 'Compiling ZIP C...' 'cc zip c 'parms say 'Compiling UTIL C...' 'cc util c 'parms say 'Compiling CRC32 C...' 'cc crc32 c 'parms say 'Compiling ZIPFILE C...' 'cc zipfile c 'parms say 'Compiling ZIPUP C...' 'cc zipup c 'parms say 'Compiling CMSMVS C...' 'cc cmsmvs c 'parms say 'Compiling CMS C...' 'cc cms c 'parms say 'Linking all files...' 'cmod zip zip trees crypt deflate fileio globals ttyio', 'util crc32 zipfile zipup cmsmvs cms' say 'All Done!' say "To run enter : ZIP parms" exit rc error: say 'Error durring compilation!' exit rc zip30/crc32.c0100644000076400000060000011335511007364634011055 0ustar edisk/* Copyright (c) 1990-2008 Info-ZIP. All rights reserved. See the accompanying file LICENSE, version 2007-Mar-4 or later (the contents of which are also included in zip.h) for terms of use. If, for some reason, all these files are missing, the Info-ZIP license also may be found at: ftp://ftp.info-zip.org/pub/infozip/license.html */ /* crc32.c -- compute the CRC-32 of a data stream * Copyright (C) 1995 Mark Adler * For conditions of distribution and use, see copyright notice in zlib.h * * Thanks to Rodney Brown for his contribution of faster * CRC methods: exclusive-oring 32 bits of data at a time, and pre-computing * tables for updating the shift register in one step with three exclusive-ors * instead of four steps with four exclusive-ors. This results about a factor * of two increase in speed on a Power PC G4 (PPC7455) using gcc -O3. */ /* $Id: crc32.c,v 2.0 2007/01/07 05:20:36 spc Exp $ */ #define __CRC32_C /* identifies this source module */ #include "zip.h" #if (!defined(USE_ZLIB) || defined(USE_OWN_CRCTAB)) #ifndef ZCONST # define ZCONST const #endif #include "crc32.h" /* When only the table of precomputed CRC values is needed, only the basic system-independent table containing 256 entries is created; any support for "unfolding" optimization is disabled. */ #if (defined(USE_ZLIB) || defined(CRC_TABLE_ONLY)) # ifdef IZ_CRCOPTIM_UNFOLDTBL # undef IZ_CRCOPTIM_UNFOLDTBL # endif #endif /* (USE_ZLIB || CRC_TABLE_ONLY) */ #if defined(IZ_CRCOPTIM_UNFOLDTBL) # define CRC_TBLS 4 #else # define CRC_TBLS 1 #endif /* Generate tables for a byte-wise 32-bit CRC calculation on the polynomial: x^32+x^26+x^23+x^22+x^16+x^12+x^11+x^10+x^8+x^7+x^5+x^4+x^2+x+1. Polynomials over GF(2) are represented in binary, one bit per coefficient, with the lowest powers in the most significant bit. Then adding polynomials is just exclusive-or, and multiplying a polynomial by x is a right shift by one. If we call the above polynomial p, and represent a byte as the polynomial q, also with the lowest power in the most significant bit (so the byte 0xb1 is the polynomial x^7+x^3+x+1), then the CRC is (q*x^32) mod p, where a mod b means the remainder after dividing a by b. This calculation is done using the shift-register method of multiplying and taking the remainder. The register is initialized to zero, and for each incoming bit, x^32 is added mod p to the register if the bit is a one (where x^32 mod p is p+x^32 = x^26+...+1), and the register is multiplied mod p by x (which is shifting right by one and adding x^32 mod p if the bit shifted out is a one). We start with the highest power (least significant bit) of q and repeat for all eight bits of q. The first (or only) table is simply the CRC of all possible eight bit values. This is all the information needed to generate CRC's on data a byte-at-a-time for all combinations of CRC register values and incoming bytes. The remaining 3 tables (if IZ_CRCOPTIM_UNFOLDTBL is enabled) allow for word-at-a-time CRC calculation, where a word is four bytes. */ #ifdef DYNAMIC_CRC_TABLE /* ========================================================================= * Make the crc table. This function is needed only if you want to compute * the table dynamically. */ local void make_crc_table OF((void)); #if (defined(DYNALLOC_CRCTAB) && defined(REENTRANT)) error: Dynamic allocation of CRC table not safe with reentrant code. #endif /* DYNALLOC_CRCTAB && REENTRANT */ #ifdef DYNALLOC_CRCTAB local ulg near *crc_table = NULL; # if 0 /* not used, since sizeof("near *") <= sizeof(int) */ /* Use this section when access to a "local int" is faster than access to a "local pointer" (e.g.: i86 16bit code with far pointers). */ local int crc_table_empty = 1; # define CRC_TABLE_IS_EMPTY (crc_table_empty != 0) # define MARK_CRCTAB_FILLED crc_table_empty = 0 # define MARK_CRCTAB_EMPTY crc_table_empty = 1 # else /* Use this section on systems where the size of pointers and ints is equal (e.g.: all 32bit systems). */ # define CRC_TABLE_IS_EMPTY (crc_table == NULL) # define MARK_CRCTAB_FILLED crc_table = crctab_p # define MARK_CRCTAB_EMPTY crc_table = NULL # endif #else /* !DYNALLOC_CRCTAB */ local ulg near crc_table[CRC_TBLS*256]; local int crc_table_empty = 1; # define CRC_TABLE_IS_EMPTY (crc_table_empty != 0) # define MARK_CRCTAB_FILLED crc_table_empty = 0 #endif /* ?DYNALLOC_CRCTAB */ local void make_crc_table() { ulg c; /* crc shift register */ int n; /* counter for all possible eight bit values */ int k; /* byte being shifted into crc apparatus */ #ifdef DYNALLOC_CRCTAB ulg near *crctab_p; /* temporary pointer to allocated crc_table area */ #else /* !DYNALLOC_CRCTAB */ # define crctab_p crc_table #endif /* DYNALLOC_CRCTAB */ #ifdef COMPUTE_XOR_PATTERN /* This piece of code has been left here to explain how the XOR pattern * used in the creation of the crc_table values can be recomputed. * For production versions of this function, it is more efficient to * supply the resultant pattern at compile time. */ ulg xor; /* polynomial exclusive-or pattern */ /* terms of polynomial defining this crc (except x^32): */ static ZCONST uch p[] = {0,1,2,4,5,7,8,10,11,12,16,22,23,26}; /* make exclusive-or pattern from polynomial (0xedb88320L) */ xor = 0L; for (n = 0; n < sizeof(p)/sizeof(uch); n++) xor |= 1L << (31 - p[n]); #else # define xor 0xedb88320L #endif #ifdef DYNALLOC_CRCTAB crctab_p = (ulg near *) nearmalloc (CRC_TBLS*256*sizeof(ulg)); if (crctab_p == NULL) { ziperr(ZE_MEM, "crc_table allocation"); } #endif /* DYNALLOC_CRCTAB */ /* generate a crc for every 8-bit value */ for (n = 0; n < 256; n++) { c = (ulg)n; for (k = 8; k; k--) c = c & 1 ? xor ^ (c >> 1) : c >> 1; crctab_p[n] = REV_BE(c); } #ifdef IZ_CRCOPTIM_UNFOLDTBL /* generate crc for each value followed by one, two, and three zeros */ for (n = 0; n < 256; n++) { c = crctab_p[n]; for (k = 1; k < 4; k++) { c = CRC32(c, 0, crctab_p); crctab_p[k*256+n] = c; } } #endif /* IZ_CRCOPTIM_UNFOLDTBL */ MARK_CRCTAB_FILLED; } #else /* !DYNAMIC_CRC_TABLE */ #ifdef DYNALLOC_CRCTAB error: Inconsistent flags, DYNALLOC_CRCTAB without DYNAMIC_CRC_TABLE. #endif /* ======================================================================== * Table of CRC-32's of all single-byte values (made by make_crc_table) */ local ZCONST ulg near crc_table[CRC_TBLS*256] = { # ifdef IZ_CRC_BE_OPTIMIZ 0x00000000L, 0x96300777L, 0x2c610eeeL, 0xba510999L, 0x19c46d07L, 0x8ff46a70L, 0x35a563e9L, 0xa395649eL, 0x3288db0eL, 0xa4b8dc79L, 0x1ee9d5e0L, 0x88d9d297L, 0x2b4cb609L, 0xbd7cb17eL, 0x072db8e7L, 0x911dbf90L, 0x6410b71dL, 0xf220b06aL, 0x4871b9f3L, 0xde41be84L, 0x7dd4da1aL, 0xebe4dd6dL, 0x51b5d4f4L, 0xc785d383L, 0x56986c13L, 0xc0a86b64L, 0x7af962fdL, 0xecc9658aL, 0x4f5c0114L, 0xd96c0663L, 0x633d0ffaL, 0xf50d088dL, 0xc8206e3bL, 0x5e10694cL, 0xe44160d5L, 0x727167a2L, 0xd1e4033cL, 0x47d4044bL, 0xfd850dd2L, 0x6bb50aa5L, 0xfaa8b535L, 0x6c98b242L, 0xd6c9bbdbL, 0x40f9bcacL, 0xe36cd832L, 0x755cdf45L, 0xcf0dd6dcL, 0x593dd1abL, 0xac30d926L, 0x3a00de51L, 0x8051d7c8L, 0x1661d0bfL, 0xb5f4b421L, 0x23c4b356L, 0x9995bacfL, 0x0fa5bdb8L, 0x9eb80228L, 0x0888055fL, 0xb2d90cc6L, 0x24e90bb1L, 0x877c6f2fL, 0x114c6858L, 0xab1d61c1L, 0x3d2d66b6L, 0x9041dc76L, 0x0671db01L, 0xbc20d298L, 0x2a10d5efL, 0x8985b171L, 0x1fb5b606L, 0xa5e4bf9fL, 0x33d4b8e8L, 0xa2c90778L, 0x34f9000fL, 0x8ea80996L, 0x18980ee1L, 0xbb0d6a7fL, 0x2d3d6d08L, 0x976c6491L, 0x015c63e6L, 0xf4516b6bL, 0x62616c1cL, 0xd8306585L, 0x4e0062f2L, 0xed95066cL, 0x7ba5011bL, 0xc1f40882L, 0x57c40ff5L, 0xc6d9b065L, 0x50e9b712L, 0xeab8be8bL, 0x7c88b9fcL, 0xdf1ddd62L, 0x492dda15L, 0xf37cd38cL, 0x654cd4fbL, 0x5861b24dL, 0xce51b53aL, 0x7400bca3L, 0xe230bbd4L, 0x41a5df4aL, 0xd795d83dL, 0x6dc4d1a4L, 0xfbf4d6d3L, 0x6ae96943L, 0xfcd96e34L, 0x468867adL, 0xd0b860daL, 0x732d0444L, 0xe51d0333L, 0x5f4c0aaaL, 0xc97c0dddL, 0x3c710550L, 0xaa410227L, 0x10100bbeL, 0x86200cc9L, 0x25b56857L, 0xb3856f20L, 0x09d466b9L, 0x9fe461ceL, 0x0ef9de5eL, 0x98c9d929L, 0x2298d0b0L, 0xb4a8d7c7L, 0x173db359L, 0x810db42eL, 0x3b5cbdb7L, 0xad6cbac0L, 0x2083b8edL, 0xb6b3bf9aL, 0x0ce2b603L, 0x9ad2b174L, 0x3947d5eaL, 0xaf77d29dL, 0x1526db04L, 0x8316dc73L, 0x120b63e3L, 0x843b6494L, 0x3e6a6d0dL, 0xa85a6a7aL, 0x0bcf0ee4L, 0x9dff0993L, 0x27ae000aL, 0xb19e077dL, 0x44930ff0L, 0xd2a30887L, 0x68f2011eL, 0xfec20669L, 0x5d5762f7L, 0xcb676580L, 0x71366c19L, 0xe7066b6eL, 0x761bd4feL, 0xe02bd389L, 0x5a7ada10L, 0xcc4add67L, 0x6fdfb9f9L, 0xf9efbe8eL, 0x43beb717L, 0xd58eb060L, 0xe8a3d6d6L, 0x7e93d1a1L, 0xc4c2d838L, 0x52f2df4fL, 0xf167bbd1L, 0x6757bca6L, 0xdd06b53fL, 0x4b36b248L, 0xda2b0dd8L, 0x4c1b0aafL, 0xf64a0336L, 0x607a0441L, 0xc3ef60dfL, 0x55df67a8L, 0xef8e6e31L, 0x79be6946L, 0x8cb361cbL, 0x1a8366bcL, 0xa0d26f25L, 0x36e26852L, 0x95770cccL, 0x03470bbbL, 0xb9160222L, 0x2f260555L, 0xbe3bbac5L, 0x280bbdb2L, 0x925ab42bL, 0x046ab35cL, 0xa7ffd7c2L, 0x31cfd0b5L, 0x8b9ed92cL, 0x1daede5bL, 0xb0c2649bL, 0x26f263ecL, 0x9ca36a75L, 0x0a936d02L, 0xa906099cL, 0x3f360eebL, 0x85670772L, 0x13570005L, 0x824abf95L, 0x147ab8e2L, 0xae2bb17bL, 0x381bb60cL, 0x9b8ed292L, 0x0dbed5e5L, 0xb7efdc7cL, 0x21dfdb0bL, 0xd4d2d386L, 0x42e2d4f1L, 0xf8b3dd68L, 0x6e83da1fL, 0xcd16be81L, 0x5b26b9f6L, 0xe177b06fL, 0x7747b718L, 0xe65a0888L, 0x706a0fffL, 0xca3b0666L, 0x5c0b0111L, 0xff9e658fL, 0x69ae62f8L, 0xd3ff6b61L, 0x45cf6c16L, 0x78e20aa0L, 0xeed20dd7L, 0x5483044eL, 0xc2b30339L, 0x612667a7L, 0xf71660d0L, 0x4d476949L, 0xdb776e3eL, 0x4a6ad1aeL, 0xdc5ad6d9L, 0x660bdf40L, 0xf03bd837L, 0x53aebca9L, 0xc59ebbdeL, 0x7fcfb247L, 0xe9ffb530L, 0x1cf2bdbdL, 0x8ac2bacaL, 0x3093b353L, 0xa6a3b424L, 0x0536d0baL, 0x9306d7cdL, 0x2957de54L, 0xbf67d923L, 0x2e7a66b3L, 0xb84a61c4L, 0x021b685dL, 0x942b6f2aL, 0x37be0bb4L, 0xa18e0cc3L, 0x1bdf055aL, 0x8def022dL # ifdef IZ_CRCOPTIM_UNFOLDTBL , 0x00000000L, 0x41311b19L, 0x82623632L, 0xc3532d2bL, 0x04c56c64L, 0x45f4777dL, 0x86a75a56L, 0xc796414fL, 0x088ad9c8L, 0x49bbc2d1L, 0x8ae8effaL, 0xcbd9f4e3L, 0x0c4fb5acL, 0x4d7eaeb5L, 0x8e2d839eL, 0xcf1c9887L, 0x5112c24aL, 0x1023d953L, 0xd370f478L, 0x9241ef61L, 0x55d7ae2eL, 0x14e6b537L, 0xd7b5981cL, 0x96848305L, 0x59981b82L, 0x18a9009bL, 0xdbfa2db0L, 0x9acb36a9L, 0x5d5d77e6L, 0x1c6c6cffL, 0xdf3f41d4L, 0x9e0e5acdL, 0xa2248495L, 0xe3159f8cL, 0x2046b2a7L, 0x6177a9beL, 0xa6e1e8f1L, 0xe7d0f3e8L, 0x2483dec3L, 0x65b2c5daL, 0xaaae5d5dL, 0xeb9f4644L, 0x28cc6b6fL, 0x69fd7076L, 0xae6b3139L, 0xef5a2a20L, 0x2c09070bL, 0x6d381c12L, 0xf33646dfL, 0xb2075dc6L, 0x715470edL, 0x30656bf4L, 0xf7f32abbL, 0xb6c231a2L, 0x75911c89L, 0x34a00790L, 0xfbbc9f17L, 0xba8d840eL, 0x79dea925L, 0x38efb23cL, 0xff79f373L, 0xbe48e86aL, 0x7d1bc541L, 0x3c2ade58L, 0x054f79f0L, 0x447e62e9L, 0x872d4fc2L, 0xc61c54dbL, 0x018a1594L, 0x40bb0e8dL, 0x83e823a6L, 0xc2d938bfL, 0x0dc5a038L, 0x4cf4bb21L, 0x8fa7960aL, 0xce968d13L, 0x0900cc5cL, 0x4831d745L, 0x8b62fa6eL, 0xca53e177L, 0x545dbbbaL, 0x156ca0a3L, 0xd63f8d88L, 0x970e9691L, 0x5098d7deL, 0x11a9ccc7L, 0xd2fae1ecL, 0x93cbfaf5L, 0x5cd76272L, 0x1de6796bL, 0xdeb55440L, 0x9f844f59L, 0x58120e16L, 0x1923150fL, 0xda703824L, 0x9b41233dL, 0xa76bfd65L, 0xe65ae67cL, 0x2509cb57L, 0x6438d04eL, 0xa3ae9101L, 0xe29f8a18L, 0x21cca733L, 0x60fdbc2aL, 0xafe124adL, 0xeed03fb4L, 0x2d83129fL, 0x6cb20986L, 0xab2448c9L, 0xea1553d0L, 0x29467efbL, 0x687765e2L, 0xf6793f2fL, 0xb7482436L, 0x741b091dL, 0x352a1204L, 0xf2bc534bL, 0xb38d4852L, 0x70de6579L, 0x31ef7e60L, 0xfef3e6e7L, 0xbfc2fdfeL, 0x7c91d0d5L, 0x3da0cbccL, 0xfa368a83L, 0xbb07919aL, 0x7854bcb1L, 0x3965a7a8L, 0x4b98833bL, 0x0aa99822L, 0xc9fab509L, 0x88cbae10L, 0x4f5def5fL, 0x0e6cf446L, 0xcd3fd96dL, 0x8c0ec274L, 0x43125af3L, 0x022341eaL, 0xc1706cc1L, 0x804177d8L, 0x47d73697L, 0x06e62d8eL, 0xc5b500a5L, 0x84841bbcL, 0x1a8a4171L, 0x5bbb5a68L, 0x98e87743L, 0xd9d96c5aL, 0x1e4f2d15L, 0x5f7e360cL, 0x9c2d1b27L, 0xdd1c003eL, 0x120098b9L, 0x533183a0L, 0x9062ae8bL, 0xd153b592L, 0x16c5f4ddL, 0x57f4efc4L, 0x94a7c2efL, 0xd596d9f6L, 0xe9bc07aeL, 0xa88d1cb7L, 0x6bde319cL, 0x2aef2a85L, 0xed796bcaL, 0xac4870d3L, 0x6f1b5df8L, 0x2e2a46e1L, 0xe136de66L, 0xa007c57fL, 0x6354e854L, 0x2265f34dL, 0xe5f3b202L, 0xa4c2a91bL, 0x67918430L, 0x26a09f29L, 0xb8aec5e4L, 0xf99fdefdL, 0x3accf3d6L, 0x7bfde8cfL, 0xbc6ba980L, 0xfd5ab299L, 0x3e099fb2L, 0x7f3884abL, 0xb0241c2cL, 0xf1150735L, 0x32462a1eL, 0x73773107L, 0xb4e17048L, 0xf5d06b51L, 0x3683467aL, 0x77b25d63L, 0x4ed7facbL, 0x0fe6e1d2L, 0xccb5ccf9L, 0x8d84d7e0L, 0x4a1296afL, 0x0b238db6L, 0xc870a09dL, 0x8941bb84L, 0x465d2303L, 0x076c381aL, 0xc43f1531L, 0x850e0e28L, 0x42984f67L, 0x03a9547eL, 0xc0fa7955L, 0x81cb624cL, 0x1fc53881L, 0x5ef42398L, 0x9da70eb3L, 0xdc9615aaL, 0x1b0054e5L, 0x5a314ffcL, 0x996262d7L, 0xd85379ceL, 0x174fe149L, 0x567efa50L, 0x952dd77bL, 0xd41ccc62L, 0x138a8d2dL, 0x52bb9634L, 0x91e8bb1fL, 0xd0d9a006L, 0xecf37e5eL, 0xadc26547L, 0x6e91486cL, 0x2fa05375L, 0xe836123aL, 0xa9070923L, 0x6a542408L, 0x2b653f11L, 0xe479a796L, 0xa548bc8fL, 0x661b91a4L, 0x272a8abdL, 0xe0bccbf2L, 0xa18dd0ebL, 0x62defdc0L, 0x23efe6d9L, 0xbde1bc14L, 0xfcd0a70dL, 0x3f838a26L, 0x7eb2913fL, 0xb924d070L, 0xf815cb69L, 0x3b46e642L, 0x7a77fd5bL, 0xb56b65dcL, 0xf45a7ec5L, 0x370953eeL, 0x763848f7L, 0xb1ae09b8L, 0xf09f12a1L, 0x33cc3f8aL, 0x72fd2493L , 0x00000000L, 0x376ac201L, 0x6ed48403L, 0x59be4602L, 0xdca80907L, 0xebc2cb06L, 0xb27c8d04L, 0x85164f05L, 0xb851130eL, 0x8f3bd10fL, 0xd685970dL, 0xe1ef550cL, 0x64f91a09L, 0x5393d808L, 0x0a2d9e0aL, 0x3d475c0bL, 0x70a3261cL, 0x47c9e41dL, 0x1e77a21fL, 0x291d601eL, 0xac0b2f1bL, 0x9b61ed1aL, 0xc2dfab18L, 0xf5b56919L, 0xc8f23512L, 0xff98f713L, 0xa626b111L, 0x914c7310L, 0x145a3c15L, 0x2330fe14L, 0x7a8eb816L, 0x4de47a17L, 0xe0464d38L, 0xd72c8f39L, 0x8e92c93bL, 0xb9f80b3aL, 0x3cee443fL, 0x0b84863eL, 0x523ac03cL, 0x6550023dL, 0x58175e36L, 0x6f7d9c37L, 0x36c3da35L, 0x01a91834L, 0x84bf5731L, 0xb3d59530L, 0xea6bd332L, 0xdd011133L, 0x90e56b24L, 0xa78fa925L, 0xfe31ef27L, 0xc95b2d26L, 0x4c4d6223L, 0x7b27a022L, 0x2299e620L, 0x15f32421L, 0x28b4782aL, 0x1fdeba2bL, 0x4660fc29L, 0x710a3e28L, 0xf41c712dL, 0xc376b32cL, 0x9ac8f52eL, 0xada2372fL, 0xc08d9a70L, 0xf7e75871L, 0xae591e73L, 0x9933dc72L, 0x1c259377L, 0x2b4f5176L, 0x72f11774L, 0x459bd575L, 0x78dc897eL, 0x4fb64b7fL, 0x16080d7dL, 0x2162cf7cL, 0xa4748079L, 0x931e4278L, 0xcaa0047aL, 0xfdcac67bL, 0xb02ebc6cL, 0x87447e6dL, 0xdefa386fL, 0xe990fa6eL, 0x6c86b56bL, 0x5bec776aL, 0x02523168L, 0x3538f369L, 0x087faf62L, 0x3f156d63L, 0x66ab2b61L, 0x51c1e960L, 0xd4d7a665L, 0xe3bd6464L, 0xba032266L, 0x8d69e067L, 0x20cbd748L, 0x17a11549L, 0x4e1f534bL, 0x7975914aL, 0xfc63de4fL, 0xcb091c4eL, 0x92b75a4cL, 0xa5dd984dL, 0x989ac446L, 0xaff00647L, 0xf64e4045L, 0xc1248244L, 0x4432cd41L, 0x73580f40L, 0x2ae64942L, 0x1d8c8b43L, 0x5068f154L, 0x67023355L, 0x3ebc7557L, 0x09d6b756L, 0x8cc0f853L, 0xbbaa3a52L, 0xe2147c50L, 0xd57ebe51L, 0xe839e25aL, 0xdf53205bL, 0x86ed6659L, 0xb187a458L, 0x3491eb5dL, 0x03fb295cL, 0x5a456f5eL, 0x6d2fad5fL, 0x801b35e1L, 0xb771f7e0L, 0xeecfb1e2L, 0xd9a573e3L, 0x5cb33ce6L, 0x6bd9fee7L, 0x3267b8e5L, 0x050d7ae4L, 0x384a26efL, 0x0f20e4eeL, 0x569ea2ecL, 0x61f460edL, 0xe4e22fe8L, 0xd388ede9L, 0x8a36abebL, 0xbd5c69eaL, 0xf0b813fdL, 0xc7d2d1fcL, 0x9e6c97feL, 0xa90655ffL, 0x2c101afaL, 0x1b7ad8fbL, 0x42c49ef9L, 0x75ae5cf8L, 0x48e900f3L, 0x7f83c2f2L, 0x263d84f0L, 0x115746f1L, 0x944109f4L, 0xa32bcbf5L, 0xfa958df7L, 0xcdff4ff6L, 0x605d78d9L, 0x5737bad8L, 0x0e89fcdaL, 0x39e33edbL, 0xbcf571deL, 0x8b9fb3dfL, 0xd221f5ddL, 0xe54b37dcL, 0xd80c6bd7L, 0xef66a9d6L, 0xb6d8efd4L, 0x81b22dd5L, 0x04a462d0L, 0x33cea0d1L, 0x6a70e6d3L, 0x5d1a24d2L, 0x10fe5ec5L, 0x27949cc4L, 0x7e2adac6L, 0x494018c7L, 0xcc5657c2L, 0xfb3c95c3L, 0xa282d3c1L, 0x95e811c0L, 0xa8af4dcbL, 0x9fc58fcaL, 0xc67bc9c8L, 0xf1110bc9L, 0x740744ccL, 0x436d86cdL, 0x1ad3c0cfL, 0x2db902ceL, 0x4096af91L, 0x77fc6d90L, 0x2e422b92L, 0x1928e993L, 0x9c3ea696L, 0xab546497L, 0xf2ea2295L, 0xc580e094L, 0xf8c7bc9fL, 0xcfad7e9eL, 0x9613389cL, 0xa179fa9dL, 0x246fb598L, 0x13057799L, 0x4abb319bL, 0x7dd1f39aL, 0x3035898dL, 0x075f4b8cL, 0x5ee10d8eL, 0x698bcf8fL, 0xec9d808aL, 0xdbf7428bL, 0x82490489L, 0xb523c688L, 0x88649a83L, 0xbf0e5882L, 0xe6b01e80L, 0xd1dadc81L, 0x54cc9384L, 0x63a65185L, 0x3a181787L, 0x0d72d586L, 0xa0d0e2a9L, 0x97ba20a8L, 0xce0466aaL, 0xf96ea4abL, 0x7c78ebaeL, 0x4b1229afL, 0x12ac6fadL, 0x25c6adacL, 0x1881f1a7L, 0x2feb33a6L, 0x765575a4L, 0x413fb7a5L, 0xc429f8a0L, 0xf3433aa1L, 0xaafd7ca3L, 0x9d97bea2L, 0xd073c4b5L, 0xe71906b4L, 0xbea740b6L, 0x89cd82b7L, 0x0cdbcdb2L, 0x3bb10fb3L, 0x620f49b1L, 0x55658bb0L, 0x6822d7bbL, 0x5f4815baL, 0x06f653b8L, 0x319c91b9L, 0xb48adebcL, 0x83e01cbdL, 0xda5e5abfL, 0xed3498beL , 0x00000000L, 0x6567bcb8L, 0x8bc809aaL, 0xeeafb512L, 0x5797628fL, 0x32f0de37L, 0xdc5f6b25L, 0xb938d79dL, 0xef28b4c5L, 0x8a4f087dL, 0x64e0bd6fL, 0x018701d7L, 0xb8bfd64aL, 0xddd86af2L, 0x3377dfe0L, 0x56106358L, 0x9f571950L, 0xfa30a5e8L, 0x149f10faL, 0x71f8ac42L, 0xc8c07bdfL, 0xada7c767L, 0x43087275L, 0x266fcecdL, 0x707fad95L, 0x1518112dL, 0xfbb7a43fL, 0x9ed01887L, 0x27e8cf1aL, 0x428f73a2L, 0xac20c6b0L, 0xc9477a08L, 0x3eaf32a0L, 0x5bc88e18L, 0xb5673b0aL, 0xd00087b2L, 0x6938502fL, 0x0c5fec97L, 0xe2f05985L, 0x8797e53dL, 0xd1878665L, 0xb4e03addL, 0x5a4f8fcfL, 0x3f283377L, 0x8610e4eaL, 0xe3775852L, 0x0dd8ed40L, 0x68bf51f8L, 0xa1f82bf0L, 0xc49f9748L, 0x2a30225aL, 0x4f579ee2L, 0xf66f497fL, 0x9308f5c7L, 0x7da740d5L, 0x18c0fc6dL, 0x4ed09f35L, 0x2bb7238dL, 0xc518969fL, 0xa07f2a27L, 0x1947fdbaL, 0x7c204102L, 0x928ff410L, 0xf7e848a8L, 0x3d58149bL, 0x583fa823L, 0xb6901d31L, 0xd3f7a189L, 0x6acf7614L, 0x0fa8caacL, 0xe1077fbeL, 0x8460c306L, 0xd270a05eL, 0xb7171ce6L, 0x59b8a9f4L, 0x3cdf154cL, 0x85e7c2d1L, 0xe0807e69L, 0x0e2fcb7bL, 0x6b4877c3L, 0xa20f0dcbL, 0xc768b173L, 0x29c70461L, 0x4ca0b8d9L, 0xf5986f44L, 0x90ffd3fcL, 0x7e5066eeL, 0x1b37da56L, 0x4d27b90eL, 0x284005b6L, 0xc6efb0a4L, 0xa3880c1cL, 0x1ab0db81L, 0x7fd76739L, 0x9178d22bL, 0xf41f6e93L, 0x03f7263bL, 0x66909a83L, 0x883f2f91L, 0xed589329L, 0x546044b4L, 0x3107f80cL, 0xdfa84d1eL, 0xbacff1a6L, 0xecdf92feL, 0x89b82e46L, 0x67179b54L, 0x027027ecL, 0xbb48f071L, 0xde2f4cc9L, 0x3080f9dbL, 0x55e74563L, 0x9ca03f6bL, 0xf9c783d3L, 0x176836c1L, 0x720f8a79L, 0xcb375de4L, 0xae50e15cL, 0x40ff544eL, 0x2598e8f6L, 0x73888baeL, 0x16ef3716L, 0xf8408204L, 0x9d273ebcL, 0x241fe921L, 0x41785599L, 0xafd7e08bL, 0xcab05c33L, 0x3bb659edL, 0x5ed1e555L, 0xb07e5047L, 0xd519ecffL, 0x6c213b62L, 0x094687daL, 0xe7e932c8L, 0x828e8e70L, 0xd49eed28L, 0xb1f95190L, 0x5f56e482L, 0x3a31583aL, 0x83098fa7L, 0xe66e331fL, 0x08c1860dL, 0x6da63ab5L, 0xa4e140bdL, 0xc186fc05L, 0x2f294917L, 0x4a4ef5afL, 0xf3762232L, 0x96119e8aL, 0x78be2b98L, 0x1dd99720L, 0x4bc9f478L, 0x2eae48c0L, 0xc001fdd2L, 0xa566416aL, 0x1c5e96f7L, 0x79392a4fL, 0x97969f5dL, 0xf2f123e5L, 0x05196b4dL, 0x607ed7f5L, 0x8ed162e7L, 0xebb6de5fL, 0x528e09c2L, 0x37e9b57aL, 0xd9460068L, 0xbc21bcd0L, 0xea31df88L, 0x8f566330L, 0x61f9d622L, 0x049e6a9aL, 0xbda6bd07L, 0xd8c101bfL, 0x366eb4adL, 0x53090815L, 0x9a4e721dL, 0xff29cea5L, 0x11867bb7L, 0x74e1c70fL, 0xcdd91092L, 0xa8beac2aL, 0x46111938L, 0x2376a580L, 0x7566c6d8L, 0x10017a60L, 0xfeaecf72L, 0x9bc973caL, 0x22f1a457L, 0x479618efL, 0xa939adfdL, 0xcc5e1145L, 0x06ee4d76L, 0x6389f1ceL, 0x8d2644dcL, 0xe841f864L, 0x51792ff9L, 0x341e9341L, 0xdab12653L, 0xbfd69aebL, 0xe9c6f9b3L, 0x8ca1450bL, 0x620ef019L, 0x07694ca1L, 0xbe519b3cL, 0xdb362784L, 0x35999296L, 0x50fe2e2eL, 0x99b95426L, 0xfcdee89eL, 0x12715d8cL, 0x7716e134L, 0xce2e36a9L, 0xab498a11L, 0x45e63f03L, 0x208183bbL, 0x7691e0e3L, 0x13f65c5bL, 0xfd59e949L, 0x983e55f1L, 0x2106826cL, 0x44613ed4L, 0xaace8bc6L, 0xcfa9377eL, 0x38417fd6L, 0x5d26c36eL, 0xb389767cL, 0xd6eecac4L, 0x6fd61d59L, 0x0ab1a1e1L, 0xe41e14f3L, 0x8179a84bL, 0xd769cb13L, 0xb20e77abL, 0x5ca1c2b9L, 0x39c67e01L, 0x80fea99cL, 0xe5991524L, 0x0b36a036L, 0x6e511c8eL, 0xa7166686L, 0xc271da3eL, 0x2cde6f2cL, 0x49b9d394L, 0xf0810409L, 0x95e6b8b1L, 0x7b490da3L, 0x1e2eb11bL, 0x483ed243L, 0x2d596efbL, 0xc3f6dbe9L, 0xa6916751L, 0x1fa9b0ccL, 0x7ace0c74L, 0x9461b966L, 0xf10605deL # endif /* IZ_CRCOPTIM_UNFOLDTBL */ # else /* !IZ_CRC_BE_OPTIMIZ */ 0x00000000L, 0x77073096L, 0xee0e612cL, 0x990951baL, 0x076dc419L, 0x706af48fL, 0xe963a535L, 0x9e6495a3L, 0x0edb8832L, 0x79dcb8a4L, 0xe0d5e91eL, 0x97d2d988L, 0x09b64c2bL, 0x7eb17cbdL, 0xe7b82d07L, 0x90bf1d91L, 0x1db71064L, 0x6ab020f2L, 0xf3b97148L, 0x84be41deL, 0x1adad47dL, 0x6ddde4ebL, 0xf4d4b551L, 0x83d385c7L, 0x136c9856L, 0x646ba8c0L, 0xfd62f97aL, 0x8a65c9ecL, 0x14015c4fL, 0x63066cd9L, 0xfa0f3d63L, 0x8d080df5L, 0x3b6e20c8L, 0x4c69105eL, 0xd56041e4L, 0xa2677172L, 0x3c03e4d1L, 0x4b04d447L, 0xd20d85fdL, 0xa50ab56bL, 0x35b5a8faL, 0x42b2986cL, 0xdbbbc9d6L, 0xacbcf940L, 0x32d86ce3L, 0x45df5c75L, 0xdcd60dcfL, 0xabd13d59L, 0x26d930acL, 0x51de003aL, 0xc8d75180L, 0xbfd06116L, 0x21b4f4b5L, 0x56b3c423L, 0xcfba9599L, 0xb8bda50fL, 0x2802b89eL, 0x5f058808L, 0xc60cd9b2L, 0xb10be924L, 0x2f6f7c87L, 0x58684c11L, 0xc1611dabL, 0xb6662d3dL, 0x76dc4190L, 0x01db7106L, 0x98d220bcL, 0xefd5102aL, 0x71b18589L, 0x06b6b51fL, 0x9fbfe4a5L, 0xe8b8d433L, 0x7807c9a2L, 0x0f00f934L, 0x9609a88eL, 0xe10e9818L, 0x7f6a0dbbL, 0x086d3d2dL, 0x91646c97L, 0xe6635c01L, 0x6b6b51f4L, 0x1c6c6162L, 0x856530d8L, 0xf262004eL, 0x6c0695edL, 0x1b01a57bL, 0x8208f4c1L, 0xf50fc457L, 0x65b0d9c6L, 0x12b7e950L, 0x8bbeb8eaL, 0xfcb9887cL, 0x62dd1ddfL, 0x15da2d49L, 0x8cd37cf3L, 0xfbd44c65L, 0x4db26158L, 0x3ab551ceL, 0xa3bc0074L, 0xd4bb30e2L, 0x4adfa541L, 0x3dd895d7L, 0xa4d1c46dL, 0xd3d6f4fbL, 0x4369e96aL, 0x346ed9fcL, 0xad678846L, 0xda60b8d0L, 0x44042d73L, 0x33031de5L, 0xaa0a4c5fL, 0xdd0d7cc9L, 0x5005713cL, 0x270241aaL, 0xbe0b1010L, 0xc90c2086L, 0x5768b525L, 0x206f85b3L, 0xb966d409L, 0xce61e49fL, 0x5edef90eL, 0x29d9c998L, 0xb0d09822L, 0xc7d7a8b4L, 0x59b33d17L, 0x2eb40d81L, 0xb7bd5c3bL, 0xc0ba6cadL, 0xedb88320L, 0x9abfb3b6L, 0x03b6e20cL, 0x74b1d29aL, 0xead54739L, 0x9dd277afL, 0x04db2615L, 0x73dc1683L, 0xe3630b12L, 0x94643b84L, 0x0d6d6a3eL, 0x7a6a5aa8L, 0xe40ecf0bL, 0x9309ff9dL, 0x0a00ae27L, 0x7d079eb1L, 0xf00f9344L, 0x8708a3d2L, 0x1e01f268L, 0x6906c2feL, 0xf762575dL, 0x806567cbL, 0x196c3671L, 0x6e6b06e7L, 0xfed41b76L, 0x89d32be0L, 0x10da7a5aL, 0x67dd4accL, 0xf9b9df6fL, 0x8ebeeff9L, 0x17b7be43L, 0x60b08ed5L, 0xd6d6a3e8L, 0xa1d1937eL, 0x38d8c2c4L, 0x4fdff252L, 0xd1bb67f1L, 0xa6bc5767L, 0x3fb506ddL, 0x48b2364bL, 0xd80d2bdaL, 0xaf0a1b4cL, 0x36034af6L, 0x41047a60L, 0xdf60efc3L, 0xa867df55L, 0x316e8eefL, 0x4669be79L, 0xcb61b38cL, 0xbc66831aL, 0x256fd2a0L, 0x5268e236L, 0xcc0c7795L, 0xbb0b4703L, 0x220216b9L, 0x5505262fL, 0xc5ba3bbeL, 0xb2bd0b28L, 0x2bb45a92L, 0x5cb36a04L, 0xc2d7ffa7L, 0xb5d0cf31L, 0x2cd99e8bL, 0x5bdeae1dL, 0x9b64c2b0L, 0xec63f226L, 0x756aa39cL, 0x026d930aL, 0x9c0906a9L, 0xeb0e363fL, 0x72076785L, 0x05005713L, 0x95bf4a82L, 0xe2b87a14L, 0x7bb12baeL, 0x0cb61b38L, 0x92d28e9bL, 0xe5d5be0dL, 0x7cdcefb7L, 0x0bdbdf21L, 0x86d3d2d4L, 0xf1d4e242L, 0x68ddb3f8L, 0x1fda836eL, 0x81be16cdL, 0xf6b9265bL, 0x6fb077e1L, 0x18b74777L, 0x88085ae6L, 0xff0f6a70L, 0x66063bcaL, 0x11010b5cL, 0x8f659effL, 0xf862ae69L, 0x616bffd3L, 0x166ccf45L, 0xa00ae278L, 0xd70dd2eeL, 0x4e048354L, 0x3903b3c2L, 0xa7672661L, 0xd06016f7L, 0x4969474dL, 0x3e6e77dbL, 0xaed16a4aL, 0xd9d65adcL, 0x40df0b66L, 0x37d83bf0L, 0xa9bcae53L, 0xdebb9ec5L, 0x47b2cf7fL, 0x30b5ffe9L, 0xbdbdf21cL, 0xcabac28aL, 0x53b39330L, 0x24b4a3a6L, 0xbad03605L, 0xcdd70693L, 0x54de5729L, 0x23d967bfL, 0xb3667a2eL, 0xc4614ab8L, 0x5d681b02L, 0x2a6f2b94L, 0xb40bbe37L, 0xc30c8ea1L, 0x5a05df1bL, 0x2d02ef8dL # ifdef IZ_CRCOPTIM_UNFOLDTBL , 0x00000000L, 0x191b3141L, 0x32366282L, 0x2b2d53c3L, 0x646cc504L, 0x7d77f445L, 0x565aa786L, 0x4f4196c7L, 0xc8d98a08L, 0xd1c2bb49L, 0xfaefe88aL, 0xe3f4d9cbL, 0xacb54f0cL, 0xb5ae7e4dL, 0x9e832d8eL, 0x87981ccfL, 0x4ac21251L, 0x53d92310L, 0x78f470d3L, 0x61ef4192L, 0x2eaed755L, 0x37b5e614L, 0x1c98b5d7L, 0x05838496L, 0x821b9859L, 0x9b00a918L, 0xb02dfadbL, 0xa936cb9aL, 0xe6775d5dL, 0xff6c6c1cL, 0xd4413fdfL, 0xcd5a0e9eL, 0x958424a2L, 0x8c9f15e3L, 0xa7b24620L, 0xbea97761L, 0xf1e8e1a6L, 0xe8f3d0e7L, 0xc3de8324L, 0xdac5b265L, 0x5d5daeaaL, 0x44469febL, 0x6f6bcc28L, 0x7670fd69L, 0x39316baeL, 0x202a5aefL, 0x0b07092cL, 0x121c386dL, 0xdf4636f3L, 0xc65d07b2L, 0xed705471L, 0xf46b6530L, 0xbb2af3f7L, 0xa231c2b6L, 0x891c9175L, 0x9007a034L, 0x179fbcfbL, 0x0e848dbaL, 0x25a9de79L, 0x3cb2ef38L, 0x73f379ffL, 0x6ae848beL, 0x41c51b7dL, 0x58de2a3cL, 0xf0794f05L, 0xe9627e44L, 0xc24f2d87L, 0xdb541cc6L, 0x94158a01L, 0x8d0ebb40L, 0xa623e883L, 0xbf38d9c2L, 0x38a0c50dL, 0x21bbf44cL, 0x0a96a78fL, 0x138d96ceL, 0x5ccc0009L, 0x45d73148L, 0x6efa628bL, 0x77e153caL, 0xbabb5d54L, 0xa3a06c15L, 0x888d3fd6L, 0x91960e97L, 0xded79850L, 0xc7cca911L, 0xece1fad2L, 0xf5facb93L, 0x7262d75cL, 0x6b79e61dL, 0x4054b5deL, 0x594f849fL, 0x160e1258L, 0x0f152319L, 0x243870daL, 0x3d23419bL, 0x65fd6ba7L, 0x7ce65ae6L, 0x57cb0925L, 0x4ed03864L, 0x0191aea3L, 0x188a9fe2L, 0x33a7cc21L, 0x2abcfd60L, 0xad24e1afL, 0xb43fd0eeL, 0x9f12832dL, 0x8609b26cL, 0xc94824abL, 0xd05315eaL, 0xfb7e4629L, 0xe2657768L, 0x2f3f79f6L, 0x362448b7L, 0x1d091b74L, 0x04122a35L, 0x4b53bcf2L, 0x52488db3L, 0x7965de70L, 0x607eef31L, 0xe7e6f3feL, 0xfefdc2bfL, 0xd5d0917cL, 0xcccba03dL, 0x838a36faL, 0x9a9107bbL, 0xb1bc5478L, 0xa8a76539L, 0x3b83984bL, 0x2298a90aL, 0x09b5fac9L, 0x10aecb88L, 0x5fef5d4fL, 0x46f46c0eL, 0x6dd93fcdL, 0x74c20e8cL, 0xf35a1243L, 0xea412302L, 0xc16c70c1L, 0xd8774180L, 0x9736d747L, 0x8e2de606L, 0xa500b5c5L, 0xbc1b8484L, 0x71418a1aL, 0x685abb5bL, 0x4377e898L, 0x5a6cd9d9L, 0x152d4f1eL, 0x0c367e5fL, 0x271b2d9cL, 0x3e001cddL, 0xb9980012L, 0xa0833153L, 0x8bae6290L, 0x92b553d1L, 0xddf4c516L, 0xc4eff457L, 0xefc2a794L, 0xf6d996d5L, 0xae07bce9L, 0xb71c8da8L, 0x9c31de6bL, 0x852aef2aL, 0xca6b79edL, 0xd37048acL, 0xf85d1b6fL, 0xe1462a2eL, 0x66de36e1L, 0x7fc507a0L, 0x54e85463L, 0x4df36522L, 0x02b2f3e5L, 0x1ba9c2a4L, 0x30849167L, 0x299fa026L, 0xe4c5aeb8L, 0xfdde9ff9L, 0xd6f3cc3aL, 0xcfe8fd7bL, 0x80a96bbcL, 0x99b25afdL, 0xb29f093eL, 0xab84387fL, 0x2c1c24b0L, 0x350715f1L, 0x1e2a4632L, 0x07317773L, 0x4870e1b4L, 0x516bd0f5L, 0x7a468336L, 0x635db277L, 0xcbfad74eL, 0xd2e1e60fL, 0xf9ccb5ccL, 0xe0d7848dL, 0xaf96124aL, 0xb68d230bL, 0x9da070c8L, 0x84bb4189L, 0x03235d46L, 0x1a386c07L, 0x31153fc4L, 0x280e0e85L, 0x674f9842L, 0x7e54a903L, 0x5579fac0L, 0x4c62cb81L, 0x8138c51fL, 0x9823f45eL, 0xb30ea79dL, 0xaa1596dcL, 0xe554001bL, 0xfc4f315aL, 0xd7626299L, 0xce7953d8L, 0x49e14f17L, 0x50fa7e56L, 0x7bd72d95L, 0x62cc1cd4L, 0x2d8d8a13L, 0x3496bb52L, 0x1fbbe891L, 0x06a0d9d0L, 0x5e7ef3ecL, 0x4765c2adL, 0x6c48916eL, 0x7553a02fL, 0x3a1236e8L, 0x230907a9L, 0x0824546aL, 0x113f652bL, 0x96a779e4L, 0x8fbc48a5L, 0xa4911b66L, 0xbd8a2a27L, 0xf2cbbce0L, 0xebd08da1L, 0xc0fdde62L, 0xd9e6ef23L, 0x14bce1bdL, 0x0da7d0fcL, 0x268a833fL, 0x3f91b27eL, 0x70d024b9L, 0x69cb15f8L, 0x42e6463bL, 0x5bfd777aL, 0xdc656bb5L, 0xc57e5af4L, 0xee530937L, 0xf7483876L, 0xb809aeb1L, 0xa1129ff0L, 0x8a3fcc33L, 0x9324fd72L , 0x00000000L, 0x01c26a37L, 0x0384d46eL, 0x0246be59L, 0x0709a8dcL, 0x06cbc2ebL, 0x048d7cb2L, 0x054f1685L, 0x0e1351b8L, 0x0fd13b8fL, 0x0d9785d6L, 0x0c55efe1L, 0x091af964L, 0x08d89353L, 0x0a9e2d0aL, 0x0b5c473dL, 0x1c26a370L, 0x1de4c947L, 0x1fa2771eL, 0x1e601d29L, 0x1b2f0bacL, 0x1aed619bL, 0x18abdfc2L, 0x1969b5f5L, 0x1235f2c8L, 0x13f798ffL, 0x11b126a6L, 0x10734c91L, 0x153c5a14L, 0x14fe3023L, 0x16b88e7aL, 0x177ae44dL, 0x384d46e0L, 0x398f2cd7L, 0x3bc9928eL, 0x3a0bf8b9L, 0x3f44ee3cL, 0x3e86840bL, 0x3cc03a52L, 0x3d025065L, 0x365e1758L, 0x379c7d6fL, 0x35dac336L, 0x3418a901L, 0x3157bf84L, 0x3095d5b3L, 0x32d36beaL, 0x331101ddL, 0x246be590L, 0x25a98fa7L, 0x27ef31feL, 0x262d5bc9L, 0x23624d4cL, 0x22a0277bL, 0x20e69922L, 0x2124f315L, 0x2a78b428L, 0x2bbade1fL, 0x29fc6046L, 0x283e0a71L, 0x2d711cf4L, 0x2cb376c3L, 0x2ef5c89aL, 0x2f37a2adL, 0x709a8dc0L, 0x7158e7f7L, 0x731e59aeL, 0x72dc3399L, 0x7793251cL, 0x76514f2bL, 0x7417f172L, 0x75d59b45L, 0x7e89dc78L, 0x7f4bb64fL, 0x7d0d0816L, 0x7ccf6221L, 0x798074a4L, 0x78421e93L, 0x7a04a0caL, 0x7bc6cafdL, 0x6cbc2eb0L, 0x6d7e4487L, 0x6f38fadeL, 0x6efa90e9L, 0x6bb5866cL, 0x6a77ec5bL, 0x68315202L, 0x69f33835L, 0x62af7f08L, 0x636d153fL, 0x612bab66L, 0x60e9c151L, 0x65a6d7d4L, 0x6464bde3L, 0x662203baL, 0x67e0698dL, 0x48d7cb20L, 0x4915a117L, 0x4b531f4eL, 0x4a917579L, 0x4fde63fcL, 0x4e1c09cbL, 0x4c5ab792L, 0x4d98dda5L, 0x46c49a98L, 0x4706f0afL, 0x45404ef6L, 0x448224c1L, 0x41cd3244L, 0x400f5873L, 0x4249e62aL, 0x438b8c1dL, 0x54f16850L, 0x55330267L, 0x5775bc3eL, 0x56b7d609L, 0x53f8c08cL, 0x523aaabbL, 0x507c14e2L, 0x51be7ed5L, 0x5ae239e8L, 0x5b2053dfL, 0x5966ed86L, 0x58a487b1L, 0x5deb9134L, 0x5c29fb03L, 0x5e6f455aL, 0x5fad2f6dL, 0xe1351b80L, 0xe0f771b7L, 0xe2b1cfeeL, 0xe373a5d9L, 0xe63cb35cL, 0xe7fed96bL, 0xe5b86732L, 0xe47a0d05L, 0xef264a38L, 0xeee4200fL, 0xeca29e56L, 0xed60f461L, 0xe82fe2e4L, 0xe9ed88d3L, 0xebab368aL, 0xea695cbdL, 0xfd13b8f0L, 0xfcd1d2c7L, 0xfe976c9eL, 0xff5506a9L, 0xfa1a102cL, 0xfbd87a1bL, 0xf99ec442L, 0xf85cae75L, 0xf300e948L, 0xf2c2837fL, 0xf0843d26L, 0xf1465711L, 0xf4094194L, 0xf5cb2ba3L, 0xf78d95faL, 0xf64fffcdL, 0xd9785d60L, 0xd8ba3757L, 0xdafc890eL, 0xdb3ee339L, 0xde71f5bcL, 0xdfb39f8bL, 0xddf521d2L, 0xdc374be5L, 0xd76b0cd8L, 0xd6a966efL, 0xd4efd8b6L, 0xd52db281L, 0xd062a404L, 0xd1a0ce33L, 0xd3e6706aL, 0xd2241a5dL, 0xc55efe10L, 0xc49c9427L, 0xc6da2a7eL, 0xc7184049L, 0xc25756ccL, 0xc3953cfbL, 0xc1d382a2L, 0xc011e895L, 0xcb4dafa8L, 0xca8fc59fL, 0xc8c97bc6L, 0xc90b11f1L, 0xcc440774L, 0xcd866d43L, 0xcfc0d31aL, 0xce02b92dL, 0x91af9640L, 0x906dfc77L, 0x922b422eL, 0x93e92819L, 0x96a63e9cL, 0x976454abL, 0x9522eaf2L, 0x94e080c5L, 0x9fbcc7f8L, 0x9e7eadcfL, 0x9c381396L, 0x9dfa79a1L, 0x98b56f24L, 0x99770513L, 0x9b31bb4aL, 0x9af3d17dL, 0x8d893530L, 0x8c4b5f07L, 0x8e0de15eL, 0x8fcf8b69L, 0x8a809decL, 0x8b42f7dbL, 0x89044982L, 0x88c623b5L, 0x839a6488L, 0x82580ebfL, 0x801eb0e6L, 0x81dcdad1L, 0x8493cc54L, 0x8551a663L, 0x8717183aL, 0x86d5720dL, 0xa9e2d0a0L, 0xa820ba97L, 0xaa6604ceL, 0xaba46ef9L, 0xaeeb787cL, 0xaf29124bL, 0xad6fac12L, 0xacadc625L, 0xa7f18118L, 0xa633eb2fL, 0xa4755576L, 0xa5b73f41L, 0xa0f829c4L, 0xa13a43f3L, 0xa37cfdaaL, 0xa2be979dL, 0xb5c473d0L, 0xb40619e7L, 0xb640a7beL, 0xb782cd89L, 0xb2cddb0cL, 0xb30fb13bL, 0xb1490f62L, 0xb08b6555L, 0xbbd72268L, 0xba15485fL, 0xb853f606L, 0xb9919c31L, 0xbcde8ab4L, 0xbd1ce083L, 0xbf5a5edaL, 0xbe9834edL , 0x00000000L, 0xb8bc6765L, 0xaa09c88bL, 0x12b5afeeL, 0x8f629757L, 0x37def032L, 0x256b5fdcL, 0x9dd738b9L, 0xc5b428efL, 0x7d084f8aL, 0x6fbde064L, 0xd7018701L, 0x4ad6bfb8L, 0xf26ad8ddL, 0xe0df7733L, 0x58631056L, 0x5019579fL, 0xe8a530faL, 0xfa109f14L, 0x42acf871L, 0xdf7bc0c8L, 0x67c7a7adL, 0x75720843L, 0xcdce6f26L, 0x95ad7f70L, 0x2d111815L, 0x3fa4b7fbL, 0x8718d09eL, 0x1acfe827L, 0xa2738f42L, 0xb0c620acL, 0x087a47c9L, 0xa032af3eL, 0x188ec85bL, 0x0a3b67b5L, 0xb28700d0L, 0x2f503869L, 0x97ec5f0cL, 0x8559f0e2L, 0x3de59787L, 0x658687d1L, 0xdd3ae0b4L, 0xcf8f4f5aL, 0x7733283fL, 0xeae41086L, 0x525877e3L, 0x40edd80dL, 0xf851bf68L, 0xf02bf8a1L, 0x48979fc4L, 0x5a22302aL, 0xe29e574fL, 0x7f496ff6L, 0xc7f50893L, 0xd540a77dL, 0x6dfcc018L, 0x359fd04eL, 0x8d23b72bL, 0x9f9618c5L, 0x272a7fa0L, 0xbafd4719L, 0x0241207cL, 0x10f48f92L, 0xa848e8f7L, 0x9b14583dL, 0x23a83f58L, 0x311d90b6L, 0x89a1f7d3L, 0x1476cf6aL, 0xaccaa80fL, 0xbe7f07e1L, 0x06c36084L, 0x5ea070d2L, 0xe61c17b7L, 0xf4a9b859L, 0x4c15df3cL, 0xd1c2e785L, 0x697e80e0L, 0x7bcb2f0eL, 0xc377486bL, 0xcb0d0fa2L, 0x73b168c7L, 0x6104c729L, 0xd9b8a04cL, 0x446f98f5L, 0xfcd3ff90L, 0xee66507eL, 0x56da371bL, 0x0eb9274dL, 0xb6054028L, 0xa4b0efc6L, 0x1c0c88a3L, 0x81dbb01aL, 0x3967d77fL, 0x2bd27891L, 0x936e1ff4L, 0x3b26f703L, 0x839a9066L, 0x912f3f88L, 0x299358edL, 0xb4446054L, 0x0cf80731L, 0x1e4da8dfL, 0xa6f1cfbaL, 0xfe92dfecL, 0x462eb889L, 0x549b1767L, 0xec277002L, 0x71f048bbL, 0xc94c2fdeL, 0xdbf98030L, 0x6345e755L, 0x6b3fa09cL, 0xd383c7f9L, 0xc1366817L, 0x798a0f72L, 0xe45d37cbL, 0x5ce150aeL, 0x4e54ff40L, 0xf6e89825L, 0xae8b8873L, 0x1637ef16L, 0x048240f8L, 0xbc3e279dL, 0x21e91f24L, 0x99557841L, 0x8be0d7afL, 0x335cb0caL, 0xed59b63bL, 0x55e5d15eL, 0x47507eb0L, 0xffec19d5L, 0x623b216cL, 0xda874609L, 0xc832e9e7L, 0x708e8e82L, 0x28ed9ed4L, 0x9051f9b1L, 0x82e4565fL, 0x3a58313aL, 0xa78f0983L, 0x1f336ee6L, 0x0d86c108L, 0xb53aa66dL, 0xbd40e1a4L, 0x05fc86c1L, 0x1749292fL, 0xaff54e4aL, 0x322276f3L, 0x8a9e1196L, 0x982bbe78L, 0x2097d91dL, 0x78f4c94bL, 0xc048ae2eL, 0xd2fd01c0L, 0x6a4166a5L, 0xf7965e1cL, 0x4f2a3979L, 0x5d9f9697L, 0xe523f1f2L, 0x4d6b1905L, 0xf5d77e60L, 0xe762d18eL, 0x5fdeb6ebL, 0xc2098e52L, 0x7ab5e937L, 0x680046d9L, 0xd0bc21bcL, 0x88df31eaL, 0x3063568fL, 0x22d6f961L, 0x9a6a9e04L, 0x07bda6bdL, 0xbf01c1d8L, 0xadb46e36L, 0x15080953L, 0x1d724e9aL, 0xa5ce29ffL, 0xb77b8611L, 0x0fc7e174L, 0x9210d9cdL, 0x2aacbea8L, 0x38191146L, 0x80a57623L, 0xd8c66675L, 0x607a0110L, 0x72cfaefeL, 0xca73c99bL, 0x57a4f122L, 0xef189647L, 0xfdad39a9L, 0x45115eccL, 0x764dee06L, 0xcef18963L, 0xdc44268dL, 0x64f841e8L, 0xf92f7951L, 0x41931e34L, 0x5326b1daL, 0xeb9ad6bfL, 0xb3f9c6e9L, 0x0b45a18cL, 0x19f00e62L, 0xa14c6907L, 0x3c9b51beL, 0x842736dbL, 0x96929935L, 0x2e2efe50L, 0x2654b999L, 0x9ee8defcL, 0x8c5d7112L, 0x34e11677L, 0xa9362eceL, 0x118a49abL, 0x033fe645L, 0xbb838120L, 0xe3e09176L, 0x5b5cf613L, 0x49e959fdL, 0xf1553e98L, 0x6c820621L, 0xd43e6144L, 0xc68bceaaL, 0x7e37a9cfL, 0xd67f4138L, 0x6ec3265dL, 0x7c7689b3L, 0xc4caeed6L, 0x591dd66fL, 0xe1a1b10aL, 0xf3141ee4L, 0x4ba87981L, 0x13cb69d7L, 0xab770eb2L, 0xb9c2a15cL, 0x017ec639L, 0x9ca9fe80L, 0x241599e5L, 0x36a0360bL, 0x8e1c516eL, 0x866616a7L, 0x3eda71c2L, 0x2c6fde2cL, 0x94d3b949L, 0x090481f0L, 0xb1b8e695L, 0xa30d497bL, 0x1bb12e1eL, 0x43d23e48L, 0xfb6e592dL, 0xe9dbf6c3L, 0x516791a6L, 0xccb0a91fL, 0x740cce7aL, 0x66b96194L, 0xde0506f1L # endif /* IZ_CRCOPTIM_UNFOLDTBL */ # endif /* ? IZ_CRC_BE_OPTIMIZ */ }; #endif /* ?DYNAMIC_CRC_TABLE */ /* use "OF((void))" here to work around a Borland TC++ 1.0 problem */ #ifdef USE_ZLIB ZCONST uLongf *get_crc_table OF((void)) #else ZCONST ulg near *get_crc_table OF((void)) #endif { #ifdef DYNAMIC_CRC_TABLE if (CRC_TABLE_IS_EMPTY) make_crc_table(); #endif #ifdef USE_ZLIB return (ZCONST uLongf *)crc_table; #else return crc_table; #endif } #ifdef DYNALLOC_CRCTAB void free_crc_table() { if (!CRC_TABLE_IS_EMPTY) { nearfree((ulg near *)crc_table); MARK_CRCTAB_EMPTY; } } #endif #ifndef USE_ZLIB #ifndef CRC_TABLE_ONLY #ifndef ASM_CRC #define DO1(crc, buf) crc = CRC32(crc, *buf++, crc_32_tab) #define DO2(crc, buf) DO1(crc, buf); DO1(crc, buf) #define DO4(crc, buf) DO2(crc, buf); DO2(crc, buf) #define DO8(crc, buf) DO4(crc, buf); DO4(crc, buf) #if (defined(IZ_CRC_BE_OPTIMIZ) || defined(IZ_CRC_LE_OPTIMIZ)) # ifdef IZ_CRCOPTIM_UNFOLDTBL # ifdef IZ_CRC_BE_OPTIMIZ # define DO_OPT4(c, buf4) c ^= *(buf4)++; \ c = crc_32_tab[c & 0xff] ^ crc_32_tab[256+((c>>8) & 0xff)] ^ \ crc_32_tab[2*256+((c>>16) & 0xff)] ^ crc_32_tab[3*256+(c>>24)] # else /* !IZ_CRC_BE_OPTIMIZ */ # define DO_OPT4(c, buf4) c ^= *(buf4)++; \ c = crc_32_tab[3*256+(c & 0xff)] ^ crc_32_tab[2*256+((c>>8) & 0xff)] \ ^ crc_32_tab[256+((c>>16) & 0xff)] ^ crc_32_tab[c>>24] # endif /* ?IZ_CRC_BE_OPTIMIZ */ # else /* !IZ_CRCOPTIM_UNFOLDTBL */ # define DO_OPT4(c, buf4) c ^= *(buf4)++; \ c = CRC32UPD(c, crc_32_tab); \ c = CRC32UPD(c, crc_32_tab); \ c = CRC32UPD(c, crc_32_tab); \ c = CRC32UPD(c, crc_32_tab) # endif /* ?IZ_CRCOPTIM_UNFOLDTBL */ # define DO_OPT16(crc, buf4) DO_OPT4(crc, buf4); DO_OPT4(crc, buf4); \ DO_OPT4(crc, buf4); DO_OPT4(crc, buf4); #endif /* (IZ_CRC_BE_OPTIMIZ || IZ_CRC_LE_OPTIMIZ) */ /* ========================================================================= */ ulg crc32(crc, buf, len) ulg crc; /* crc shift register */ register ZCONST uch *buf; /* pointer to bytes to pump through */ extent len; /* number of bytes in buf[] */ /* Run a set of bytes through the crc shift register. If buf is a NULL pointer, then initialize the crc shift register contents instead. Return the current crc in either case. */ { register z_uint4 c; register ZCONST ulg near *crc_32_tab; if (buf == NULL) return 0L; crc_32_tab = get_crc_table(); c = (REV_BE((z_uint4)crc) ^ 0xffffffffL); #if (defined(IZ_CRC_BE_OPTIMIZ) || defined(IZ_CRC_LE_OPTIMIZ)) /* Align buf pointer to next DWORD boundary. */ while (len && ((ptrdiff_t)buf & 3)) { DO1(c, buf); len--; } { ZCONST z_uint4 *buf4 = (ZCONST z_uint4 *)buf; while (len >= 16) { DO_OPT16(c, buf4); len -= 16; } while (len >= 4) { DO_OPT4(c, buf4); len -= 4; } buf = (ZCONST uch *)buf4; } #else /* !(IZ_CRC_BE_OPTIMIZ || IZ_CRC_LE_OPTIMIZ) */ #ifndef NO_UNROLLED_LOOPS while (len >= 8) { DO8(c, buf); len -= 8; } #endif /* !NO_UNROLLED_LOOPS */ #endif /* ?(IZ_CRC_BE_OPTIMIZ || IZ_CRC_LE_OPTIMIZ) */ if (len) do { DO1(c, buf); } while (--len); return REV_BE(c) ^ 0xffffffffL; /* (instead of ~c for 64-bit machines) */ } #endif /* !ASM_CRC */ #endif /* !CRC_TABLE_ONLY */ #endif /* !USE_ZLIB */ #endif /* !USE_ZLIB || USE_OWN_CRCTAB */ zip30/crc32.h0100644000076400000060000000336110773161712011056 0ustar edisk/* Copyright (c) 1990-2008 Info-ZIP. All rights reserved. See the accompanying file LICENSE, version 2000-Apr-09 or later (the contents of which are also included in zip.h) for terms of use. If, for some reason, all these files are missing, the Info-ZIP license also may be found at: ftp://ftp.info-zip.org/pub/infozip/license.html */ /* crc32.h -- compute the CRC-32 of a data stream * Copyright (C) 1995 Mark Adler * For conditions of distribution and use, see copyright notice in zlib.h */ #ifndef __crc32_h #define __crc32_h /* identifies this source module */ /* This header should be read AFTER zip.h resp. unzip.h * (the latter with UNZIP_INTERNAL defined...). */ #ifndef OF # define OF(a) a #endif #ifndef ZCONST # define ZCONST const #endif #ifdef DYNALLOC_CRCTAB void free_crc_table OF((void)); #endif #ifndef USE_ZLIB ZCONST ulg near *get_crc_table OF((void)); #endif #if (defined(USE_ZLIB) || defined(CRC_TABLE_ONLY)) # ifdef IZ_CRC_BE_OPTIMIZ # undef IZ_CRC_BE_OPTIMIZ # endif #else /* !(USE_ZLIB || CRC_TABLE_ONLY) */ ulg crc32 OF((ulg crc, ZCONST uch *buf, extent len)); #endif /* ?(USE_ZLIB || CRC_TABLE_ONLY) */ #ifndef CRC_32_TAB # define CRC_32_TAB crc_32_tab #endif #ifdef CRC32 # undef CRC32 #endif #ifdef IZ_CRC_BE_OPTIMIZ # define CRC32UPD(c, crctab) (crctab[((c) >> 24)] ^ ((c) << 8)) # define CRC32(c, b, crctab) (crctab[(((int)(c) >> 24) ^ (b))] ^ ((c) << 8)) # define REV_BE(w) (((w)>>24)+(((w)>>8)&0xff00)+ \ (((w)&0xff00)<<8)+(((w)&0xff)<<24)) #else # define CRC32UPD(c, crctab) (crctab[((int)(c)) & 0xff] ^ ((c) >> 8)) # define CRC32(c, b, crctab) (crctab[((int)(c) ^ (b)) & 0xff] ^ ((c) >> 8)) # define REV_BE(w) w #endif #endif /* !__crc32_h */ zip30/crc_i386.S0100644000076400000060000002757210547735042011451 0ustar edisk/* Copyright (c) 1990-2007 Info-ZIP. All rights reserved. See the accompanying file LICENSE, version 2000-Apr-09 or later (the contents of which are also included in zip.h) for terms of use. If, for some reason, all these files are missing, the Info-ZIP license also may be found at: ftp://ftp.info-zip.org/pub/infozip/license.html */ /* * crc_i386.S, optimized CRC calculation function for Zip and UnZip, * created by Paul Kienitz and Christian Spieler. Last revised 07 Jan 2007. * * GRR 961110: incorporated Scott Field optimizations from win32/crc_i386.asm * => overall 6% speedup in "unzip -tq" on 9MB zipfile (486-66) * * SPC 970402: revised for Rodney Brown's optimizations (32-bit-wide * aligned reads for most of the data from buffer), can be * disabled by defining the macro NO_32_BIT_LOADS * * SPC 971012: added Rodney Brown's additional tweaks for 32-bit-optimized * CPUs (like the Pentium Pro, Pentium II, and probably some * Pentium clones). This optimization is controlled by the * preprocessor switch "__686" and is disabled by default. * (This default is based on the assumption that most users * do not yet work on a Pentium Pro or Pentium II machine ...) * * COS 050116: Enabled the 686 build by default, because there are hardly any * pre-686 CPUs in serious use nowadays. (See SPC 970402 above.) * * SPC 060103: Updated code to incorporate newer optimizations found in zlib. * * SPC 070107: Added conditional switch to deactivate crc32() compilation. * * FLAT memory model assumed. Calling interface: * - args are pushed onto the stack from right to left, * - return value is given in the EAX register, * - all other registers (with exception of EFLAGS) are preserved. (With * GNU C 2.7.x, %edx and %ecx are `scratch' registers, but preserving * them nevertheless adds only 4 single byte instructions.) * * This source generates the function * ulg crc32(ulg crc, ZCONST uch *buf, extent len). * * Loop unrolling can be disabled by defining the macro NO_UNROLLED_LOOPS. * This results in shorter code at the expense of reduced performance. */ /* This file is NOT used in conjunction with zlib, or when only creation of * the basic CRC_32_Table (for other purpose) is requested. */ #if !defined(USE_ZLIB) && !defined(CRC_TABLE_ONLY) /* Preprocess with -DNO_UNDERLINE if your C compiler does not prefix * external symbols with an underline character '_'. */ #if defined(NO_UNDERLINE) || defined(__ELF__) # define _crc32 crc32 # define _get_crc_table get_crc_table #endif /* Use 16-byte alignment if your assembler supports it. Warning: gas * uses a log(x) parameter (.align 4 means 16-byte alignment). On SVR4 * the parameter is a number of bytes. */ #ifndef ALIGNMENT # define ALIGNMENT .align 4,0x90 #endif #if defined(i386) || defined(_i386) || defined(_I386) || defined(__i386) /* This version is for 386 Unix, OS/2, MSDOS in 32 bit mode (gcc & gas). * Warning: it uses the AT&T syntax: mov source,dest * This file is only optional. If you want to use the C version, * remove -DASM_CRC from CFLAGS in Makefile and set OBJA to an empty string. */ .file "crc_i386.S" #if !defined(PRE_686) && !defined(__686) /* Optimize for Pentium Pro and compatible CPUs by default. */ # define __686 #endif #if defined(NO_STD_STACKFRAME) && defined(USE_STD_STACKFRAME) # undef USE_STACKFRAME #else /* The default is to use standard stack frame entry, because it * results in smaller code! */ # ifndef USE_STD_STACKFRAME # define USE_STD_STACKFRAME # endif #endif #ifdef USE_STD_STACKFRAME # define _STD_ENTRY pushl %ebp ; movl %esp,%ebp # define arg1 8(%ebp) # define arg2 12(%ebp) # define arg3 16(%ebp) # define _STD_LEAVE popl %ebp #else /* !USE_STD_STACKFRAME */ # define _STD_ENTRY # define arg1 24(%esp) # define arg2 28(%esp) # define arg3 32(%esp) # define _STD_LEAVE #endif /* ?USE_STD_STACKFRAME */ /* * These two (three) macros make up the loop body of the CRC32 cruncher. * registers modified: * eax : crc value "c" * esi : pointer to next data byte (or lword) "buf++" * registers read: * edi : pointer to base of crc_table array * scratch registers: * ebx : index into crc_table array * (requires upper three bytes = 0 when __686 is undefined) */ #ifndef __686 /* optimize for 386, 486, Pentium */ #define Do_CRC /* c = (c >> 8) ^ table[c & 0xFF] */\ movb %al, %bl ;/* tmp = c & 0xFF */\ shrl $8, %eax ;/* c = (c >> 8) */\ xorl (%edi, %ebx, 4), %eax ;/* c ^= table[tmp] */ #else /* __686 : optimize for Pentium Pro and compatible CPUs */ #define Do_CRC /* c = (c >> 8) ^ table[c & 0xFF] */\ movzbl %al, %ebx ;/* tmp = c & 0xFF */\ shrl $8, %eax ;/* c = (c >> 8) */\ xorl (%edi, %ebx, 4), %eax ;/* c ^=table[tmp] */ #endif /* ?__686 */ #define Do_CRC_byte /* c = (c >> 8) ^ table[(c^*buf++)&0xFF] */\ xorb (%esi), %al ;/* c ^= *buf */\ incl %esi ;/* buf++ */\ Do_CRC #define Do_CRC_byteof(ofs) /* c = (c >> 8) ^ table[(c^*buf++)&0xFF] */\ xorb ofs(%esi), %al ;/* c ^= *buf */\ incl %esi ;/* buf++ */\ Do_CRC #ifndef NO_32_BIT_LOADS # ifdef IZ_CRCOPTIM_UNFOLDTBL /* the edx register is needed in crc calculation */ # define SavLen arg3 # define UpdCRC_lword \ movzbl %al, %ebx ; \ movl 3072(%edi,%ebx,4), %edx ; \ movzbl %ah, %ebx ; \ shrl $16, %eax ; \ xor 2048(%edi,%ebx,4), %edx ; \ movzbl %al, %ebx ; \ shrl $8,%eax ; \ xorl 1024(%edi,%ebx,4), %edx ; \ movl (%edi,%eax,4), %eax ; \ xorl %edx,%eax ; # define UpdCRC_lword_sh(dwPtrIncr) \ movzbl %al, %ebx ; \ movl 3072(%edi,%ebx,4), %edx ; \ movzbl %ah, %ebx ; \ shrl $16, %eax ; \ xor 2048(%edi,%ebx,4), %edx ; \ movzbl %al, %ebx ; \ addl $4*(dwPtrIncr), %esi ;/* ((ulg *)buf)+=dwPtrIncr */\ shrl $8,%eax ; \ xorl 1024(%edi,%ebx,4), %edx ; \ movl (%edi,%eax,4),%eax ; \ xorl %edx,%eax ; # else /* !IZ_CRCOPTIM_UNFOLDTBL */ /* the edx register is not needed anywhere else */ # define SavLen %edx # define UpdCRC_lword \ Do_CRC \ Do_CRC \ Do_CRC \ Do_CRC # define UpdCRC_lword_sh(dwPtrIncr) \ Do_CRC \ Do_CRC \ addl $4*(dwPtrIncr), %esi ;/* ((ulg *)buf)++ */\ Do_CRC \ Do_CRC # endif /* ?IZ_CRCOPTIM_UNFOLDTBL */ #define Do_CRC_lword \ xorl (%esi), %eax ;/* c ^= *(ulg *)buf */\ UpdCRC_lword_sh(1) /* ... ((ulg *)buf)++ */ #define Do_CRC_4lword \ xorl (%esi), %eax ;/* c ^= *(ulg *)buf */\ UpdCRC_lword \ xorl 4(%esi), %eax ;/* c ^= *((ulg *)buf+1) */\ UpdCRC_lword \ xorl 8(%esi), %eax ;/* c ^= *((ulg *)buf+2) */\ UpdCRC_lword \ xorl 12(%esi), %eax ;/* c ^= *((ulg *)buf]+3 */\ UpdCRC_lword_sh(4) /* ... ((ulg *)buf)+=4 */ #endif /* !NO_32_BIT_LOADS */ .text .globl _crc32 _crc32: /* ulg crc32(ulg crc, uch *buf, extent len) */ _STD_ENTRY pushl %edi pushl %esi pushl %ebx pushl %edx pushl %ecx movl arg2, %esi /* 2nd arg: uch *buf */ subl %eax, %eax /* > if (!buf) */ testl %esi, %esi /* > return 0; */ jz .L_fine /* > else { */ call _get_crc_table movl %eax, %edi movl arg1, %eax /* 1st arg: ulg crc */ #ifndef __686 subl %ebx, %ebx /* ebx=0; bl usable as dword */ #endif movl arg3, %ecx /* 3rd arg: extent len */ notl %eax /* > c = ~crc; */ testl %ecx, %ecx #ifndef NO_UNROLLED_LOOPS jz .L_bail # ifndef NO_32_BIT_LOADS /* Assert now have positive length */ .L_align_loop: testl $3, %esi /* Align buf on lword boundary */ jz .L_aligned_now Do_CRC_byte decl %ecx jnz .L_align_loop .L_aligned_now: # endif /* !NO_32_BIT_LOADS */ movl %ecx, SavLen /* save current value of len */ shrl $4, %ecx /* ecx = len / 16 */ jz .L_No_Sixteens /* align loop head at start of 486 internal cache line !! */ ALIGNMENT .L_Next_Sixteen: # ifndef NO_32_BIT_LOADS Do_CRC_4lword # else /* NO_32_BIT_LOADS */ Do_CRC_byteof(0) Do_CRC_byteof(1) Do_CRC_byteof(2) Do_CRC_byteof(3) Do_CRC_byteof(4) Do_CRC_byteof(5) Do_CRC_byteof(6) Do_CRC_byteof(7) Do_CRC_byteof(8) Do_CRC_byteof(9) Do_CRC_byteof(10) Do_CRC_byteof(11) Do_CRC_byteof(12) Do_CRC_byteof(13) Do_CRC_byteof(14) Do_CRC_byteof(15) addl $16,%esi ;/* buf += 16 */ # endif /* ?NO_32_BIT_LOADS */ decl %ecx jnz .L_Next_Sixteen .L_No_Sixteens: movl SavLen, %ecx andl $15, %ecx /* ecx = len % 16 */ # ifndef NO_32_BIT_LOADS shrl $2,%ecx /* ecx = len / 4 */ jz .L_No_Fours .L_Next_Four: Do_CRC_lword decl %ecx jnz .L_Next_Four .L_No_Fours: movl SavLen,%ecx andl $3,%ecx /* ecx = len % 4 */ # endif /* !NO_32_BIT_LOADS */ #endif /* !NO_UNROLLED_LOOPS */ jz .L_bail /* > if (len) */ /* align loop head at start of 486 internal cache line !! */ ALIGNMENT .L_loupe: /* > do { */ Do_CRC_byte /* c = CRC32(c,*buf++,crctab);*/ decl %ecx /* > } while (--len); */ jnz .L_loupe .L_bail: /* > } */ notl %eax /* > return ~c; */ .L_fine: popl %ecx popl %edx popl %ebx popl %esi popl %edi _STD_LEAVE ret #else error: this asm version is for 386 only #endif /* i386 || _i386 || _I386 || __i386 */ #endif /* !USE_ZLIB && !CRC_TABLE_ONLY */ zip30/crypt.c0100644000076400000060000005416511007364634011305 0ustar edisk/* Copyright (c) 1990-2008 Info-ZIP. All rights reserved. See the accompanying file LICENSE, version 2007-Mar-4 or later (the contents of which are also included in zip.h) for terms of use. If, for some reason, all these files are missing, the Info-ZIP license also may be found at: ftp://ftp.info-zip.org/pub/infozip/license.html */ /* crypt.c (full version) by Info-ZIP. Last revised: [see crypt.h] The main encryption/decryption source code for Info-Zip software was originally written in Europe. To the best of our knowledge, it can be freely distributed in both source and object forms from any country, including the USA under License Exception TSU of the U.S. Export Administration Regulations (section 740.13(e)) of 6 June 2002. NOTE on copyright history: Previous versions of this source package (up to version 2.8) were not copyrighted and put in the public domain. If you cannot comply with the Info-Zip LICENSE, you may want to look for one of those public domain versions. */ /* This encryption code is a direct transcription of the algorithm from Roger Schlafly, described by Phil Katz in the file appnote.txt. This file (appnote.txt) is distributed with the PKZIP program (even in the version without encryption capabilities). */ #define ZCRYPT_INTERNAL #include "zip.h" #include "crypt.h" #include "ttyio.h" #if CRYPT #ifndef FALSE # define FALSE 0 #endif #ifdef ZIP /* For the encoding task used in Zip (and ZipCloak), we want to initialize the crypt algorithm with some reasonably unpredictable bytes, see the crypthead() function. The standard rand() library function is used to supply these `random' bytes, which in turn is initialized by a srand() call. The srand() function takes an "unsigned" (at least 16bit) seed value as argument to determine the starting point of the rand() pseudo-random number generator. This seed number is constructed as "Seed = Seed1 .XOR. Seed2" with Seed1 supplied by the current time (= "(unsigned)time()") and Seed2 as some (hopefully) nondeterministic bitmask. On many (most) systems, we use some "process specific" number, as the PID or something similar, but when nothing unpredictable is available, a fixed number may be sufficient. NOTE: 1.) This implementation requires the availability of the following standard UNIX C runtime library functions: time(), rand(), srand(). On systems where some of them are missing, the environment that incorporates the crypt routines must supply suitable replacement functions. 2.) It is a very bad idea to use a second call to time() to set the "Seed2" number! In this case, both "Seed1" and "Seed2" would be (almost) identical, resulting in a (mostly) "zero" constant seed number passed to srand(). The implementation environment defined in the "zip.h" header should supply a reasonable definition for ZCR_SEED2 (an unsigned number; for most implementations of rand() and srand(), only the lower 16 bits are significant!). An example that works on many systems would be "#define ZCR_SEED2 (unsigned)getpid()". The default definition for ZCR_SEED2 supplied below should be regarded as a fallback to allow successful compilation in "beta state" environments. */ # include /* time() function supplies first part of crypt seed */ /* "last resort" source for second part of crypt seed pattern */ # ifndef ZCR_SEED2 # define ZCR_SEED2 (unsigned)3141592654L /* use PI as default pattern */ # endif # ifdef GLOBAL /* used in Amiga system headers, maybe others too */ # undef GLOBAL # endif # define GLOBAL(g) g #else /* !ZIP */ # define GLOBAL(g) G.g #endif /* ?ZIP */ #ifdef UNZIP /* char *key = (char *)NULL; moved to globals.h */ # ifndef FUNZIP local int testp OF((__GPRO__ ZCONST uch *h)); local int testkey OF((__GPRO__ ZCONST uch *h, ZCONST char *key)); # endif #else /* def UNZIP */ /* moved to globals.h for UnZip */ local z_uint4 keys[3]; /* keys defining the pseudo-random sequence */ #endif /* def UNZIP [else] */ #ifndef Trace # ifdef CRYPT_DEBUG # define Trace(x) fprintf x # else # define Trace(x) # endif #endif #include "crc32.h" #ifdef IZ_CRC_BE_OPTIMIZ local z_uint4 near crycrctab[256]; local z_uint4 near *cry_crctb_p = NULL; local z_uint4 near *crytab_init OF((__GPRO)); # define CRY_CRC_TAB cry_crctb_p # undef CRC32 # define CRC32(c, b, crctab) (crctab[((int)(c) ^ (b)) & 0xff] ^ ((c) >> 8)) #else # define CRY_CRC_TAB CRC_32_TAB #endif /* ?IZ_CRC_BE_OPTIMIZ */ /*********************************************************************** * Return the next byte in the pseudo-random sequence */ int decrypt_byte(__G) __GDEF { unsigned temp; /* POTENTIAL BUG: temp*(temp^1) may overflow in an * unpredictable manner on 16-bit systems; not a problem * with any known compiler so far, though */ temp = ((unsigned)GLOBAL(keys[2]) & 0xffff) | 2; return (int)(((temp * (temp ^ 1)) >> 8) & 0xff); } /*********************************************************************** * Update the encryption keys with the next byte of plain text */ int update_keys(__G__ c) __GDEF int c; /* byte of plain text */ { GLOBAL(keys[0]) = CRC32(GLOBAL(keys[0]), c, CRY_CRC_TAB); GLOBAL(keys[1]) = (GLOBAL(keys[1]) + (GLOBAL(keys[0]) & 0xff)) * 134775813L + 1; { register int keyshift = (int)(GLOBAL(keys[1]) >> 24); GLOBAL(keys[2]) = CRC32(GLOBAL(keys[2]), keyshift, CRY_CRC_TAB); } return c; } /*********************************************************************** * Initialize the encryption keys and the random header according to * the given password. */ void init_keys(__G__ passwd) __GDEF ZCONST char *passwd; /* password string with which to modify keys */ { #ifdef IZ_CRC_BE_OPTIMIZ if (cry_crctb_p == NULL) { cry_crctb_p = crytab_init(__G); } #endif GLOBAL(keys[0]) = 305419896L; GLOBAL(keys[1]) = 591751049L; GLOBAL(keys[2]) = 878082192L; while (*passwd != '\0') { update_keys(__G__ (int)*passwd); passwd++; } } /*********************************************************************** * Initialize the local copy of the table of precomputed crc32 values. * Whereas the public crc32-table is optimized for crc32 calculations * on arrays of bytes, the crypt code needs the crc32 values in an * byte-order-independent form as 32-bit unsigned numbers. On systems * with Big-Endian byte order using the optimized crc32 code, this * requires inverting the byte-order of the values in the * crypt-crc32-table. */ #ifdef IZ_CRC_BE_OPTIMIZ local z_uint4 near *crytab_init(__G) __GDEF { int i; for (i = 0; i < 256; i++) { crycrctab[i] = REV_BE(CRC_32_TAB[i]); } return crycrctab; } #endif #ifdef ZIP /*********************************************************************** * Write encryption header to file zfile using the password passwd * and the cyclic redundancy check crc. */ void crypthead(passwd, crc) ZCONST char *passwd; /* password string */ ulg crc; /* crc of file being encrypted */ { int n; /* index in random header */ int t; /* temporary */ int c; /* random byte */ uch header[RAND_HEAD_LEN]; /* random header */ static unsigned calls = 0; /* ensure different random header each time */ /* First generate RAND_HEAD_LEN-2 random bytes. We encrypt the * output of rand() to get less predictability, since rand() is * often poorly implemented. */ if (++calls == 1) { srand((unsigned)time(NULL) ^ ZCR_SEED2); } init_keys(passwd); for (n = 0; n < RAND_HEAD_LEN-2; n++) { c = (rand() >> 7) & 0xff; header[n] = (uch)zencode(c, t); } /* Encrypt random header (last two bytes is high word of crc) */ init_keys(passwd); for (n = 0; n < RAND_HEAD_LEN-2; n++) { header[n] = (uch)zencode(header[n], t); } header[RAND_HEAD_LEN-2] = (uch)zencode((int)(crc >> 16) & 0xff, t); header[RAND_HEAD_LEN-1] = (uch)zencode((int)(crc >> 24) & 0xff, t); bfwrite(header, 1, RAND_HEAD_LEN, BFWRITE_DATA); } #ifdef UTIL /*********************************************************************** * Encrypt the zip entry described by z from file in_file to file y * using the password passwd. Return an error code in the ZE_ class. */ int zipcloak(z, passwd) struct zlist far *z; /* zip entry to encrypt */ ZCONST char *passwd; /* password string */ { int c; /* input byte */ int res; /* result code */ zoff_t n; /* holds offset and counts size */ int t; /* temporary */ struct zlist far *localz; /* local header */ uch buf[1024]; /* write buffer */ int b; /* bytes in buffer */ /* Set encrypted bit, clear extended local header bit and write local header to output file */ if ((n = (zoff_t)zftello(y)) == (zoff_t)-1L) return ZE_TEMP; /* assume this archive is one disk and the file is open */ /* read the local header */ res = readlocal(&localz, z); /* update disk and offset */ z->dsk = 0; z->off = n; /* Set encryption and unset any extended local header */ z->flg |= 1, z->flg &= ~8; localz->lflg |= 1, localz->lflg &= ~8; /* Add size of encryption header */ localz->siz += RAND_HEAD_LEN; z->siz = localz->siz; /* Put the local header */ if ((res = putlocal(localz, PUTLOCAL_WRITE)) != ZE_OK) return res; /* Initialize keys with password and write random header */ crypthead(passwd, localz->crc); /* Encrypt data */ b = 0; for (n = z->siz - RAND_HEAD_LEN; n; n--) { if ((c = getc(in_file)) == EOF) { return ferror(in_file) ? ZE_READ : ZE_EOF; } buf[b] = (uch)zencode(c, t); b++; if (b >= 1024) { /* write the buffer */ bfwrite(buf, 1, b, BFWRITE_DATA); b = 0; } } if (b) { /* write the buffer */ bfwrite(buf, 1, b, BFWRITE_DATA); b = 0; } /* Since we seek to the start of each local header can skip reading any extended local header */ /* if ((flag & 8) != 0 && zfseeko(in_file, 16L, SEEK_CUR)) { return ferror(in_file) ? ZE_READ : ZE_EOF; } if (fflush(y) == EOF) return ZE_TEMP; */ /* Update number of bytes written to output file */ tempzn += (4 + LOCHEAD) + localz->nam + localz->ext + localz->siz; /* Free local header */ if (localz->ext) free(localz->extra); if (localz->nam) free(localz->iname); if (localz->nam) free(localz->name); #ifdef UNICODE_SUPPORT if (localz->uname) free(localz->uname); #endif free(localz); return ZE_OK; } /*********************************************************************** * Decrypt the zip entry described by z from file in_file to file y * using the password passwd. Return an error code in the ZE_ class. */ int zipbare(z, passwd) struct zlist far *z; /* zip entry to encrypt */ ZCONST char *passwd; /* password string */ { #ifdef ZIP10 int c0 /* byte preceding the last input byte */ #endif int c1; /* last input byte */ /* all file offset and size now zoff_t - 8/28/04 EG */ zoff_t size; /* size of input data */ struct zlist far *localz; /* local header */ uch buf[1024]; /* write buffer */ int b; /* bytes in buffer */ zoff_t n; int r; /* size of encryption header */ int res; /* return code */ /* Save position */ if ((n = (zoff_t)zftello(y)) == (zoff_t)-1L) return ZE_TEMP; /* Read local header */ res = readlocal(&localz, z); /* Update disk and offset */ z->dsk = 0; z->off = n; /* Initialize keys with password */ init_keys(passwd); /* Decrypt encryption header, save last two bytes */ c1 = 0; for (r = RAND_HEAD_LEN; r; r--) { #ifdef ZIP10 c0 = c1; #endif if ((c1 = getc(in_file)) == EOF) { return ferror(in_file) ? ZE_READ : ZE_EOF; } Trace((stdout, " (%02x)", c1)); zdecode(c1); Trace((stdout, " %02x", c1)); } Trace((stdout, "\n")); /* If last two bytes of header don't match crc (or file time in the * case of an extended local header), back up and just copy. For * pkzip 2.0, the check has been reduced to one byte only. */ #ifdef ZIP10 if ((ush)(c0 | (c1<<8)) != (z->flg & 8 ? (ush) z->tim & 0xffff : (ush)(z->crc >> 16))) { #else if ((ush)c1 != (z->flg & 8 ? (ush) z->tim >> 8 : (ush)(z->crc >> 24))) { #endif if (zfseeko(in_file, n, SEEK_SET)) { return ferror(in_file) ? ZE_READ : ZE_EOF; } if ((res = zipcopy(z)) != ZE_OK) { ziperr(res, "was copying an entry"); } return ZE_MISS; } z->siz -= RAND_HEAD_LEN; localz->siz = z->siz; localz->flg = z->flg &= ~9; z->lflg = localz->lflg &= ~9; if ((res = putlocal(localz, PUTLOCAL_WRITE)) != ZE_OK) return res; /* Decrypt data */ b = 0; for (size = z->siz; size; size--) { if ((c1 = getc(in_file)) == EOF) { return ferror(in_file) ? ZE_READ : ZE_EOF; } zdecode(c1); buf[b] = c1; b++; if (b >= 1024) { /* write the buffer */ bfwrite(buf, 1, b, BFWRITE_DATA); b = 0; } } if (b) { /* write the buffer */ bfwrite(buf, 1, b, BFWRITE_DATA); b = 0; } /* Since we seek to the start of each local header can skip reading any extended local header */ /* Update number of bytes written to output file */ tempzn += (4 + LOCHEAD) + localz->nam + localz->ext + localz->siz; /* Free local header */ if (localz->ext) free(localz->extra); if (localz->nam) free(localz->iname); if (localz->nam) free(localz->name); #ifdef UNICODE_SUPPORT if (localz->uname) free(localz->uname); #endif free(localz); return ZE_OK; } #else /* !UTIL */ /*********************************************************************** * If requested, encrypt the data in buf, and in any case call fwrite() * with the arguments to zfwrite(). Return what fwrite() returns. * * now write to global y * * A bug has been found when encrypting large files that don't * compress. See trees.c for the details and the fix. */ unsigned zfwrite(buf, item_size, nb) zvoid *buf; /* data buffer */ extent item_size; /* size of each item in bytes */ extent nb; /* number of items */ #if 0 FILE *f; /* file to write to */ #endif { int t; /* temporary */ if (key != (char *)NULL) { /* key is the global password pointer */ ulg size; /* buffer size */ char *p = (char *)buf; /* steps through buffer */ /* Encrypt data in buffer */ for (size = item_size*(ulg)nb; size != 0; p++, size--) { *p = (char)zencode(*p, t); } } /* Write the buffer out */ return bfwrite(buf, item_size, nb, BFWRITE_DATA); } #endif /* ?UTIL */ #endif /* ZIP */ #if (defined(UNZIP) && !defined(FUNZIP)) /*********************************************************************** * Get the password and set up keys for current zipfile member. * Return PK_ class error. */ int decrypt(__G__ passwrd) __GDEF ZCONST char *passwrd; { ush b; int n, r; uch h[RAND_HEAD_LEN]; Trace((stdout, "\n[incnt = %d]: ", GLOBAL(incnt))); /* get header once (turn off "encrypted" flag temporarily so we don't * try to decrypt the same data twice) */ GLOBAL(pInfo->encrypted) = FALSE; defer_leftover_input(__G); for (n = 0; n < RAND_HEAD_LEN; n++) { b = NEXTBYTE; h[n] = (uch)b; Trace((stdout, " (%02x)", h[n])); } undefer_input(__G); GLOBAL(pInfo->encrypted) = TRUE; if (GLOBAL(newzip)) { /* this is first encrypted member in this zipfile */ GLOBAL(newzip) = FALSE; if (passwrd != (char *)NULL) { /* user gave password on command line */ if (!GLOBAL(key)) { if ((GLOBAL(key) = (char *)malloc(strlen(passwrd)+1)) == (char *)NULL) return PK_MEM2; strcpy(GLOBAL(key), passwrd); GLOBAL(nopwd) = TRUE; /* inhibit password prompting! */ } } else if (GLOBAL(key)) { /* get rid of previous zipfile's key */ free(GLOBAL(key)); GLOBAL(key) = (char *)NULL; } } /* if have key already, test it; else allocate memory for it */ if (GLOBAL(key)) { if (!testp(__G__ h)) return PK_COOL; /* existing password OK (else prompt for new) */ else if (GLOBAL(nopwd)) return PK_WARN; /* user indicated no more prompting */ } else if ((GLOBAL(key) = (char *)malloc(IZ_PWLEN+1)) == (char *)NULL) return PK_MEM2; /* try a few keys */ n = 0; do { r = (*G.decr_passwd)((zvoid *)&G, &n, GLOBAL(key), IZ_PWLEN+1, GLOBAL(zipfn), GLOBAL(filename)); if (r == IZ_PW_ERROR) { /* internal error in fetch of PW */ free (GLOBAL(key)); GLOBAL(key) = NULL; return PK_MEM2; } if (r != IZ_PW_ENTERED) { /* user replied "skip" or "skip all" */ *GLOBAL(key) = '\0'; /* We try the NIL password, ... */ n = 0; /* and cancel fetch for this item. */ } if (!testp(__G__ h)) return PK_COOL; if (r == IZ_PW_CANCELALL) /* User replied "Skip all" */ GLOBAL(nopwd) = TRUE; /* inhibit any further PW prompt! */ } while (n > 0); return PK_WARN; } /* end function decrypt() */ /*********************************************************************** * Test the password. Return -1 if bad, 0 if OK. */ local int testp(__G__ h) __GDEF ZCONST uch *h; { int r; char *key_translated; /* On systems with "obscure" native character coding (e.g., EBCDIC), * the first test translates the password to the "main standard" * character coding. */ #ifdef STR_TO_CP1 /* allocate buffer for translated password */ if ((key_translated = malloc(strlen(GLOBAL(key)) + 1)) == (char *)NULL) return -1; /* first try, test password translated "standard" charset */ r = testkey(__G__ h, STR_TO_CP1(key_translated, GLOBAL(key))); #else /* !STR_TO_CP1 */ /* first try, test password as supplied on the extractor's host */ r = testkey(__G__ h, GLOBAL(key)); #endif /* ?STR_TO_CP1 */ #ifdef STR_TO_CP2 if (r != 0) { #ifndef STR_TO_CP1 /* now prepare for second (and maybe third) test with translated pwd */ if ((key_translated = malloc(strlen(GLOBAL(key)) + 1)) == (char *)NULL) return -1; #endif /* second try, password translated to alternate ("standard") charset */ r = testkey(__G__ h, STR_TO_CP2(key_translated, GLOBAL(key))); #ifdef STR_TO_CP3 if (r != 0) /* third try, password translated to another "standard" charset */ r = testkey(__G__ h, STR_TO_CP3(key_translated, GLOBAL(key))); #endif #ifndef STR_TO_CP1 free(key_translated); #endif } #endif /* STR_TO_CP2 */ #ifdef STR_TO_CP1 free(key_translated); if (r != 0) { /* last resort, test password as supplied on the extractor's host */ r = testkey(__G__ h, GLOBAL(key)); } #endif /* STR_TO_CP1 */ return r; } /* end function testp() */ local int testkey(__G__ h, key) __GDEF ZCONST uch *h; /* decrypted header */ ZCONST char *key; /* decryption password to test */ { ush b; #ifdef ZIP10 ush c; #endif int n; uch *p; uch hh[RAND_HEAD_LEN]; /* decrypted header */ /* set keys and save the encrypted header */ init_keys(__G__ key); memcpy(hh, h, RAND_HEAD_LEN); /* check password */ for (n = 0; n < RAND_HEAD_LEN; n++) { zdecode(hh[n]); Trace((stdout, " %02x", hh[n])); } /* use fzofft to format zoff_t as strings - 10/19/04 from SMS */ Trace((stdout, "\n lrec.crc= %08lx crec.crc= %08lx pInfo->ExtLocHdr= %s\n", GLOBAL(lrec.crc32), GLOBAL(pInfo->crc), GLOBAL(pInfo->ExtLocHdr) ? "true":"false")); Trace((stdout, " incnt = %d unzip offset into zipfile = %s\n", GLOBAL(incnt), fzofft(GLOBAL(cur_zipfile_bufstart)+(GLOBAL(inptr)-GLOBAL(inbuf)), NULL, NULL))); /* same test as in zipbare(): */ #ifdef ZIP10 /* check two bytes */ c = hh[RAND_HEAD_LEN-2], b = hh[RAND_HEAD_LEN-1]; Trace((stdout, " (c | (b<<8)) = %04x (crc >> 16) = %04x lrec.time = %04x\n", (ush)(c | (b<<8)), (ush)(GLOBAL(lrec.crc32) >> 16), ((ush)GLOBAL(lrec.last_mod_dos_datetime) & 0xffff)))); if ((ush)(c | (b<<8)) != (GLOBAL(pInfo->ExtLocHdr) ? ((ush)GLOBAL(lrec.last_mod_dos_datetime) & 0xffff) : (ush)(GLOBAL(lrec.crc32) >> 16))) return -1; /* bad */ #else b = hh[RAND_HEAD_LEN-1]; Trace((stdout, " b = %02x (crc >> 24) = %02x (lrec.time >> 8) = %02x\n", b, (ush)(GLOBAL(lrec.crc32) >> 24), ((ush)GLOBAL(lrec.last_mod_dos_datetime) >> 8) & 0xff)); if (b != (GLOBAL(pInfo->ExtLocHdr) ? ((ush)GLOBAL(lrec.last_mod_dos_datetime) >> 8) & 0xff : (ush)(GLOBAL(lrec.crc32) >> 24))) return -1; /* bad */ #endif /* password OK: decrypt current buffer contents before leaving */ for (n = (zoff_t)GLOBAL(incnt) > GLOBAL(csize) ? (int)GLOBAL(csize) : GLOBAL(incnt), p = GLOBAL(inptr); n--; p++) zdecode(*p); return 0; /* OK */ } /* end function testkey() */ #endif /* UNZIP && !FUNZIP */ #else /* !CRYPT */ /* something "externally visible" to shut up compiler/linker warnings */ int zcr_dummy; #endif /* ?CRYPT */ zip30/crypt.h0100644000076400000060000001117310602132644011274 0ustar edisk/* Copyright (c) 1990-2007 Info-ZIP. All rights reserved. See the accompanying file LICENSE, version 2007-Mar-4 or later (the contents of which are also included in zip.h) for terms of use. If, for some reason, all these files are missing, the Info-ZIP license also may be found at: ftp://ftp.info-zip.org/pub/infozip/license.html */ /* crypt.h (full version) by Info-ZIP. Last revised: [see CR_VERSION_DATE] The main encryption/decryption source code for Info-Zip software was originally written in Europe. To the best of our knowledge, it can be freely distributed in both source and object forms from any country, including the USA under License Exception TSU of the U.S. Export Administration Regulations (section 740.13(e)) of 6 June 2002. NOTE on copyright history: Previous versions of this source package (up to version 2.8) were not copyrighted and put in the public domain. If you cannot comply with the Info-Zip LICENSE, you may want to look for one of those public domain versions. */ #ifndef __crypt_h /* don't include more than once */ #define __crypt_h #ifdef CRYPT # undef CRYPT #endif /* Logic of selecting "full crypt" code: a) default behaviour: - dummy crypt code when compiling UnZipSFX stub, to minimize size - full crypt code when used to compile Zip, UnZip and fUnZip b) USE_CRYPT defined: - always full crypt code c) NO_CRYPT defined: - never full crypt code NO_CRYPT takes precedence over USE_CRYPT */ #if defined(NO_CRYPT) # define CRYPT 0 /* dummy version */ #else #if defined(USE_CRYPT) # define CRYPT 1 /* full version */ #else #if !defined(SFX) # define CRYPT 1 /* full version for zip and main unzip */ #else # define CRYPT 0 /* dummy version for unzip sfx */ #endif #endif /* ?USE_CRYPT */ #endif /* ?NO_CRYPT */ #if CRYPT /* full version */ #ifdef CR_BETA # undef CR_BETA /* this is not a beta release */ #endif #define CR_MAJORVER 2 #define CR_MINORVER 91 #ifdef CR_BETA # define CR_BETA_VER "c BETA" # define CR_VERSION_DATE "05 Jan 2007" /* last real code change */ #else # define CR_BETA_VER "" # define CR_VERSION_DATE "05 Jan 2007" /* last public release date */ # define CR_RELEASE #endif #ifndef __G /* UnZip only, for now (DLL stuff) */ # define __G # define __G__ # define __GDEF # define __GPRO void # define __GPRO__ #endif #if defined(MSDOS) || defined(OS2) || defined(WIN32) # ifndef DOS_OS2_W32 # define DOS_OS2_W32 # endif #endif #if defined(DOS_OS2_W32) || defined(__human68k__) # ifndef DOS_H68_OS2_W32 # define DOS_H68_OS2_W32 # endif #endif #if defined(VM_CMS) || defined(MVS) # ifndef CMS_MVS # define CMS_MVS # endif #endif /* To allow combining of Zip and UnZip static libraries in a single binary, * the Zip and UnZip versions of the crypt core functions have to be named * differently. */ #ifdef ZIP # ifdef REALLY_SHORT_SYMS # define decrypt_byte zdcrby # else # define decrypt_byte zp_decrypt_byte # endif # define update_keys zp_update_keys # define init_keys zp_init_keys #else /* !ZIP */ # ifdef REALLY_SHORT_SYMS # define decrypt_byte dcrbyt # endif #endif /* ?ZIP */ #define IZ_PWLEN 80 /* input buffer size for reading encryption key */ #ifndef PWLEN /* for compatibility with previous zcrypt release... */ # define PWLEN IZ_PWLEN #endif #define RAND_HEAD_LEN 12 /* length of encryption random header */ /* the crc_32_tab array has to be provided externally for the crypt calculus */ /* encode byte c, using temp t. Warning: c must not have side effects. */ #define zencode(c,t) (t=decrypt_byte(__G), update_keys(c), t^(c)) /* decode byte c in place */ #define zdecode(c) update_keys(__G__ c ^= decrypt_byte(__G)) int decrypt_byte OF((__GPRO)); int update_keys OF((__GPRO__ int c)); void init_keys OF((__GPRO__ ZCONST char *passwd)); #ifdef ZIP void crypthead OF((ZCONST char *, ulg)); # ifdef UTIL int zipcloak OF((struct zlist far *, ZCONST char *)); int zipbare OF((struct zlist far *, ZCONST char *)); # else unsigned zfwrite OF((zvoid *, extent, extent)); extern char *key; # endif #endif /* ZIP */ #if (defined(UNZIP) && !defined(FUNZIP)) int decrypt OF((__GPRO__ ZCONST char *passwrd)); #endif #ifdef FUNZIP extern int encrypted; # ifdef NEXTBYTE # undef NEXTBYTE # endif # define NEXTBYTE \ (encrypted? update_keys(__G__ getc(G.in)^decrypt_byte(__G)) : getc(G.in)) #endif /* FUNZIP */ #else /* !CRYPT */ /* dummy version */ #define zencode #define zdecode #define zfwrite(b,s,c) bfwrite(b,s,c,BFWRITE_DATA) #endif /* ?CRYPT */ #endif /* !__crypt_h */ zip30/deflate.c0100644000076400000060000010407510554631656011553 0ustar edisk/* deflate.c - Zip 3 Copyright (c) 1990-2007 Info-ZIP. All rights reserved. See the accompanying file LICENSE, version 2005-Feb-10 or later (the contents of which are also included in zip.h) for terms of use. If, for some reason, all these files are missing, the Info-ZIP license also may be found at: ftp://ftp.info-zip.org/pub/infozip/license.html */ /* * deflate.c by Jean-loup Gailly. * * PURPOSE * * Identify new text as repetitions of old text within a fixed- * length sliding window trailing behind the new text. * * DISCUSSION * * The "deflation" process depends on being able to identify portions * of the input text which are identical to earlier input (within a * sliding window trailing behind the input currently being processed). * * The most straightforward technique turns out to be the fastest for * most input files: try all possible matches and select the longest. * The key feature of this algorithm is that insertions into the string * dictionary are very simple and thus fast, and deletions are avoided * completely. Insertions are performed at each input character, whereas * string matches are performed only when the previous match ends. So it * is preferable to spend more time in matches to allow very fast string * insertions and avoid deletions. The matching algorithm for small * strings is inspired from that of Rabin & Karp. A brute force approach * is used to find longer strings when a small match has been found. * A similar algorithm is used in comic (by Jan-Mark Wams) and freeze * (by Leonid Broukhis). * A previous version of this file used a more sophisticated algorithm * (by Fiala and Greene) which is guaranteed to run in linear amortized * time, but has a larger average cost, uses more memory and is patented. * However the F&G algorithm may be faster for some highly redundant * files if the parameter max_chain_length (described below) is too large. * * ACKNOWLEDGEMENTS * * The idea of lazy evaluation of matches is due to Jan-Mark Wams, and * I found it in 'freeze' written by Leonid Broukhis. * Thanks to many info-zippers for bug reports and testing. * * REFERENCES * * APPNOTE.TXT documentation file in PKZIP 1.93a distribution. * * A description of the Rabin and Karp algorithm is given in the book * "Algorithms" by R. Sedgewick, Addison-Wesley, p252. * * Fiala,E.R., and Greene,D.H. * Data Compression with Finite Windows, Comm.ACM, 32,4 (1989) 490-595 * * INTERFACE * * void lm_init (int pack_level, ush *flags) * Initialize the "longest match" routines for a new file * * ulg deflate (void) * Processes a new input file and return its compressed length. Sets * the compressed length, crc, deflate flags and internal file * attributes. */ #define __DEFLATE_C #include "zip.h" #ifndef USE_ZLIB /* =========================================================================== * Configuration parameters */ /* Compile with MEDIUM_MEM to reduce the memory requirements or * with SMALL_MEM to use as little memory as possible. Use BIG_MEM if the * entire input file can be held in memory (not possible on 16 bit systems). * Warning: defining these symbols affects HASH_BITS (see below) and thus * affects the compression ratio. The compressed output * is still correct, and might even be smaller in some cases. */ #ifdef SMALL_MEM # define HASH_BITS 13 /* Number of bits used to hash strings */ #endif #ifdef MEDIUM_MEM # define HASH_BITS 14 #endif #ifndef HASH_BITS # define HASH_BITS 15 /* For portability to 16 bit machines, do not use values above 15. */ #endif #define HASH_SIZE (unsigned)(1<= HASH_BITS */ unsigned int near prev_length; /* Length of the best match at previous step. Matches not greater than this * are discarded. This is used in the lazy match evaluation. */ unsigned near strstart; /* start of string to insert */ unsigned near match_start; /* start of matching string */ local int eofile; /* flag set at end of input file */ local unsigned lookahead; /* number of valid bytes ahead in window */ unsigned near max_chain_length; /* To speed up deflation, hash chains are never searched beyond this length. * A higher limit improves compression ratio but degrades the speed. */ local unsigned int max_lazy_match; /* Attempt to find a better match only when the current match is strictly * smaller than this value. This mechanism is used only for compression * levels >= 4. */ #define max_insert_length max_lazy_match /* Insert new strings in the hash table only if the match length * is not greater than this length. This saves time but degrades compression. * max_insert_length is used only for compression levels <= 3. */ unsigned near good_match; /* Use a faster search when the previous match is longer than this */ #ifdef FULL_SEARCH # define nice_match MAX_MATCH #else int near nice_match; /* Stop searching when current match exceeds this */ #endif /* Values for max_lazy_match, good_match, nice_match and max_chain_length, * depending on the desired pack level (0..9). The values given below have * been tuned to exclude worst case performance for pathological files. * Better values may be found for specific files. */ typedef struct config { ush good_length; /* reduce lazy search above this match length */ ush max_lazy; /* do not perform lazy search above this match length */ ush nice_length; /* quit search above this match length */ ush max_chain; } config; local config configuration_table[10] = { /* good lazy nice chain */ /* 0 */ {0, 0, 0, 0}, /* store only */ /* 1 */ {4, 4, 8, 4}, /* maximum speed, no lazy matches */ /* 2 */ {4, 5, 16, 8}, /* 3 */ {4, 6, 32, 32}, /* 4 */ {4, 4, 16, 16}, /* lazy matches */ /* 5 */ {8, 16, 32, 32}, /* 6 */ {8, 16, 128, 128}, /* 7 */ {8, 32, 128, 256}, /* 8 */ {32, 128, 258, 1024}, /* 9 */ {32, 258, 258, 4096}}; /* maximum compression */ /* Note: the deflate() code requires max_lazy >= MIN_MATCH and max_chain >= 4 * For deflate_fast() (levels <= 3) good is ignored and lazy has a different * meaning. */ #define EQUAL 0 /* result of memcmp for equal strings */ /* =========================================================================== * Prototypes for local functions. */ local void fill_window OF((void)); local uzoff_t deflate_fast OF((void)); /* now use uzoff_t 7/24/04 EG */ int longest_match OF((IPos cur_match)); #if defined(ASMV) && !defined(RISCOS) void match_init OF((void)); /* asm code initialization */ #endif #ifdef DEBUG local void check_match OF((IPos start, IPos match, int length)); #endif /* =========================================================================== * Update a hash value with the given input byte * IN assertion: all calls to to UPDATE_HASH are made with consecutive * input characters, so that a running hash key can be computed from the * previous key instead of complete recalculation each time. */ #define UPDATE_HASH(h,c) (h = (((h)< 0 if the input file is already read or * mmap'ed in the window[] array, 0 otherwise. In the first case, * window_size is sufficient to contain the whole input file plus * MIN_LOOKAHEAD bytes (to avoid referencing memory beyond the end * of window[] when looking for matches towards the end). */ void lm_init (pack_level, flags) int pack_level; /* 0: store, 1: best speed, 9: best compression */ ush *flags; /* general purpose bit flag */ { register unsigned j; if (pack_level < 1 || pack_level > 9) error("bad pack level"); /* Do not slide the window if the whole input is already in memory * (window_size > 0) */ sliding = 0; if (window_size == 0L) { sliding = 1; window_size = (ulg)2L*WSIZE; } /* Use dynamic allocation if compiler does not like big static arrays: */ #ifdef DYN_ALLOC if (window == NULL) { window = (uch far *) zcalloc(WSIZE, 2*sizeof(uch)); if (window == NULL) ziperr(ZE_MEM, "window allocation"); } if (prev == NULL) { prev = (Pos far *) zcalloc(WSIZE, sizeof(Pos)); head = (Pos far *) zcalloc(HASH_SIZE, sizeof(Pos)); if (prev == NULL || head == NULL) { ziperr(ZE_MEM, "hash table allocation"); } } #endif /* DYN_ALLOC */ /* Initialize the hash table (avoiding 64K overflow for 16 bit systems). * prev[] will be initialized on the fly. */ head[HASH_SIZE-1] = NIL; memset((char*)head, NIL, (unsigned)(HASH_SIZE-1)*sizeof(*head)); /* Set the default configuration parameters: */ max_lazy_match = configuration_table[pack_level].max_lazy; good_match = configuration_table[pack_level].good_length; #ifndef FULL_SEARCH nice_match = configuration_table[pack_level].nice_length; #endif max_chain_length = configuration_table[pack_level].max_chain; if (pack_level <= 2) { *flags |= FAST; } else if (pack_level >= 8) { *flags |= SLOW; } /* ??? reduce max_chain_length for binary files */ strstart = 0; block_start = 0L; #if defined(ASMV) && !defined(RISCOS) match_init(); /* initialize the asm code */ #endif j = WSIZE; #ifndef MAXSEG_64K if (sizeof(int) > 2) j <<= 1; /* Can read 64K in one step */ #endif lookahead = (*read_buf)((char*)window, j); if (lookahead == 0 || lookahead == (unsigned)EOF) { eofile = 1, lookahead = 0; return; } eofile = 0; /* Make sure that we always have enough lookahead. This is important * if input comes from a device such as a tty. */ if (lookahead < MIN_LOOKAHEAD) fill_window(); ins_h = 0; for (j=0; j= 1 */ #ifndef ASMV /* For 80x86 and 680x0 and ARM, an optimized version is in match.asm or * match.S. The code is functionally equivalent, so you can use the C version * if desired. */ int longest_match(cur_match) IPos cur_match; /* current match */ { unsigned chain_length = max_chain_length; /* max hash chain length */ register uch far *scan = window + strstart; /* current string */ register uch far *match; /* matched string */ register int len; /* length of current match */ int best_len = prev_length; /* best match length so far */ IPos limit = strstart > (IPos)MAX_DIST ? strstart - (IPos)MAX_DIST : NIL; /* Stop when cur_match becomes <= limit. To simplify the code, * we prevent matches with the string of window index 0. */ /* The code is optimized for HASH_BITS >= 8 and MAX_MATCH-2 multiple of 16. * It is easy to get rid of this optimization if necessary. */ #if HASH_BITS < 8 || MAX_MATCH != 258 error: Code too clever #endif #ifdef UNALIGNED_OK /* Compare two bytes at a time. Note: this is not always beneficial. * Try with and without -DUNALIGNED_OK to check. */ register uch far *strend = window + strstart + MAX_MATCH - 1; register ush scan_start = *(ush far *)scan; register ush scan_end = *(ush far *)(scan+best_len-1); #else register uch far *strend = window + strstart + MAX_MATCH; register uch scan_end1 = scan[best_len-1]; register uch scan_end = scan[best_len]; #endif /* Do not waste too much time if we already have a good match: */ if (prev_length >= good_match) { chain_length >>= 2; } Assert(strstart <= window_size-MIN_LOOKAHEAD, "insufficient lookahead"); do { Assert(cur_match < strstart, "no future"); match = window + cur_match; /* Skip to next match if the match length cannot increase * or if the match length is less than 2: */ #if (defined(UNALIGNED_OK) && MAX_MATCH == 258) /* This code assumes sizeof(unsigned short) == 2. Do not use * UNALIGNED_OK if your compiler uses a different size. */ if (*(ush far *)(match+best_len-1) != scan_end || *(ush far *)match != scan_start) continue; /* It is not necessary to compare scan[2] and match[2] since they are * always equal when the other bytes match, given that the hash keys * are equal and that HASH_BITS >= 8. Compare 2 bytes at a time at * strstart+3, +5, ... up to strstart+257. We check for insufficient * lookahead only every 4th comparison; the 128th check will be made * at strstart+257. If MAX_MATCH-2 is not a multiple of 8, it is * necessary to put more guard bytes at the end of the window, or * to check more often for insufficient lookahead. */ scan++, match++; do { } while (*(ush far *)(scan+=2) == *(ush far *)(match+=2) && *(ush far *)(scan+=2) == *(ush far *)(match+=2) && *(ush far *)(scan+=2) == *(ush far *)(match+=2) && *(ush far *)(scan+=2) == *(ush far *)(match+=2) && scan < strend); /* The funny "do {}" generates better code on most compilers */ /* Here, scan <= window+strstart+257 */ Assert(scan <= window+(unsigned)(window_size-1), "wild scan"); if (*scan == *match) scan++; len = (MAX_MATCH - 1) - (int)(strend-scan); scan = strend - (MAX_MATCH-1); #else /* UNALIGNED_OK */ if (match[best_len] != scan_end || match[best_len-1] != scan_end1 || *match != *scan || *++match != scan[1]) continue; /* The check at best_len-1 can be removed because it will be made * again later. (This heuristic is not always a win.) * It is not necessary to compare scan[2] and match[2] since they * are always equal when the other bytes match, given that * the hash keys are equal and that HASH_BITS >= 8. */ scan += 2, match++; /* We check for insufficient lookahead only every 8th comparison; * the 256th check will be made at strstart+258. */ do { } while (*++scan == *++match && *++scan == *++match && *++scan == *++match && *++scan == *++match && *++scan == *++match && *++scan == *++match && *++scan == *++match && *++scan == *++match && scan < strend); Assert(scan <= window+(unsigned)(window_size-1), "wild scan"); len = MAX_MATCH - (int)(strend - scan); scan = strend - MAX_MATCH; #endif /* UNALIGNED_OK */ if (len > best_len) { match_start = cur_match; best_len = len; if (len >= nice_match) break; #ifdef UNALIGNED_OK scan_end = *(ush far *)(scan+best_len-1); #else scan_end1 = scan[best_len-1]; scan_end = scan[best_len]; #endif } } while ((cur_match = prev[cur_match & WMASK]) > limit && --chain_length != 0); return best_len; } #endif /* ASMV */ #ifdef DEBUG /* =========================================================================== * Check that the match at match_start is indeed a match. */ local void check_match(start, match, length) IPos start, match; int length; { /* check that the match is indeed a match */ if (memcmp((char*)window + match, (char*)window + start, length) != EQUAL) { fprintf(mesg, " start %d, match %d, length %d\n", start, match, length); error("invalid match"); } if (verbose > 1) { fprintf(mesg,"\\[%d,%d]", start-match, length); #ifndef WINDLL do { putc(window[start++], mesg); } while (--length != 0); #else do { fprintf(stdout,"%c",window[start++]); } while (--length != 0); #endif } } #else # define check_match(start, match, length) #endif /* =========================================================================== * Flush the current block, with given end-of-file flag. * IN assertion: strstart is set to the end of the current match. */ #define FLUSH_BLOCK(eof) \ flush_block(block_start >= 0L ? (char*)&window[(unsigned)block_start] : \ (char*)NULL, (ulg)strstart - (ulg)block_start, (eof)) /* =========================================================================== * Fill the window when the lookahead becomes insufficient. * Updates strstart and lookahead, and sets eofile if end of input file. * * IN assertion: lookahead < MIN_LOOKAHEAD && strstart + lookahead > 0 * OUT assertions: strstart <= window_size-MIN_LOOKAHEAD * At least one byte has been read, or eofile is set; file reads are * performed for at least two bytes (required for the translate_eol option). */ local void fill_window() { register unsigned n, m; unsigned more; /* Amount of free space at the end of the window. */ do { more = (unsigned)(window_size - (ulg)lookahead - (ulg)strstart); /* If the window is almost full and there is insufficient lookahead, * move the upper half to the lower one to make room in the upper half. */ if (more == (unsigned)EOF) { /* Very unlikely, but possible on 16 bit machine if strstart == 0 * and lookahead == 1 (input done one byte at time) */ more--; /* For MMAP or BIG_MEM, the whole input file is already in memory so * we must not perform sliding. We must however call (*read_buf)() in * order to compute the crc, update lookahead and possibly set eofile. */ } else if (strstart >= WSIZE+MAX_DIST && sliding) { #ifdef FORCE_METHOD /* When methods "stored" or "store_block" are requested, the * current block must be flushed before sliding the window. */ if (level <= 2) FLUSH_BLOCK(0), block_start = strstart; #endif /* By the IN assertion, the window is not empty so we can't confuse * more == 0 with more == 64K on a 16 bit machine. */ memcpy((char*)window, (char*)window+WSIZE, (unsigned)WSIZE); match_start -= WSIZE; strstart -= WSIZE; /* we now have strstart >= MAX_DIST: */ block_start -= (long) WSIZE; for (n = 0; n < HASH_SIZE; n++) { m = head[n]; head[n] = (Pos)(m >= WSIZE ? m-WSIZE : NIL); } for (n = 0; n < WSIZE; n++) { m = prev[n]; prev[n] = (Pos)(m >= WSIZE ? m-WSIZE : NIL); /* If n is not on any hash chain, prev[n] is garbage but * its value will never be used. */ } more += WSIZE; if (dot_size > 0 && !display_globaldots) { /* initial space */ if (noisy && dot_count == -1) { #ifndef WINDLL putc(' ', mesg); fflush(mesg); #else fprintf(stdout,"%c",' '); #endif dot_count++; } dot_count++; if (dot_size <= (dot_count + 1) * WSIZE) dot_count = 0; } if ((verbose || noisy) && dot_size && !dot_count) { #ifndef WINDLL putc('.', mesg); fflush(mesg); #else fprintf(stdout,"%c",'.'); #endif mesg_line_started = 1; } } if (eofile) return; /* If there was no sliding: * strstart <= WSIZE+MAX_DIST-1 && lookahead <= MIN_LOOKAHEAD - 1 && * more == window_size - lookahead - strstart * => more >= window_size - (MIN_LOOKAHEAD-1 + WSIZE + MAX_DIST-1) * => more >= window_size - 2*WSIZE + 2 * In the MMAP or BIG_MEM case (not yet supported in gzip), * window_size == input_size + MIN_LOOKAHEAD && * strstart + lookahead <= input_size => more >= MIN_LOOKAHEAD. * Otherwise, window_size == 2*WSIZE so more >= 2. * If there was sliding, more >= WSIZE. So in all cases, more >= 2. */ Assert(more >= 2, "more < 2"); n = (*read_buf)((char*)window+strstart+lookahead, more); if (n == 0 || n == (unsigned)EOF) { eofile = 1; } else { lookahead += n; } } while (lookahead < MIN_LOOKAHEAD && !eofile); } /* =========================================================================== * Processes a new input file and return its compressed length. This * function does not perform lazy evaluation of matches and inserts * new strings in the dictionary only for unmatched strings or for short * matches. It is used only for the fast compression options. */ local uzoff_t deflate_fast() { IPos hash_head = NIL; /* head of the hash chain */ int flush; /* set if current block must be flushed */ unsigned match_length = 0; /* length of best match */ prev_length = MIN_MATCH-1; while (lookahead != 0) { /* Insert the string window[strstart .. strstart+2] in the * dictionary, and set hash_head to the head of the hash chain: */ #ifndef DEFL_UNDETERM if (lookahead >= MIN_MATCH) #endif INSERT_STRING(strstart, hash_head); /* Find the longest match, discarding those <= prev_length. * At this point we have always match_length < MIN_MATCH */ if (hash_head != NIL && strstart - hash_head <= MAX_DIST) { /* To simplify the code, we prevent matches with the string * of window index 0 (in particular we have to avoid a match * of the string with itself at the start of the input file). */ #ifndef HUFFMAN_ONLY # ifndef DEFL_UNDETERM /* Do not look for matches beyond the end of the input. * This is necessary to make deflate deterministic. */ if ((unsigned)nice_match > lookahead) nice_match = (int)lookahead; # endif match_length = longest_match (hash_head); /* longest_match() sets match_start */ if (match_length > lookahead) match_length = lookahead; #endif } if (match_length >= MIN_MATCH) { check_match(strstart, match_start, match_length); flush = ct_tally(strstart-match_start, match_length - MIN_MATCH); lookahead -= match_length; /* Insert new strings in the hash table only if the match length * is not too large. This saves time but degrades compression. */ if (match_length <= max_insert_length #ifndef DEFL_UNDETERM && lookahead >= MIN_MATCH #endif ) { match_length--; /* string at strstart already in hash table */ do { strstart++; INSERT_STRING(strstart, hash_head); /* strstart never exceeds WSIZE-MAX_MATCH, so there are * always MIN_MATCH bytes ahead. */ #ifdef DEFL_UNDETERM /* If lookahead < MIN_MATCH these bytes are garbage, * but it does not matter since the next lookahead bytes * will be emitted as literals. */ #endif } while (--match_length != 0); strstart++; } else { strstart += match_length; match_length = 0; ins_h = window[strstart]; UPDATE_HASH(ins_h, window[strstart+1]); #if MIN_MATCH != 3 Call UPDATE_HASH() MIN_MATCH-3 more times #endif } } else { /* No match, output a literal byte */ Tracevv((stderr,"%c",window[strstart])); flush = ct_tally (0, window[strstart]); lookahead--; strstart++; } if (flush) FLUSH_BLOCK(0), block_start = strstart; /* Make sure that we always have enough lookahead, except * at the end of the input file. We need MAX_MATCH bytes * for the next match, plus MIN_MATCH bytes to insert the * string following the next match. */ if (lookahead < MIN_LOOKAHEAD) fill_window(); } return FLUSH_BLOCK(1); /* eof */ } /* =========================================================================== * Same as above, but achieves better compression. We use a lazy * evaluation for matches: a match is finally adopted only if there is * no better match at the next window position. */ uzoff_t deflate() { IPos hash_head = NIL; /* head of hash chain */ IPos prev_match; /* previous match */ int flush; /* set if current block must be flushed */ int match_available = 0; /* set if previous match exists */ register unsigned match_length = MIN_MATCH-1; /* length of best match */ #ifdef DEBUG extern uzoff_t isize; /* byte length of input file, for debug only */ #endif if (level <= 3) return deflate_fast(); /* optimized for speed */ /* Process the input block. */ while (lookahead != 0) { /* Insert the string window[strstart .. strstart+2] in the * dictionary, and set hash_head to the head of the hash chain: */ #ifndef DEFL_UNDETERM if (lookahead >= MIN_MATCH) #endif INSERT_STRING(strstart, hash_head); /* Find the longest match, discarding those <= prev_length. */ prev_length = match_length, prev_match = match_start; match_length = MIN_MATCH-1; if (hash_head != NIL && prev_length < max_lazy_match && strstart - hash_head <= MAX_DIST) { /* To simplify the code, we prevent matches with the string * of window index 0 (in particular we have to avoid a match * of the string with itself at the start of the input file). */ #ifndef HUFFMAN_ONLY # ifndef DEFL_UNDETERM /* Do not look for matches beyond the end of the input. * This is necessary to make deflate deterministic. */ if ((unsigned)nice_match > lookahead) nice_match = (int)lookahead; # endif match_length = longest_match (hash_head); /* longest_match() sets match_start */ if (match_length > lookahead) match_length = lookahead; #endif #ifdef FILTERED /* Ignore matches of length <= 5 */ if (match_length <= 5) { #else /* Ignore a length 3 match if it is too distant: */ if (match_length == MIN_MATCH && strstart-match_start > TOO_FAR){ #endif /* If prev_match is also MIN_MATCH, match_start is garbage * but we will ignore the current match anyway. */ match_length = MIN_MATCH-1; } } /* If there was a match at the previous step and the current * match is not better, output the previous match: */ if (prev_length >= MIN_MATCH && match_length <= prev_length) { #ifndef DEFL_UNDETERM unsigned max_insert = strstart + lookahead - MIN_MATCH; #endif check_match(strstart-1, prev_match, prev_length); flush = ct_tally(strstart-1-prev_match, prev_length - MIN_MATCH); /* Insert in hash table all strings up to the end of the match. * strstart-1 and strstart are already inserted. */ lookahead -= prev_length-1; prev_length -= 2; #ifndef DEFL_UNDETERM do { if (++strstart <= max_insert) { INSERT_STRING(strstart, hash_head); /* strstart never exceeds WSIZE-MAX_MATCH, so there are * always MIN_MATCH bytes ahead. */ } } while (--prev_length != 0); strstart++; #else /* DEFL_UNDETERM */ do { strstart++; INSERT_STRING(strstart, hash_head); /* strstart never exceeds WSIZE-MAX_MATCH, so there are * always MIN_MATCH bytes ahead. If lookahead < MIN_MATCH * these bytes are garbage, but it does not matter since the * next lookahead bytes will always be emitted as literals. */ } while (--prev_length != 0); strstart++; #endif /* ?DEFL_UNDETERM */ match_available = 0; match_length = MIN_MATCH-1; if (flush) FLUSH_BLOCK(0), block_start = strstart; } else if (match_available) { /* If there was no match at the previous position, output a * single literal. If there was a match but the current match * is longer, truncate the previous match to a single literal. */ Tracevv((stderr,"%c",window[strstart-1])); if (ct_tally (0, window[strstart-1])) { FLUSH_BLOCK(0), block_start = strstart; } strstart++; lookahead--; } else { /* There is no previous match to compare with, wait for * the next step to decide. */ match_available = 1; strstart++; lookahead--; } Assert(strstart <= isize && lookahead <= isize, "a bit too far"); /* Make sure that we always have enough lookahead, except * at the end of the input file. We need MAX_MATCH bytes * for the next match, plus MIN_MATCH bytes to insert the * string following the next match. */ if (lookahead < MIN_LOOKAHEAD) fill_window(); } if (match_available) ct_tally (0, window[strstart-1]); return FLUSH_BLOCK(1); /* eof */ } #endif /* !USE_ZLIB */ zip30/ebcdic.h0100644000076400000060000004141110226042252011337 0ustar edisk/* ebcdic.h Copyright (c) 1990-2005 Info-ZIP. All rights reserved. See the accompanying file LICENSE, version 2005-Feb-10 or later (the contents of which are also included in zip.h) for terms of use. If, for some reason, both of these files are missing, the Info-ZIP license also may be found at: ftp://ftp.info-zip.org/pub/infozip/licen */ /*--------------------------------------------------------------------------- ebcdic.h The CECP 1047 (Extended de-facto EBCDIC) <-> ISO 8859-1 conversion tables, from ftp://aix1.segi.ulg.ac.be/pub/docs/iso8859/iso8859.networking NOTES: (OS/390 port 12/97) These table no longer represent the standard mappings (for example in the OS/390 iconv utility). In order to follow current standards I remapped ebcdic x0a to ascii x15 and ebcdic x85 to ascii x25 (and vice-versa) Without these changes, newlines in auto-convert text files appeared as literal \045. I'm not sure what effect this remap would have on the MVS and CMS ports, so I ifdef'd these changes. Hopefully these ifdef's can be removed when the MVS/CMS folks test the new mappings. Christian Spieler , 27-Apr-1998 The problem mentioned by Paul von Behren was already observed previously on VM/CMS, during the preparation of the CMS&MVS port of UnZip 5.20 in 1996. At that point, the ebcdic tables were not changed since they seemed to be an adopted standard (to my knowledge, these tables are still used as presented in mainfraime KERMIT). Instead, the "end-of-line" conversion feature of Zip's and UnZip's "text-translation" mode was used to force correct mappings between ASCII and EBCDIC newline markers. Before interchanging the ASCII mappings of the EBCDIC control characters "NL" 0x25 and "LF" 0x15 according to the OS/390 setting, we have to make sure that EBCDIC 0x15 is never used as line termination. ---------------------------------------------------------------------------*/ #ifndef __ebcdic_h /* prevent multiple inclusions */ #define __ebcdic_h #ifndef ZCONST # define ZCONST const #endif #ifdef EBCDIC #ifndef MTS /* MTS uses a slightly "special" EBCDIC code page */ ZCONST uch ebcdic[] = { 0x00, 0x01, 0x02, 0x03, 0x37, 0x2D, 0x2E, 0x2F, /* 00 - 07 */ #ifdef OS390 0x16, 0x05, 0x15, 0x0B, 0x0C, 0x0D, 0x0E, 0x0F, /* 08 - 0F */ #else 0x16, 0x05, 0x25, 0x0B, 0x0C, 0x0D, 0x0E, 0x0F, /* 08 - 0F */ #endif 0x10, 0x11, 0x12, 0x13, 0x3C, 0x3D, 0x32, 0x26, /* 10 - 17 */ 0x18, 0x19, 0x3F, 0x27, 0x1C, 0x1D, 0x1E, 0x1F, /* 18 - 1F */ 0x40, 0x5A, 0x7F, 0x7B, 0x5B, 0x6C, 0x50, 0x7D, /* 20 - 27 */ 0x4D, 0x5D, 0x5C, 0x4E, 0x6B, 0x60, 0x4B, 0x61, /* 28 - 2F */ 0xF0, 0xF1, 0xF2, 0xF3, 0xF4, 0xF5, 0xF6, 0xF7, /* 30 - 37 */ 0xF8, 0xF9, 0x7A, 0x5E, 0x4C, 0x7E, 0x6E, 0x6F, /* 38 - 3F */ 0x7C, 0xC1, 0xC2, 0xC3, 0xC4, 0xC5, 0xC6, 0xC7, /* 40 - 47 */ 0xC8, 0xC9, 0xD1, 0xD2, 0xD3, 0xD4, 0xD5, 0xD6, /* 48 - 4F */ 0xD7, 0xD8, 0xD9, 0xE2, 0xE3, 0xE4, 0xE5, 0xE6, /* 50 - 57 */ 0xE7, 0xE8, 0xE9, 0xAD, 0xE0, 0xBD, 0x5F, 0x6D, /* 58 - 5F */ 0x79, 0x81, 0x82, 0x83, 0x84, 0x85, 0x86, 0x87, /* 60 - 67 */ 0x88, 0x89, 0x91, 0x92, 0x93, 0x94, 0x95, 0x96, /* 68 - 6F */ 0x97, 0x98, 0x99, 0xA2, 0xA3, 0xA4, 0xA5, 0xA6, /* 70 - 77 */ 0xA7, 0xA8, 0xA9, 0xC0, 0x4F, 0xD0, 0xA1, 0x07, /* 78 - 7F */ #ifdef OS390 0x20, 0x21, 0x22, 0x23, 0x24, 0x25, 0x06, 0x17, /* 80 - 87 */ #else 0x20, 0x21, 0x22, 0x23, 0x24, 0x15, 0x06, 0x17, /* 80 - 87 */ #endif 0x28, 0x29, 0x2A, 0x2B, 0x2C, 0x09, 0x0A, 0x1B, /* 88 - 8F */ 0x30, 0x31, 0x1A, 0x33, 0x34, 0x35, 0x36, 0x08, /* 90 - 97 */ 0x38, 0x39, 0x3A, 0x3B, 0x04, 0x14, 0x3E, 0xFF, /* 98 - 9F */ 0x41, 0xAA, 0x4A, 0xB1, 0x9F, 0xB2, 0x6A, 0xB5, /* A0 - A7 */ 0xBB, 0xB4, 0x9A, 0x8A, 0xB0, 0xCA, 0xAF, 0xBC, /* A8 - AF */ 0x90, 0x8F, 0xEA, 0xFA, 0xBE, 0xA0, 0xB6, 0xB3, /* B0 - B7 */ 0x9D, 0xDA, 0x9B, 0x8B, 0xB7, 0xB8, 0xB9, 0xAB, /* B8 - BF */ 0x64, 0x65, 0x62, 0x66, 0x63, 0x67, 0x9E, 0x68, /* C0 - C7 */ 0x74, 0x71, 0x72, 0x73, 0x78, 0x75, 0x76, 0x77, /* C8 - CF */ 0xAC, 0x69, 0xED, 0xEE, 0xEB, 0xEF, 0xEC, 0xBF, /* D0 - D7 */ 0x80, 0xFD, 0xFE, 0xFB, 0xFC, 0xBA, 0xAE, 0x59, /* D8 - DF */ 0x44, 0x45, 0x42, 0x46, 0x43, 0x47, 0x9C, 0x48, /* E0 - E7 */ 0x54, 0x51, 0x52, 0x53, 0x58, 0x55, 0x56, 0x57, /* E8 - EF */ 0x8C, 0x49, 0xCD, 0xCE, 0xCB, 0xCF, 0xCC, 0xE1, /* F0 - F7 */ 0x70, 0xDD, 0xDE, 0xDB, 0xDC, 0x8D, 0x8E, 0xDF /* F8 - FF */ }; #if (defined(ZIP) || CRYPT) ZCONST uch ascii[] = { 0x00, 0x01, 0x02, 0x03, 0x9C, 0x09, 0x86, 0x7F, /* 00 - 07 */ 0x97, 0x8D, 0x8E, 0x0B, 0x0C, 0x0D, 0x0E, 0x0F, /* 08 - 0F */ #ifdef OS390 0x10, 0x11, 0x12, 0x13, 0x9D, 0x0A, 0x08, 0x87, /* 10 - 17 */ #else 0x10, 0x11, 0x12, 0x13, 0x9D, 0x85, 0x08, 0x87, /* 10 - 17 */ #endif 0x18, 0x19, 0x92, 0x8F, 0x1C, 0x1D, 0x1E, 0x1F, /* 18 - 1F */ #ifdef OS390 0x80, 0x81, 0x82, 0x83, 0x84, 0x85, 0x17, 0x1B, /* 20 - 27 */ #else 0x80, 0x81, 0x82, 0x83, 0x84, 0x0A, 0x17, 0x1B, /* 20 - 27 */ #endif 0x88, 0x89, 0x8A, 0x8B, 0x8C, 0x05, 0x06, 0x07, /* 28 - 2F */ 0x90, 0x91, 0x16, 0x93, 0x94, 0x95, 0x96, 0x04, /* 30 - 37 */ 0x98, 0x99, 0x9A, 0x9B, 0x14, 0x15, 0x9E, 0x1A, /* 38 - 3F */ 0x20, 0xA0, 0xE2, 0xE4, 0xE0, 0xE1, 0xE3, 0xE5, /* 40 - 47 */ 0xE7, 0xF1, 0xA2, 0x2E, 0x3C, 0x28, 0x2B, 0x7C, /* 48 - 4F */ 0x26, 0xE9, 0xEA, 0xEB, 0xE8, 0xED, 0xEE, 0xEF, /* 50 - 57 */ 0xEC, 0xDF, 0x21, 0x24, 0x2A, 0x29, 0x3B, 0x5E, /* 58 - 5F */ 0x2D, 0x2F, 0xC2, 0xC4, 0xC0, 0xC1, 0xC3, 0xC5, /* 60 - 67 */ 0xC7, 0xD1, 0xA6, 0x2C, 0x25, 0x5F, 0x3E, 0x3F, /* 68 - 6F */ 0xF8, 0xC9, 0xCA, 0xCB, 0xC8, 0xCD, 0xCE, 0xCF, /* 70 - 77 */ 0xCC, 0x60, 0x3A, 0x23, 0x40, 0x27, 0x3D, 0x22, /* 78 - 7F */ 0xD8, 0x61, 0x62, 0x63, 0x64, 0x65, 0x66, 0x67, /* 80 - 87 */ 0x68, 0x69, 0xAB, 0xBB, 0xF0, 0xFD, 0xFE, 0xB1, /* 88 - 8F */ 0xB0, 0x6A, 0x6B, 0x6C, 0x6D, 0x6E, 0x6F, 0x70, /* 90 - 97 */ 0x71, 0x72, 0xAA, 0xBA, 0xE6, 0xB8, 0xC6, 0xA4, /* 98 - 9F */ 0xB5, 0x7E, 0x73, 0x74, 0x75, 0x76, 0x77, 0x78, /* A0 - A7 */ 0x79, 0x7A, 0xA1, 0xBF, 0xD0, 0x5B, 0xDE, 0xAE, /* A8 - AF */ 0xAC, 0xA3, 0xA5, 0xB7, 0xA9, 0xA7, 0xB6, 0xBC, /* B0 - B7 */ 0xBD, 0xBE, 0xDD, 0xA8, 0xAF, 0x5D, 0xB4, 0xD7, /* B8 - BF */ 0x7B, 0x41, 0x42, 0x43, 0x44, 0x45, 0x46, 0x47, /* C0 - C7 */ 0x48, 0x49, 0xAD, 0xF4, 0xF6, 0xF2, 0xF3, 0xF5, /* C8 - CF */ 0x7D, 0x4A, 0x4B, 0x4C, 0x4D, 0x4E, 0x4F, 0x50, /* D0 - D7 */ 0x51, 0x52, 0xB9, 0xFB, 0xFC, 0xF9, 0xFA, 0xFF, /* D8 - DF */ 0x5C, 0xF7, 0x53, 0x54, 0x55, 0x56, 0x57, 0x58, /* E0 - E7 */ 0x59, 0x5A, 0xB2, 0xD4, 0xD6, 0xD2, 0xD3, 0xD5, /* E8 - EF */ 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37, /* F0 - F7 */ 0x38, 0x39, 0xB3, 0xDB, 0xDC, 0xD9, 0xDA, 0x9F /* F8 - FF */ }; #endif /* ZIP || CRYPT */ #else /* MTS */ /* * This is the MTS ASCII->EBCDIC translation table. It provides a 1-1 * translation from ISO 8859/1 8-bit ASCII to IBM Code Page 37 EBCDIC. */ ZCONST uch ebcdic[] = { 0x00, 0x01, 0x02, 0x03, 0x37, 0x2D, 0x2E, 0x2F, /* 00 - 07 */ 0x16, 0x05, 0x25, 0x0B, 0x0C, 0x0D, 0x0E, 0x0F, /* 08 - 0F */ 0x10, 0x11, 0x12, 0x13, 0x3C, 0x3D, 0x32, 0x26, /* 10 - 17 */ 0x18, 0x19, 0x3F, 0x27, 0x1C, 0x1D, 0x1E, 0x1F, /* 18 - 1F */ 0x40, 0x5A, 0x7F, 0x7B, 0x5B, 0x6C, 0x50, 0x7D, /* 20 - 27 */ 0x4D, 0x5D, 0x5C, 0x4E, 0x6B, 0x60, 0x4B, 0x61, /* 28 - 2F */ 0xF0, 0xF1, 0xF2, 0xF3, 0xF4, 0xF5, 0xF6, 0xF7, /* 30 - 37 */ 0xF8, 0xF9, 0x7A, 0x5E, 0x4C, 0x7E, 0x6E, 0x6F, /* 38 - 3F */ 0x7C, 0xC1, 0xC2, 0xC3, 0xC4, 0xC5, 0xC6, 0xC7, /* 40 - 47 */ 0xC8, 0xC9, 0xD1, 0xD2, 0xD3, 0xD4, 0xD5, 0xD6, /* 48 - 4F */ 0xD7, 0xD8, 0xD9, 0xE2, 0xE3, 0xE4, 0xE5, 0xE6, /* 50 - 57 */ 0xE7, 0xE8, 0xE9, 0xBA, 0xE0, 0xBB, 0xB0, 0x6D, /* 58 - 5F */ 0x79, 0x81, 0x82, 0x83, 0x84, 0x85, 0x86, 0x87, /* 60 - 67 */ 0x88, 0x89, 0x91, 0x92, 0x93, 0x94, 0x95, 0x96, /* 68 - 6F */ 0x97, 0x98, 0x99, 0xA2, 0xA3, 0xA4, 0xA5, 0xA6, /* 70 - 77 */ 0xA7, 0xA8, 0xA9, 0xC0, 0x4F, 0xD0, 0xA1, 0x07, /* 78 - 7F */ 0x20, 0x21, 0x22, 0x23, 0x24, 0x15, 0x06, 0x17, /* 80 - 87 */ 0x28, 0x29, 0x2A, 0x2B, 0x2C, 0x09, 0x0A, 0x1B, /* 88 - 8F */ 0x30, 0x31, 0x1A, 0x33, 0x34, 0x35, 0x36, 0x08, /* 90 - 97 */ 0x38, 0x39, 0x3A, 0x3B, 0x04, 0x14, 0x3E, 0xFF, /* 98 - 9F */ 0x41, 0xAA, 0x4A, 0xB1, 0x9F, 0xB2, 0x6A, 0xB5, /* A0 - A7 */ 0xBD, 0xB4, 0x9A, 0x8A, 0x5F, 0xCA, 0xAF, 0xBC, /* A8 - AF */ 0x90, 0x8F, 0xEA, 0xFA, 0xBE, 0xA0, 0xB6, 0xB3, /* B0 - B7 */ 0x9D, 0xDA, 0x9B, 0x8B, 0xB7, 0xB8, 0xB9, 0xAB, /* B8 - BF */ 0x64, 0x65, 0x62, 0x66, 0x63, 0x67, 0x9E, 0x68, /* C0 - C7 */ 0x74, 0x71, 0x72, 0x73, 0x78, 0x75, 0x76, 0x77, /* C8 - CF */ 0xAC, 0x69, 0xED, 0xEE, 0xEB, 0xEF, 0xEC, 0xBF, /* D0 - D7 */ 0x80, 0xFD, 0xFE, 0xFB, 0xFC, 0xAD, 0xAE, 0x59, /* D8 - DF */ 0x44, 0x45, 0x42, 0x46, 0x43, 0x47, 0x9C, 0x48, /* E0 - E7 */ 0x54, 0x51, 0x52, 0x53, 0x58, 0x55, 0x56, 0x57, /* E8 - EF */ 0x8C, 0x49, 0xCD, 0xCE, 0xCB, 0xCF, 0xCC, 0xE1, /* F0 - F7 */ 0x70, 0xDD, 0xDE, 0xDB, 0xDC, 0x8D, 0x8E, 0xDF /* F8 - FF */ }; #if (defined(ZIP) || CRYPT) ZCONST uch ascii[] = { 0x00, 0x01, 0x02, 0x03, 0x9C, 0x09, 0x86, 0x7F, /* 00 - 07 */ 0x97, 0x8D, 0x8E, 0x0B, 0x0C, 0x0D, 0x0E, 0x0F, /* 08 - 0F */ 0x10, 0x11, 0x12, 0x13, 0x9D, 0x85, 0x08, 0x87, /* 10 - 17 */ 0x18, 0x19, 0x92, 0x8F, 0x1C, 0x1D, 0x1E, 0x1F, /* 18 - 1F */ 0x80, 0x81, 0x82, 0x83, 0x84, 0x0A, 0x17, 0x1B, /* 20 - 27 */ 0x88, 0x89, 0x8A, 0x8B, 0x8C, 0x05, 0x06, 0x07, /* 28 - 2F */ 0x90, 0x91, 0x16, 0x93, 0x94, 0x95, 0x96, 0x04, /* 30 - 37 */ 0x98, 0x99, 0x9A, 0x9B, 0x14, 0x15, 0x9E, 0x1A, /* 38 - 3F */ 0x20, 0xA0, 0xE2, 0xE4, 0xE0, 0xE1, 0xE3, 0xE5, /* 40 - 47 */ 0xE7, 0xF1, 0xA2, 0x2E, 0x3C, 0x28, 0x2B, 0x7C, /* 48 - 4F */ 0x26, 0xE9, 0xEA, 0xEB, 0xE8, 0xED, 0xEE, 0xEF, /* 50 - 57 */ 0xEC, 0xDF, 0x21, 0x24, 0x2A, 0x29, 0x3B, 0xAC, /* 58 - 5F */ 0x2D, 0x2F, 0xC2, 0xC4, 0xC0, 0xC1, 0xC3, 0xC5, /* 60 - 67 */ 0xC7, 0xD1, 0xA6, 0x2C, 0x25, 0x5F, 0x3E, 0x3F, /* 68 - 6F */ 0xF8, 0xC9, 0xCA, 0xCB, 0xC8, 0xCD, 0xCE, 0xCF, /* 70 - 77 */ 0xCC, 0x60, 0x3A, 0x23, 0x40, 0x27, 0x3D, 0x22, /* 78 - 7F */ 0xD8, 0x61, 0x62, 0x63, 0x64, 0x65, 0x66, 0x67, /* 80 - 87 */ 0x68, 0x69, 0xAB, 0xBB, 0xF0, 0xFD, 0xFE, 0xB1, /* 88 - 8F */ 0xB0, 0x6A, 0x6B, 0x6C, 0x6D, 0x6E, 0x6F, 0x70, /* 90 - 97 */ 0x71, 0x72, 0xAA, 0xBA, 0xE6, 0xB8, 0xC6, 0xA4, /* 98 - 9F */ 0xB5, 0x7E, 0x73, 0x74, 0x75, 0x76, 0x77, 0x78, /* A0 - A7 */ 0x79, 0x7A, 0xA1, 0xBF, 0xD0, 0xDD, 0xDE, 0xAE, /* A8 - AF */ 0x5E, 0xA3, 0xA5, 0xB7, 0xA9, 0xA7, 0xB6, 0xBC, /* B0 - B7 */ 0xBD, 0xBE, 0x5B, 0x5D, 0xAF, 0xA8, 0xB4, 0xD7, /* B8 - BF */ 0x7B, 0x41, 0x42, 0x43, 0x44, 0x45, 0x46, 0x47, /* C0 - C7 */ 0x48, 0x49, 0xAD, 0xF4, 0xF6, 0xF2, 0xF3, 0xF5, /* C8 - CF */ 0x7D, 0x4A, 0x4B, 0x4C, 0x4D, 0x4E, 0x4F, 0x50, /* D0 - D7 */ 0x51, 0x52, 0xB9, 0xFB, 0xFC, 0xF9, 0xFA, 0xFF, /* D8 - DF */ 0x5C, 0xF7, 0x53, 0x54, 0x55, 0x56, 0x57, 0x58, /* E0 - E7 */ 0x59, 0x5A, 0xB2, 0xD4, 0xD6, 0xD2, 0xD3, 0xD5, /* E8 - EF */ 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37, /* F0 - F7 */ 0x38, 0x39, 0xB3, 0xDB, 0xDC, 0xD9, 0xDA, 0x9F /* F8 - FF */ }; #endif /* ZIP || CRYPT */ #endif /* ?MTS */ #endif /* EBCDIC */ /*--------------------------------------------------------------------------- The following conversion tables translate between IBM PC CP 850 (OEM codepage) and the "Western Europe & America" Windows codepage 1252. The Windows codepage 1252 contains the ISO 8859-1 "Latin 1" codepage, with some additional printable characters in the range (0x80 - 0x9F), that is reserved to control codes in the ISO 8859-1 character table. The ISO <--> OEM conversion tables were constructed with the help of the WIN32 (Win16?) API's OemToAnsi() and AnsiToOem() conversion functions and have been checked against the CP850 and LATIN1 tables provided in the MS-Kermit 3.14 distribution. ---------------------------------------------------------------------------*/ #ifdef IZ_ISO2OEM_ARRAY #ifdef OEM_RUSS ZCONST uch Far iso2oem[] = { 0x3F, 0x3F, 0x27, 0x9F, 0x22, 0x2E, 0xC5, 0xCE, /* 80 - 87 */ 0xFD, 0x25, 0x53, 0x3C, 0x4F, 0x3F, 0x3F, 0x3F, /* 88 - 8F */ 0x3F, 0x27, 0x27, 0x22, 0x22, 0xF9, 0x2D, 0x2D, /* 90 - 97 */ 0x7E, 0x54, 0x73, 0x3E, 0x6F, 0x3F, 0x3F, 0x59, /* 98 - 9F */ 0xFF, 0xF6, 0xF7, 0x9C, 0xCF, 0xBE, 0xFE, 0xF5, /* A0 - A7 */ 0xF0, 0xB8, 0xF2, 0xAE, 0xAA, 0xF0, 0xA9, 0xEE, /* A8 - AF */ 0xF8, 0xFB, 0xF4, 0xF5, 0xEF, 0xE6, 0xF4, 0xFA, /* B0 - B7 */ 0xF1, 0xFC, 0xF3, 0xAF, 0xAC, 0xAB, 0xF3, 0xA8, /* B8 - BF */ 0x80, 0x81, 0x82, 0x83, 0x84, 0x86, 0x86, 0x87, /* C0 - C7 */ 0x88, 0x89, 0x8A, 0x8B, 0x8C, 0x8D, 0x8E, 0x8F, /* C8 - CF */ 0x90, 0x91, 0x92, 0x93, 0x94, 0x95, 0x96, 0x97, /* D0 - D7 */ 0x98, 0x99, 0x9A, 0x9B, 0x9C, 0x9D, 0x9E, 0x9F, /* D8 - DF */ 0xA0, 0xA1, 0xA2, 0xA3, 0xA4, 0xA5, 0xA6, 0xA7, /* E0 - E7 */ 0xA8, 0xA9, 0xAA, 0xAB, 0xAC, 0xAD, 0xAE, 0xAF, /* E8 - EF */ 0xE0, 0xE1, 0xE2, 0xE3, 0xE4, 0xE5, 0xE6, 0xE7, /* F0 - F7 */ 0xE8, 0xE9, 0xEA, 0xEB, 0xEC, 0xED, 0xEE, 0xEF /* F8 - FF */ }; #else /* OEM_RUS */ ZCONST uch Far iso2oem[] = { 0x3F, 0x3F, 0x27, 0x9F, 0x22, 0x2E, 0xC5, 0xCE, /* 80 - 87 */ 0x5E, 0x25, 0x53, 0x3C, 0x4F, 0x3F, 0x3F, 0x3F, /* 88 - 8F */ 0x3F, 0x27, 0x27, 0x22, 0x22, 0x07, 0x2D, 0x2D, /* 90 - 97 */ 0x7E, 0x54, 0x73, 0x3E, 0x6F, 0x3F, 0x3F, 0x59, /* 98 - 9F */ 0xFF, 0xAD, 0xBD, 0x9C, 0xCF, 0xBE, 0xDD, 0xF5, /* A0 - A7 */ 0xF9, 0xB8, 0xA6, 0xAE, 0xAA, 0xF0, 0xA9, 0xEE, /* A8 - AF */ 0xF8, 0xF1, 0xFD, 0xFC, 0xEF, 0xE6, 0xF4, 0xFA, /* B0 - B7 */ 0xF7, 0xFB, 0xA7, 0xAF, 0xAC, 0xAB, 0xF3, 0xA8, /* B8 - BF */ 0xB7, 0xB5, 0xB6, 0xC7, 0x8E, 0x8F, 0x92, 0x80, /* C0 - C7 */ 0xD4, 0x90, 0xD2, 0xD3, 0xDE, 0xD6, 0xD7, 0xD8, /* C8 - CF */ 0xD1, 0xA5, 0xE3, 0xE0, 0xE2, 0xE5, 0x99, 0x9E, /* D0 - D7 */ 0x9D, 0xEB, 0xE9, 0xEA, 0x9A, 0xED, 0xE8, 0xE1, /* D8 - DF */ 0x85, 0xA0, 0x83, 0xC6, 0x84, 0x86, 0x91, 0x87, /* E0 - E7 */ 0x8A, 0x82, 0x88, 0x89, 0x8D, 0xA1, 0x8C, 0x8B, /* E8 - EF */ 0xD0, 0xA4, 0x95, 0xA2, 0x93, 0xE4, 0x94, 0xF6, /* F0 - F7 */ 0x9B, 0x97, 0xA3, 0x96, 0x81, 0xEC, 0xE7, 0x98 /* F8 - FF */ }; #endif /* OEM_RUS */ #endif /* IZ_ISO2OEM_ARRAY */ #ifdef IZ_OEM2ISO_ARRAY #ifdef OEM_RUSS ZCONST uch Far oem2iso[] = { 0xC0, 0xC1, 0xC2, 0xC3, 0xC4, 0xC5, 0xC6, 0xC7, /* 80 - 87 */ 0xC8, 0xC9, 0xCA, 0xCB, 0xCC, 0xCD, 0xCE, 0xCF, /* 88 - 8F */ 0xD0, 0xD1, 0xD2, 0xD3, 0xD4, 0xD5, 0xD6, 0xD7, /* 90 - 97 */ 0xD8, 0xD9, 0xDA, 0xDB, 0xDC, 0xDD, 0xDE, 0xDF, /* 98 - 9F */ 0xE0, 0xE1, 0xE2, 0xE3, 0xE4, 0xE5, 0xE6, 0xE7, /* A0 - A7 */ 0xE8, 0xE9, 0xEA, 0xEB, 0xEC, 0xED, 0xEE, 0xEF, /* A8 - AF */ 0xA6, 0xA6, 0xA6, 0xA6, 0xA6, 0xC1, 0xC2, 0xC0, /* B0 - B7 */ 0xA9, 0xA6, 0xA6, 0x2B, 0x2B, 0xA2, 0xA5, 0x2B, /* B8 - BF */ 0x2B, 0x2D, 0x2D, 0x2B, 0x2D, 0x2B, 0xE3, 0xC3, /* C0 - C7 */ 0x2B, 0x2B, 0x2D, 0x2D, 0xA6, 0x2D, 0x2B, 0xA4, /* C8 - CF */ 0xF0, 0xD0, 0xCA, 0xCB, 0xC8, 0x69, 0xCD, 0xCE, /* D0 - D7 */ 0xCF, 0x2B, 0x2B, 0xA6, 0x5F, 0xA6, 0xCC, 0xAF, /* D8 - DF */ 0xF0, 0xF1, 0xF2, 0xF3, 0xF4, 0xF5, 0xF6, 0xF7, /* E0 - E7 */ 0xF8, 0xF9, 0xFA, 0xFB, 0xFC, 0xFD, 0xFE, 0xFF, /* E8 - EF */ 0xA8, 0xB8, 0xAA, 0xBA, 0xB2, 0xB3, 0xA1, 0xA2, /* F0 - F7 */ 0xB0, 0x95, 0xB7, 0xB1, 0xB9, 0x88, 0xA6, 0xA0 /* F8 - FF */ }; #else /* OEM_RUS */ ZCONST uch Far oem2iso[] = { 0xC7, 0xFC, 0xE9, 0xE2, 0xE4, 0xE0, 0xE5, 0xE7, /* 80 - 87 */ 0xEA, 0xEB, 0xE8, 0xEF, 0xEE, 0xEC, 0xC4, 0xC5, /* 88 - 8F */ 0xC9, 0xE6, 0xC6, 0xF4, 0xF6, 0xF2, 0xFB, 0xF9, /* 90 - 97 */ 0xFF, 0xD6, 0xDC, 0xF8, 0xA3, 0xD8, 0xD7, 0x83, /* 98 - 9F */ 0xE1, 0xED, 0xF3, 0xFA, 0xF1, 0xD1, 0xAA, 0xBA, /* A0 - A7 */ 0xBF, 0xAE, 0xAC, 0xBD, 0xBC, 0xA1, 0xAB, 0xBB, /* A8 - AF */ 0xA6, 0xA6, 0xA6, 0xA6, 0xA6, 0xC1, 0xC2, 0xC0, /* B0 - B7 */ 0xA9, 0xA6, 0xA6, 0x2B, 0x2B, 0xA2, 0xA5, 0x2B, /* B8 - BF */ 0x2B, 0x2D, 0x2D, 0x2B, 0x2D, 0x2B, 0xE3, 0xC3, /* C0 - C7 */ 0x2B, 0x2B, 0x2D, 0x2D, 0xA6, 0x2D, 0x2B, 0xA4, /* C8 - CF */ 0xF0, 0xD0, 0xCA, 0xCB, 0xC8, 0x69, 0xCD, 0xCE, /* D0 - D7 */ 0xCF, 0x2B, 0x2B, 0xA6, 0x5F, 0xA6, 0xCC, 0xAF, /* D8 - DF */ 0xD3, 0xDF, 0xD4, 0xD2, 0xF5, 0xD5, 0xB5, 0xFE, /* E0 - E7 */ 0xDE, 0xDA, 0xDB, 0xD9, 0xFD, 0xDD, 0xAF, 0xB4, /* E8 - EF */ 0xAD, 0xB1, 0x3D, 0xBE, 0xB6, 0xA7, 0xF7, 0xB8, /* F0 - F7 */ 0xB0, 0xA8, 0xB7, 0xB9, 0xB3, 0xB2, 0xA6, 0xA0 /* F8 - FF */ }; #endif /* OEM_RUS */ #endif /* IZ_OEM2ISO_ARRAY */ #if defined(THEOS) || defined(THEOS_SUPPORT) # include "theos/charconv.h" #endif #endif /* __ebcdic_h */ zip30/fileio.c0100644000076400000060000042344611017372444011414 0ustar edisk/* fileio.c - Zip 3 Copyright (c) 1990-2008 Info-ZIP. All rights reserved. See the accompanying file LICENSE, version 2007-Mar-4 or later (the contents of which are also included in zip.h) for terms of use. If, for some reason, all these files are missing, the Info-ZIP license also may be found at: ftp://ftp.info-zip.org/pub/infozip/license.html */ /* * fileio.c by Mark Adler */ #define __FILEIO_C #include "zip.h" #include "crc32.h" #ifdef MACOS # include "helpers.h" #endif #ifdef VMS # include "vms/vms.h" #endif /* def VMS */ #include #ifdef NO_MKTIME time_t mktime OF((struct tm *)); #endif #ifdef OSF #define EXDEV 18 /* avoid a bug in the DEC OSF/1 header files. */ #else #include #endif #ifdef NO_ERRNO extern int errno; #endif /* ----------------------- For long option support ----------------------- */ #include #if defined(VMS) || defined(TOPS20) # define PAD 5 #else # define PAD 0 #endif #ifdef NO_RENAME int rename OF((ZCONST char *, ZCONST char *)); #endif /* Local functions */ local int optionerr OF((char *, ZCONST char *, int, int)); local unsigned long get_shortopt OF((char **, int, int *, int *, char **, int *, int)); local unsigned long get_longopt OF((char **, int, int *, int *, char **, int *, int)); #ifdef UNICODE_SUPPORT local int utf8_char_bytes OF((ZCONST char *utf8)); local long ucs4_char_from_utf8 OF((ZCONST char **utf8 )); local int utf8_from_ucs4_char OF((char *utf8buf, ulg ch)); local int utf8_to_ucs4_string OF((ZCONST char *utf8, ulg *usc4buf, int buflen)); local int ucs4_string_to_utf8 OF((ZCONST ulg *ucs4, char *utf8buf, int buflen)); #if 0 local int utf8_chars OF((ZCONST char *utf8)); #endif #endif /* UNICODE_SUPPORT */ #ifndef UTIL /* the companion #endif is a bit of ways down ... */ local int fqcmp OF((ZCONST zvoid *, ZCONST zvoid *)); local int fqcmpz OF((ZCONST zvoid *, ZCONST zvoid *)); /* Local module level variables. */ char *label = NULL; /* global, but only used in `system'.c */ local z_stat zipstatb; /* now use z_stat globally - 7/24/04 EG */ #if defined(UNICODE_SUPPORT) && defined(WIN32) local zw_stat zipstatbw; #endif #if (!defined(MACOS) && !defined(WINDLL)) local int zipstate = -1; #else int zipstate; #endif /* -1 unknown, 0 old zip file exists, 1 new zip file */ #if 0 char *getnam(n, fp) char *n; /* where to put name (must have >=FNMAX+1 bytes) */ #endif /* converted to return string pointer from malloc to avoid size limitation - 11/8/04 EG */ #define GETNAM_MAX 9000 /* hopefully big enough for now */ char *getnam(fp) FILE *fp; /* Read a \n or \r delimited name from stdin into n, and return n. If EOF, then return NULL. Also, if problem return NULL. */ { char name[GETNAM_MAX + 1]; int c; /* last character read */ char *p; /* pointer into name area */ p = name; while ((c = getc(fp)) == '\n' || c == '\r') ; if (c == EOF) return NULL; do { if (p - name >= GETNAM_MAX) return NULL; *p++ = (char) c; c = getc(fp); } while (c != EOF && (c != '\n' && c != '\r')); #ifdef WIN32 /* * WIN32 strips off trailing spaces and periods in filenames * XXX what about a filename that only consists of spaces ? * Answer: on WIN32, a filename must contain at least one non-space char */ while (p > name) { if ((c = p[-1]) != ' ' && c != '.') break; --p; } #endif *p = 0; /* malloc a copy */ if ((p = malloc(strlen(name) + 1)) == NULL) { return NULL; } strcpy(p, name); return p; } struct flist far *fexpel(f) struct flist far *f; /* entry to delete */ /* Delete the entry *f in the doubly-linked found list. Return pointer to next entry to allow stepping through list. */ { struct flist far *t; /* temporary variable */ t = f->nxt; *(f->lst) = t; /* point last to next, */ if (t != NULL) t->lst = f->lst; /* and next to last */ if (f->name != NULL) /* free memory used */ free((zvoid *)(f->name)); if (f->zname != NULL) free((zvoid *)(f->zname)); if (f->iname != NULL) free((zvoid *)(f->iname)); #ifdef UNICODE_SUPPORT if (f->uname) free((zvoid *)f->uname); # ifdef WIN32 if (f->namew) free((zvoid *)f->namew); if (f->inamew) free((zvoid *)f->inamew); if (f->znamew) free((zvoid *)f->znamew); # endif #endif farfree((zvoid far *)f); fcount--; /* decrement count */ return t; /* return pointer to next */ } local int fqcmp(a, b) ZCONST zvoid *a, *b; /* pointers to pointers to found entries */ /* Used by qsort() to compare entries in the found list by name. */ { return strcmp((*(struct flist far **)a)->name, (*(struct flist far **)b)->name); } local int fqcmpz(a, b) ZCONST zvoid *a, *b; /* pointers to pointers to found entries */ /* Used by qsort() to compare entries in the found list by iname. */ { return strcmp((*(struct flist far **)a)->iname, (*(struct flist far **)b)->iname); } char *last(p, c) char *p; /* sequence of path components */ int c; /* path components separator character */ /* Return a pointer to the start of the last path component. For a directory * name terminated by the character in c, the return value is an empty string. */ { char *t; /* temporary variable */ if ((t = strrchr(p, c)) != NULL) return t + 1; else #ifndef AOS_VS return p; #else /* We want to allow finding of end of path in either AOS/VS-style pathnames * or Unix-style pathnames. This presents a few little problems ... */ { if (*p == '=' || *p == '^') /* like ./ and ../ respectively */ return p + 1; else return p; } #endif } #if defined(UNICODE_SUPPORT) && defined(WIN32) wchar_t *lastw(pw, c) wchar_t *pw; /* sequence of path components */ wchar_t c; /* path components separator character */ /* Return a pointer to the start of the last path component. For a directory * name terminated by the character in c, the return value is an empty string. */ { wchar_t *tw; /* temporary variable */ if ((tw = wcsrchr(pw, c)) != NULL) return tw + 1; else # ifndef AOS_VS return pw; # else /* We want to allow finding of end of path in either AOS/VS-style pathnames * or Unix-style pathnames. This presents a few little problems ... */ { if (*pw == (wchar_t)'=' || *pw == (wchar_t)'^') /* like ./ and ../ respectively */ return pw + 1; else return pw; } # endif } #endif char *msname(n) char *n; /* Reduce all path components to MSDOS upper case 8.3 style names. */ { int c; /* current character */ int f; /* characters in current component */ char *p; /* source pointer */ char *q; /* destination pointer */ p = q = n; f = 0; while ((c = (unsigned char)*POSTINCSTR(p)) != 0) if (c == ' ' || c == ':' || c == '"' || c == '*' || c == '+' || c == ',' || c == ';' || c == '<' || c == '=' || c == '>' || c == '?' || c == '[' || c == ']' || c == '|') continue; /* char is discarded */ else if (c == '/') { *POSTINCSTR(q) = (char)c; f = 0; /* new component */ } #ifdef __human68k__ else if (ismbblead(c) && *p) { if (f == 7 || f == 11) f++; else if (*p && f < 12 && f != 8) { *q++ = c; *q++ = *p++; f += 2; } } #endif /* __human68k__ */ else if (c == '.') { if (f == 0) continue; /* leading dots are discarded */ else if (f < 9) { *POSTINCSTR(q) = (char)c; f = 9; /* now in file type */ } else f = 12; /* now just excess characters */ } else if (f < 12 && f != 8) { f += CLEN(p); /* do until end of name or type */ *POSTINCSTR(q) = (char)(to_up(c)); } *q = 0; return n; } #ifdef UNICODE_SUPPORT wchar_t *msnamew(nw) wchar_t *nw; /* Reduce all path components to MSDOS upper case 8.3 style names. */ { wchar_t c; /* current character */ int f; /* characters in current component */ wchar_t *pw; /* source pointer */ wchar_t *qw; /* destination pointer */ pw = qw = nw; f = 0; while ((c = (unsigned char)*pw++) != 0) if (c == ' ' || c == ':' || c == '"' || c == '*' || c == '+' || c == ',' || c == ';' || c == '<' || c == '=' || c == '>' || c == '?' || c == '[' || c == ']' || c == '|') continue; /* char is discarded */ else if (c == '/') { *qw++ = c; f = 0; /* new component */ } #ifdef __human68k__ else if (ismbblead(c) && *pw) { if (f == 7 || f == 11) f++; else if (*pw && f < 12 && f != 8) { *qw++ = c; *qw++ = *pw++; f += 2; } } #endif /* __human68k__ */ else if (c == '.') { if (f == 0) continue; /* leading dots are discarded */ else if (f < 9) { *qw++ = c; f = 9; /* now in file type */ } else f = 12; /* now just excess characters */ } else if (f < 12 && f != 8) { f++; /* do until end of name or type */ *qw++ = towupper(c); } *qw = 0; return nw; } #endif int proc_archive_name(n, caseflag) char *n; /* name to process */ int caseflag; /* true to force case-sensitive match */ /* Process a name or sh expression in existing archive to operate on (or exclude). Return an error code in the ZE_ class. */ { int m; /* matched flag */ char *p; /* path for recursion */ struct zlist far *z; /* steps through zfiles list */ if (strcmp(n, "-") == 0) { /* if compressing stdin */ zipwarn("Cannot select stdin when selecting archive entries", ""); return ZE_MISS; } else { /* Search for shell expression in zip file */ p = ex2in(n, 0, (int *)NULL); /* shouldn't affect matching chars */ m = 1; for (z = zfiles; z != NULL; z = z->nxt) { if (MATCH(p, z->iname, caseflag)) { z->mark = pcount ? filter(z->zname, caseflag) : 1; if (verbose) fprintf(mesg, "zip diagnostic: %scluding %s\n", z->mark ? "in" : "ex", z->oname); m = 0; } } #ifdef UNICODE_SUPPORT /* also check escaped Unicode names */ for (z = zfiles; z != NULL; z = z->nxt) { if (z->zuname) { #ifdef WIN32 /* It seems something is lost in going from a listed name from zip -su in a console window to using that name in a command line. This kluge may fix it and just takes zuname, converts to oem (i.e. ouname), then converts it back which ends up not the same as started with. */ char *zuname = z->wuname; #else char *zuname = z->zuname; #endif if (MATCH(p, zuname, caseflag)) { z->mark = pcount ? filter(zuname, caseflag) : 1; if (verbose) { fprintf(mesg, "zip diagnostic: %scluding %s\n", z->mark ? "in" : "ex", z->oname); fprintf(mesg, " Escaped Unicode: %s\n", z->ouname); } m = 0; } } } #endif free((zvoid *)p); return m ? ZE_MISS : ZE_OK; } } int check_dup() /* Sort the found list and remove duplicates. Return an error code in the ZE_ class. */ { struct flist far *f; /* steps through found linked list */ extent j, k; /* indices for s */ struct flist far **s; /* sorted table */ struct flist far **nodup; /* sorted table without duplicates */ /* sort found list, remove duplicates */ if (fcount) { extent fl_size = fcount * sizeof(struct flist far *); if ((fl_size / sizeof(struct flist far *)) != fcount || (s = (struct flist far **)malloc(fl_size)) == NULL) return ZE_MEM; for (j = 0, f = found; f != NULL; f = f->nxt) s[j++] = f; /* Check names as given (f->name) */ qsort((char *)s, fcount, sizeof(struct flist far *), fqcmp); for (k = j = fcount - 1; j > 0; j--) if (strcmp(s[j - 1]->name, s[j]->name) == 0) /* remove duplicate entry from list */ fexpel(s[j]); /* fexpel() changes fcount */ else /* copy valid entry into destination position */ s[k--] = s[j]; s[k] = s[0]; /* First entry is always valid */ nodup = &s[k]; /* Valid entries are at end of array s */ /* sort only valid items and check for unique internal names (f->iname) */ qsort((char *)nodup, fcount, sizeof(struct flist far *), fqcmpz); for (j = 1; j < fcount; j++) if (strcmp(nodup[j - 1]->iname, nodup[j]->iname) == 0) { char tempbuf[FNMAX+4081]; sprintf(errbuf, " first full name: %s\n", nodup[j - 1]->name); sprintf(tempbuf, " second full name: %s\n", nodup[j]->name); strcat(errbuf, " "); strcat(errbuf, tempbuf); #ifdef EBCDIC strtoebc(nodup[j]->iname, nodup[j]->iname); #endif sprintf(tempbuf, "name in zip file repeated: %s", nodup[j]->iname); strcat(errbuf, " "); strcat(errbuf, tempbuf); if (pathput == 0) { strcat(errbuf, "\n this may be a result of using -j"); } #ifdef EBCDIC strtoasc(nodup[j]->iname, nodup[j]->iname); #endif zipwarn(errbuf, ""); return ZE_PARMS; } free((zvoid *)s); } return ZE_OK; } int filter(name, casesensitive) char *name; int casesensitive; /* Scan the -R, -i and -x lists for matches to the given name. Return TRUE if the name must be included, FALSE otherwise. Give precedence to -x over -i and -R. Note that if both R and i patterns are given then must have a match for both. This routine relies on the following global variables: patterns array of match pattern structures pcount total number of patterns icount number of -i patterns Rcount number of -R patterns These data are set up by the command line parsing code. */ { unsigned int n; int slashes; char *p, *q; /* without -i patterns, every name matches the "-i select rules" */ int imatch = (icount == 0); /* without -R patterns, every name matches the "-R select rules" */ int Rmatch = (Rcount == 0); if (pcount == 0) return TRUE; for (n = 0; n < pcount; n++) { if (!patterns[n].zname[0]) /* it can happen... */ continue; p = name; switch (patterns[n].select) { case 'R': if (Rmatch) /* one -R match is sufficient, skip this pattern */ continue; /* With -R patterns, if the pattern has N path components (that is, N-1 slashes), then we test only the last N components of name. */ slashes = 0; for (q = patterns[n].zname; (q = MBSCHR(q, '/')) != NULL; MB_NEXTCHAR(q)) slashes++; /* The name may have M path components (M-1 slashes) */ for (q = p; (q = MBSCHR(q, '/')) != NULL; MB_NEXTCHAR(q)) slashes--; /* Now, "slashes" contains the difference "N-M" between the number of path components in the pattern (N) and in the name (M). */ if (slashes < 0) /* We found "M > N" --> skip the first (M-N) path components of the name. */ for (q = p; (q = MBSCHR(q, '/')) != NULL; MB_NEXTCHAR(q)) if (++slashes == 0) { p = q + 1; /* q points at '/', mblen("/") is 1 */ break; } break; case 'i': if (imatch) /* one -i match is sufficient, skip this pattern */ continue; break; } if (MATCH(patterns[n].zname, p, casesensitive)) { switch (patterns[n].select) { case 'x': /* The -x match takes precedence over everything else */ return FALSE; case 'R': Rmatch = TRUE; break; default: /* this must be a type -i match */ imatch = TRUE; break; } } } return imatch && Rmatch; } #ifdef UNICODE_SUPPORT # ifdef WIN32 int newnamew(namew, isdir, casesensitive) wchar_t *namew; /* name to add (or exclude) */ int isdir; /* true for a directory */ int casesensitive; /* true for case-sensitive matching */ /* Add (or exclude) the name of an existing disk file. Return an error code in the ZE_ class. */ { wchar_t *inamew = NULL; /* internal name */ wchar_t *znamew = NULL; /* external version of iname */ wchar_t *undosmw = NULL; /* zname version with "-j" and "-k" options disabled */ char *oname = NULL; /* iname converted for display */ char *name = NULL; char *iname = NULL; char *zname = NULL; char *zuname = NULL; char *undosm = NULL; struct flist far *f; /* where in found, or new found entry */ struct zlist far *z; /* where in zfiles (if found) */ int dosflag; /* Scanning files ... * * After 5 seconds output Scanning files... * then a dot every 2 seconds */ if (noisy) { /* If find files then output message after delay */ if (scan_count == 0) { time_t current = time(NULL); scan_start = current; } scan_count++; if (scan_count % 100 == 0) { time_t current = time(NULL); if (current - scan_start > scan_delay) { if (scan_last == 0) { zipmessage_nl("Scanning files ", 0); scan_last = current; } if (current - scan_last > scan_dot_time) { scan_last = current; fprintf(mesg, "."); fflush(mesg); } } } } /* Search for name in zip file. If there, mark it, else add to list of new names to do (or remove from that list). */ if ((inamew = ex2inw(namew, isdir, &dosflag)) == NULL) return ZE_MEM; /* Discard directory names with zip -rj */ if (*inamew == (wchar_t)'\0') { /* If extensions needs to be swapped, we will have empty directory names instead of the original directory. For example, zipping 'c.', 'c.main' should zip only 'main.c' while 'c.' will be converted to '\0' by ex2in. */ if (pathput && !recurse) error("empty name without -j or -r"); free((zvoid *)inamew); return ZE_OK; } if (dosflag || !pathput) { int save_dosify = dosify, save_pathput = pathput; dosify = 0; pathput = 1; /* zname is temporarly mis-used as "undosmode" iname pointer */ if ((znamew = ex2inw(namew, isdir, NULL)) != NULL) { undosmw = in2exw(znamew); free(znamew); } dosify = save_dosify; pathput = save_pathput; } if ((znamew = in2exw(inamew)) == NULL) return ZE_MEM; /* Convert names from wchar_t to char */ name = wchar_to_local_string(namew); iname = wchar_to_local_string(inamew); zname = wchar_to_local_string(znamew); oname = local_to_display_string(zname); zuname = wchar_to_local_string(znamew); if (undosmw == NULL) undosmw = znamew; undosm = wchar_to_local_string(undosmw); if ((z = zsearch(zuname)) != NULL) { if (pcount && !filter(undosm, casesensitive)) { /* Do not clear z->mark if "exclude", because, when "dosify || !pathput" * is in effect, two files with different filter options may hit the * same z entry. */ if (verbose) fprintf(mesg, "excluding %s\n", oname); } else { z->mark = 1; if ((z->name = malloc(strlen(name) + 1 + PAD)) == NULL) { if (undosmw != znamew) free(undosmw); if (undosm) free(undosm); if (inamew) free(inamew); if (znamew) free(znamew); if (name) free(name); if (iname) free(iname); if (zname) free(zname); if (oname) free(oname); if (zuname) free(zuname); return ZE_MEM; } strcpy(z->name, name); z->oname = oname; oname = NULL; z->dosflag = dosflag; #ifdef FORCE_NEWNAME free((zvoid *)(z->iname)); z->iname = iname; iname = NULL; #else /* Better keep the old name. Useful when updating on MSDOS a zip file * made on Unix. */ #endif /* ? FORCE_NEWNAME */ } if ((z->namew = (wchar_t *)malloc((wcslen(namew) + 1) * sizeof(wchar_t))) == NULL) { if (undosmw != znamew) free(undosmw); if (undosm) free(undosm); if (inamew) free(inamew); if (znamew) free(znamew); if (name) free(name); if (iname) free(iname); if (zname) free(zname); if (oname) free(oname); if (zuname) free(zuname); return ZE_MEM; } wcscpy(z->namew, namew); z->inamew = inamew; inamew = NULL; z->znamew = znamew; znamew = NULL; z->uname = wchar_to_utf8_string(z->inamew); if (name == label) { label = z->name; } } else if (pcount == 0 || filter(undosm, casesensitive)) { /* Check that we are not adding the zip file to itself. This * catches cases like "zip -m foo ../dir/foo.zip". */ /* Version of stat() for CMS/MVS isn't complete enough to see if */ /* files match. Just let ZIP.C compare the filenames. That's good */ /* enough for CMS anyway since there aren't paths to worry about. */ zw_stat statbw; /* need for wide stat */ wchar_t *zipfilew = local_to_wchar_string(zipfile); if (zipstate == -1) zipstate = strcmp(zipfile, "-") != 0 && zwstat(zipfilew, &zipstatbw) == 0; free(zipfilew); if (zipstate == 1 && (statbw = zipstatbw, zwstat(namew, &statbw) == 0 && zipstatbw.st_mode == statbw.st_mode && zipstatbw.st_ino == statbw.st_ino && zipstatbw.st_dev == statbw.st_dev && zipstatbw.st_uid == statbw.st_uid && zipstatbw.st_gid == statbw.st_gid && zipstatbw.st_size == statbw.st_size && zipstatbw.st_mtime == statbw.st_mtime && zipstatbw.st_ctime == statbw.st_ctime)) { /* Don't compare a_time since we are reading the file */ if (verbose) fprintf(mesg, "file matches zip file -- skipping\n"); if (undosmw != znamew) free(undosmw); if (undosm) free(undosm); if (inamew) free(inamew); if (znamew) free(znamew); if (name) free(name); if (iname) free(iname); if (zname) free(zname); if (oname) free(oname); if (zuname) free(zuname); return ZE_OK; } /* allocate space and add to list */ if ((f = (struct flist far *)farmalloc(sizeof(struct flist))) == NULL || fcount + 1 < fcount || (f->name = malloc(strlen(name) + 1 + PAD)) == NULL) { if (f != NULL) farfree((zvoid far *)f); if (undosmw != znamew) free(undosmw); if (undosm) free(undosm); if (inamew) free(inamew); if (znamew) free(znamew); if (name) free(name); if (iname) free(iname); if (zname) free(zname); if (oname) free(oname); if (zuname) free(zuname); return ZE_MEM; } if (undosmw != znamew) free((zvoid *)undosmw); strcpy(f->name, name); f->iname = iname; iname = NULL; f->zname = zname; zname = NULL; /* Unicode */ if ((f->namew = (wchar_t *)malloc((wcslen(namew) + 1) * sizeof(wchar_t))) == NULL) { if (f != NULL) farfree((zvoid far *)f); if (undosmw != znamew) free(undosmw); if (undosm) free(undosm); if (inamew) free(inamew); if (znamew) free(znamew); if (name) free(name); if (iname) free(iname); if (zname) free(zname); if (oname) free(oname); if (zuname) free(zuname); return ZE_MEM; } wcscpy(f->namew, namew); f->znamew = znamew; znamew = NULL; f->uname = wchar_to_utf8_string(inamew); f->inamew = inamew; inamew = NULL; f->oname = oname; oname = NULL; f->dosflag = dosflag; *fnxt = f; f->lst = fnxt; f->nxt = NULL; fnxt = &f->nxt; fcount++; if (name == label) { label = f->name; } } if (undosm) free(undosm); if (inamew) free(inamew); if (znamew) free(znamew); if (name) free(name); if (iname) free(iname); if (zname) free(zname); if (oname) free(oname); if (zuname) free(zuname); return ZE_OK; } # endif #endif int newname(name, isdir, casesensitive) char *name; /* name to add (or exclude) */ int isdir; /* true for a directory */ int casesensitive; /* true for case-sensitive matching */ /* Add (or exclude) the name of an existing disk file. Return an error code in the ZE_ class. */ { char *iname, *zname; /* internal name, external version of iname */ char *undosm; /* zname version with "-j" and "-k" options disabled */ char *oname; /* iname converted for display */ struct flist far *f; /* where in found, or new found entry */ struct zlist far *z; /* where in zfiles (if found) */ int dosflag; /* Scanning files ... * * After 5 seconds output Scanning files... * then a dot every 2 seconds */ if (noisy) { /* If find files then output message after delay */ if (scan_count == 0) { time_t current = time(NULL); scan_start = current; } scan_count++; if (scan_count % 100 == 0) { time_t current = time(NULL); if (current - scan_start > scan_delay) { if (scan_last == 0) { zipmessage_nl("Scanning files ", 0); scan_last = current; } if (current - scan_last > scan_dot_time) { scan_last = current; fprintf(mesg, "."); fflush(mesg); } } } } /* Search for name in zip file. If there, mark it, else add to list of new names to do (or remove from that list). */ if ((iname = ex2in(name, isdir, &dosflag)) == NULL) return ZE_MEM; /* Discard directory names with zip -rj */ if (*iname == '\0') { #ifndef AMIGA /* A null string is a legitimate external directory name in AmigaDOS; also, * a command like "zip -r zipfile FOO:" produces an empty internal name. */ # ifndef RISCOS /* If extensions needs to be swapped, we will have empty directory names instead of the original directory. For example, zipping 'c.', 'c.main' should zip only 'main.c' while 'c.' will be converted to '\0' by ex2in. */ if (pathput && !recurse) error("empty name without -j or -r"); # endif /* !RISCOS */ #endif /* !AMIGA */ free((zvoid *)iname); return ZE_OK; } undosm = NULL; if (dosflag || !pathput) { int save_dosify = dosify, save_pathput = pathput; dosify = 0; pathput = 1; /* zname is temporarly mis-used as "undosmode" iname pointer */ if ((zname = ex2in(name, isdir, NULL)) != NULL) { undosm = in2ex(zname); free(zname); } dosify = save_dosify; pathput = save_pathput; } if ((zname = in2ex(iname)) == NULL) return ZE_MEM; #ifdef UNICODE_SUPPORT /* Convert name to display or OEM name */ oname = local_to_display_string(iname); #else if ((oname = malloc(strlen(zname) + 1)) == NULL) return ZE_MEM; strcpy(oname, zname); #endif if (undosm == NULL) undosm = zname; if ((z = zsearch(zname)) != NULL) { if (pcount && !filter(undosm, casesensitive)) { /* Do not clear z->mark if "exclude", because, when "dosify || !pathput" * is in effect, two files with different filter options may hit the * same z entry. */ if (verbose) fprintf(mesg, "excluding %s\n", oname); free((zvoid *)iname); free((zvoid *)zname); } else { z->mark = 1; if ((z->name = malloc(strlen(name) + 1 + PAD)) == NULL) { if (undosm != zname) free((zvoid *)undosm); free((zvoid *)iname); free((zvoid *)zname); return ZE_MEM; } strcpy(z->name, name); z->oname = oname; z->dosflag = dosflag; #ifdef FORCE_NEWNAME free((zvoid *)(z->iname)); z->iname = iname; #else /* Better keep the old name. Useful when updating on MSDOS a zip file * made on Unix. */ free((zvoid *)iname); free((zvoid *)zname); #endif /* ? FORCE_NEWNAME */ } #if defined(UNICODE_SUPPORT) && defined(WIN32) z->namew = NULL; z->inamew = NULL; z->znamew = NULL; #endif if (name == label) { label = z->name; } } else if (pcount == 0 || filter(undosm, casesensitive)) { /* Check that we are not adding the zip file to itself. This * catches cases like "zip -m foo ../dir/foo.zip". */ #ifndef CMS_MVS /* Version of stat() for CMS/MVS isn't complete enough to see if */ /* files match. Just let ZIP.C compare the filenames. That's good */ /* enough for CMS anyway since there aren't paths to worry about. */ z_stat statb; /* now use structure z_stat and function zstat globally 7/24/04 EG */ if (zipstate == -1) zipstate = strcmp(zipfile, "-") != 0 && zstat(zipfile, &zipstatb) == 0; if (zipstate == 1 && (statb = zipstatb, zstat(name, &statb) == 0 && zipstatb.st_mode == statb.st_mode #ifdef VMS && memcmp(zipstatb.st_ino, statb.st_ino, sizeof(statb.st_ino)) == 0 && strcmp(zipstatb.st_dev, statb.st_dev) == 0 && zipstatb.st_uid == statb.st_uid #else /* !VMS */ && zipstatb.st_ino == statb.st_ino && zipstatb.st_dev == statb.st_dev && zipstatb.st_uid == statb.st_uid && zipstatb.st_gid == statb.st_gid #endif /* ?VMS */ && zipstatb.st_size == statb.st_size && zipstatb.st_mtime == statb.st_mtime && zipstatb.st_ctime == statb.st_ctime)) { /* Don't compare a_time since we are reading the file */ if (verbose) fprintf(mesg, "file matches zip file -- skipping\n"); if (undosm != zname) free((zvoid *)zname); if (undosm != iname) free((zvoid *)undosm); free((zvoid *)iname); free(oname); return ZE_OK; } #endif /* CMS_MVS */ /* allocate space and add to list */ if ((f = (struct flist far *)farmalloc(sizeof(struct flist))) == NULL || fcount + 1 < fcount || (f->name = malloc(strlen(name) + 1 + PAD)) == NULL) { if (f != NULL) farfree((zvoid far *)f); if (undosm != zname) free((zvoid *)undosm); free((zvoid *)iname); free((zvoid *)zname); free(oname); return ZE_MEM; } strcpy(f->name, name); f->iname = iname; f->zname = zname; #ifdef UNICODE_SUPPORT /* Unicode */ f->uname = local_to_utf8_string(iname); #ifdef WIN32 f->namew = NULL; f->inamew = NULL; f->znamew = NULL; if (strcmp(f->name, "-") == 0) { f->namew = local_to_wchar_string(f->name); } #endif #endif f->oname = oname; f->dosflag = dosflag; *fnxt = f; f->lst = fnxt; f->nxt = NULL; fnxt = &f->nxt; fcount++; if (name == label) { label = f->name; } } if (undosm != zname) free((zvoid *)undosm); return ZE_OK; } ulg dostime(y, n, d, h, m, s) int y; /* year */ int n; /* month */ int d; /* day */ int h; /* hour */ int m; /* minute */ int s; /* second */ /* Convert the date y/n/d and time h:m:s to a four byte DOS date and time (date in high two bytes, time in low two bytes allowing magnitude comparison). */ { return y < 1980 ? DOSTIME_MINIMUM /* dostime(1980, 1, 1, 0, 0, 0) */ : (((ulg)y - 1980) << 25) | ((ulg)n << 21) | ((ulg)d << 16) | ((ulg)h << 11) | ((ulg)m << 5) | ((ulg)s >> 1); } ulg unix2dostime(t) time_t *t; /* unix time to convert */ /* Return the Unix time t in DOS format, rounded up to the next two second boundary. */ { time_t t_even; struct tm *s; /* result of localtime() */ t_even = (time_t)(((unsigned long)(*t) + 1) & (~1)); /* Round up to even seconds. */ s = localtime(&t_even); /* Use local time since MSDOS does. */ if (s == (struct tm *)NULL) { /* time conversion error; use current time as emergency value (assuming that localtime() does at least accept this value!) */ t_even = (time_t)(((unsigned long)time(NULL) + 1) & (~1)); s = localtime(&t_even); } return dostime(s->tm_year + 1900, s->tm_mon + 1, s->tm_mday, s->tm_hour, s->tm_min, s->tm_sec); } int issymlnk(a) ulg a; /* Attributes returned by filetime() */ /* Return true if the attributes are those of a symbolic link */ { #ifndef QDOS #ifdef S_IFLNK #ifdef __human68k__ int *_dos_importlnenv(void); if (_dos_importlnenv() == NULL) return 0; #endif return ((a >> 16) & S_IFMT) == S_IFLNK; #else /* !S_IFLNK */ return (int)a & 0; /* avoid warning on unused parameter */ #endif /* ?S_IFLNK */ #else return 0; #endif } #endif /* !UTIL */ #if (!defined(UTIL) && !defined(ZP_NEED_GEN_D2U_TIME)) /* There is no need for dos2unixtime() in the ZipUtils' code. */ # define ZP_NEED_GEN_D2U_TIME #endif #if ((defined(OS2) || defined(VMS)) && defined(ZP_NEED_GEN_D2U_TIME)) /* OS/2 and VMS use a special solution to handle time-stams of files. */ # undef ZP_NEED_GEN_D2U_TIME #endif #if (defined(W32_STATROOT_FIX) && !defined(ZP_NEED_GEN_D2U_TIME)) /* The Win32 stat()-bandaid to fix stat'ing root directories needs * dos2unixtime() to calculate the time-stamps. */ # define ZP_NEED_GEN_D2U_TIME #endif #ifdef ZP_NEED_GEN_D2U_TIME time_t dos2unixtime(dostime) ulg dostime; /* DOS time to convert */ /* Return the Unix time_t value (GMT/UTC time) for the DOS format (local) * time dostime, where dostime is a four byte value (date in most significant * word, time in least significant word), see dostime() function. */ { struct tm *t; /* argument for mktime() */ ZCONST time_t clock = time(NULL); t = localtime(&clock); t->tm_isdst = -1; /* let mktime() determine if DST is in effect */ /* Convert DOS time to UNIX time_t format */ t->tm_sec = (((int)dostime) << 1) & 0x3e; t->tm_min = (((int)dostime) >> 5) & 0x3f; t->tm_hour = (((int)dostime) >> 11) & 0x1f; t->tm_mday = (int)(dostime >> 16) & 0x1f; t->tm_mon = ((int)(dostime >> 21) & 0x0f) - 1; t->tm_year = ((int)(dostime >> 25) & 0x7f) + 80; return mktime(t); } #undef ZP_NEED_GEN_D2U_TIME #endif /* ZP_NEED_GEN_D2U_TIME */ #ifndef MACOS int destroy(f) char *f; /* file to delete */ /* Delete the file *f, returning non-zero on failure. */ { return unlink(f); } int replace(d, s) char *d, *s; /* destination and source file names */ /* Replace file *d by file *s, removing the old *s. Return an error code in the ZE_ class. This function need not preserve the file attributes, this will be done by setfileattr() later. */ { z_stat t; /* results of stat() */ #if defined(CMS_MVS) /* cmsmvs.h defines FOPW_TEMP as memory(hiperspace). Since memory is * lost at end of run, always do copy instead of rename. */ int copy = 1; #else int copy = 0; #endif int d_exists; #if defined(VMS) || defined(CMS_MVS) /* stat() is broken on VMS remote files (accessed through Decnet). * This patch allows creation of remote zip files, but is not sufficient * to update them or compress remote files */ unlink(d); #else /* !(VMS || CMS_MVS) */ d_exists = (LSTAT(d, &t) == 0); if (d_exists) { /* * respect existing soft and hard links! */ if (t.st_nlink > 1 # ifdef S_IFLNK || (t.st_mode & S_IFMT) == S_IFLNK # endif ) copy = 1; else if (unlink(d)) return ZE_CREAT; /* Can't erase zip file--give up */ } #endif /* ?(VMS || CMS_MVS) */ #ifndef CMS_MVS if (!copy) { if (rename(s, d)) { /* Just move s on top of d */ copy = 1; /* failed ? */ #if !defined(VMS) && !defined(ATARI) && !defined(AZTEC_C) #if !defined(CMS_MVS) && !defined(RISCOS) && !defined(QDOS) /* For VMS, ATARI, AMIGA Aztec, VM_CMS, MVS, RISCOS, always assume that failure is EXDEV */ if (errno != EXDEV # ifdef THEOS && errno != EEXIST # else # ifdef ENOTSAM && errno != ENOTSAM /* Used at least on Turbo C */ # endif # endif ) return ZE_CREAT; #endif /* !CMS_MVS && !RISCOS */ #endif /* !VMS && !ATARI && !AZTEC_C */ } } #endif /* !CMS_MVS */ if (copy) { FILE *f, *g; /* source and destination files */ int r; /* temporary variable */ #ifdef RISCOS if (SWI_OS_FSControl_26(s,d,0xA1)!=NULL) { #endif /* Use zfopen for almost all opens where fopen is used. For most OS that support large files we use the 64-bit file environment and zfopen maps to fopen, but this allows tweeking ports that don't do that. 7/24/04 */ if ((f = zfopen(s, FOPR)) == NULL) { fprintf(mesg," replace: can't open %s\n", s); return ZE_TEMP; } if ((g = zfopen(d, FOPW)) == NULL) { fclose(f); return ZE_CREAT; } r = fcopy(f, g, (ulg)-1L); fclose(f); if (fclose(g) || r != ZE_OK) { unlink(d); return r ? (r == ZE_TEMP ? ZE_WRITE : r) : ZE_WRITE; } unlink(s); #ifdef RISCOS } #endif } return ZE_OK; } #endif /* !MACOS */ int getfileattr(f) char *f; /* file path */ /* Return the file attributes for file f or 0 if failure */ { #ifdef __human68k__ struct _filbuf buf; return _dos_files(&buf, f, 0xff) < 0 ? 0x20 : buf.atr; #else z_stat s; return SSTAT(f, &s) == 0 ? (int) s.st_mode : 0; #endif } int setfileattr(f, a) char *f; /* file path */ int a; /* attributes returned by getfileattr() */ /* Give the file f the attributes a, return non-zero on failure */ { #if defined(TOPS20) || defined (CMS_MVS) return 0; #else #ifdef __human68k__ return _dos_chmod(f, a) < 0 ? -1 : 0; #else return chmod(f, a); #endif #endif } /* tempname */ #ifndef VMS /* VMS-specific function is in VMS.C. */ char *tempname(zip) char *zip; /* path name of zip file to generate temp name for */ /* Return a temporary file name in its own malloc'ed space, using tempath. */ { char *t = zip; /* malloc'ed space for name (use zip to avoid warning) */ # ifdef CMS_MVS if ((t = malloc(strlen(tempath) + L_tmpnam + 2)) == NULL) return NULL; # ifdef VM_CMS tmpnam(t); /* Remove filemode and replace with tempath, if any. */ /* Otherwise A-disk is used by default */ *(strrchr(t, ' ')+1) = '\0'; if (tempath!=NULL) strcat(t, tempath); return t; # else /* !VM_CMS */ /* For MVS */ tmpnam(t); if (tempath != NULL) { int l1 = strlen(t); char *dot; if (*t == '\'' && *(t+l1-1) == '\'' && (dot = strchr(t, '.'))) { /* MVS and not OE. tmpnam() returns quoted string of 5 qualifiers. * First is HLQ, rest are timestamps. User can only replace HLQ. */ int l2 = strlen(tempath); if (strchr(tempath, '.') || l2 < 1 || l2 > 8) ziperr(ZE_PARMS, "On MVS and not OE, tempath (-b) can only be HLQ"); memmove(t+1+l2, dot, l1+1-(dot-t)); /* shift dot ready for new hlq */ memcpy(t+1, tempath, l2); /* insert new hlq */ } else { /* MVS and probably OE. tmpnam() returns filename based on TMPDIR, * no point in even attempting to change it. User should modify TMPDIR * instead. */ zipwarn("MVS, assumed to be OE, change TMPDIR instead of option -b: ", tempath); } } return t; # endif /* !VM_CMS */ # else /* !CMS_MVS */ # ifdef TANDEM char cur_subvol [FILENAME_MAX]; char temp_subvol [FILENAME_MAX]; char *zptr; char *ptr; char *cptr = &cur_subvol[0]; char *tptr = &temp_subvol[0]; short err; FILE *tempf; int attempts; t = (char *)malloc(NAMELEN); /* malloc here as you cannot free */ /* tmpnam allocated storage later */ zptr = strrchr(zip, TANDEM_DELIMITER); if (zptr != NULL) { /* ZIP file specifies a Subvol so make temp file there so it can just be renamed at end */ *tptr = *cptr = '\0'; strcat(cptr, getenv("DEFAULTS")); strncat(tptr, zip, _min(FILENAME_MAX, (zptr - zip)) ); /* temp subvol */ strncat(t, zip, _min(NAMELEN, ((zptr - zip) + 1)) ); /* temp stem */ err = chvol(tptr); ptr = t + strlen(t); /* point to end of stem */ } else ptr = t; /* If two zips are running in same subvol then we can get contention problems with the temporary filename. As a work around we attempt to create the file here, and if it already exists we get a new temporary name */ attempts = 0; do { attempts++; tmpnam(ptr); /* Add filename */ tempf = zfopen(ptr, FOPW_TMP); /* Attempt to create file */ } while (tempf == NULL && attempts < 100); if (attempts >= 100) { ziperr(ZE_TEMP, "Could not get unique temp file name"); } fclose(tempf); if (zptr != NULL) { err = chvol(cptr); /* Put ourself back to where we came in */ } return t; # else /* !CMS_MVS && !TANDEM */ /* * Do something with TMPDIR, TMP, TEMP ???? */ if (tempath != NULL) { if ((t = malloc(strlen(tempath) + 12)) == NULL) return NULL; strcpy(t, tempath); # if (!defined(VMS) && !defined(TOPS20)) # ifdef MSDOS { char c = (char)lastchar(t); if (c != '/' && c != ':' && c != '\\') strcat(t, "/"); } # else # ifdef AMIGA { char c = (char)lastchar(t); if (c != '/' && c != ':') strcat(t, "/"); } # else /* !AMIGA */ # ifdef RISCOS if (lastchar(t) != '.') strcat(t, "."); # else /* !RISCOS */ # ifdef QDOS if (lastchar(t) != '_') strcat(t, "_"); # else if (lastchar(t) != '/') strcat(t, "/"); # endif /* ?QDOS */ # endif /* ?RISCOS */ # endif /* ?AMIGA */ # endif /* ?MSDOS */ # endif /* !VMS && !TOPS20 */ } else { if ((t = malloc(12)) == NULL) return NULL; *t = 0; } # ifdef NO_MKTEMP { char *p = t + strlen(t); sprintf(p, "%08lx", (ulg)time(NULL)); return t; } # else strcat(t, "ziXXXXXX"); /* must use lowercase for Linux dos file system */ # if defined(UNIX) && !defined(NO_MKSTEMP) /* tempname should not be called */ return t; # else return mktemp(t); # endif # endif /* NO_MKTEMP */ # endif /* TANDEM */ # endif /* CMS_MVS */ } #endif /* !VMS */ int fcopy(f, g, n) FILE *f, *g; /* source and destination files */ /* now use uzoff_t for all file sizes 5/14/05 CS */ uzoff_t n; /* number of bytes to copy or -1 for all */ /* Copy n bytes from file *f to file *g, or until EOF if (zoff_t)n == -1. Return an error code in the ZE_ class. */ { char *b; /* malloc'ed buffer for copying */ extent k; /* result of fread() */ uzoff_t m; /* bytes copied so far */ if ((b = malloc(CBSZ)) == NULL) return ZE_MEM; m = 0; while (n == (uzoff_t)(-1L) || m < n) { if ((k = fread(b, 1, n == (uzoff_t)(-1) ? CBSZ : (n - m < CBSZ ? (extent)(n - m) : CBSZ), f)) == 0) { if (ferror(f)) { free((zvoid *)b); return ZE_READ; } else break; } if (fwrite(b, 1, k, g) != k) { free((zvoid *)b); fprintf(mesg," fcopy: write error\n"); return ZE_TEMP; } m += k; } free((zvoid *)b); return ZE_OK; } /* from zipfile.c */ #ifdef THEOS /* Macros cause stack overflow in compiler */ ush SH(uch* p) { return ((ush)(uch)((p)[0]) | ((ush)(uch)((p)[1]) << 8)); } ulg LG(uch* p) { return ((ulg)(SH(p)) | ((ulg)(SH((p)+2)) << 16)); } #else /* !THEOS */ /* Macros for converting integers in little-endian to machine format */ # define SH(a) ((ush)(((ush)(uch)(a)[0]) | (((ush)(uch)(a)[1]) << 8))) # define LG(a) ((ulg)SH(a) | ((ulg)SH((a)+2) << 16)) # ifdef ZIP64_SUPPORT /* zip64 support 08/31/2003 R.Nausedat */ # define LLG(a) ((zoff_t)LG(a) | ((zoff_t)LG((a)+4) << 32)) # endif #endif /* ?THEOS */ /* always copies from global in_file to global output file y */ int bfcopy(n) /* now use uzoff_t for all file sizes 5/14/05 CS */ uzoff_t n; /* number of bytes to copy or -1 for all */ /* Copy n bytes from in_file to out_file, or until EOF if (zoff_t)n == -1. Normally we have the compressed size from either the central directory entry or the local header. If n != -1 and EOF, close current split and open next and continue copying. If n == -2, copy until find the extended header (data descriptor). Only used for -FF when no size available. If fix == 1 calculate CRC of input entry and verify matches. If fix == 2 and this entry using data descriptor keep a sliding window in the buffer for looking for signature. Return an error code in the ZE_ class. */ { char *b; /* malloc'ed buffer for copying */ extent k; /* result of fread() */ uzoff_t m; /* bytes copied so far */ extent brd; /* bytes to read */ zoff_t data_start = 0; zoff_t des_start = 0; char *split_path; extent kk; int i; char sbuf[4]; /* buffer for sliding signature window for fix = 2 */ int des = 0; /* this entry has data descriptor to find */ if ((b = malloc(CBSZ)) == NULL) return ZE_MEM; if (copy_only && !display_globaldots) { /* initialize dot count */ dot_count = -1; } if (fix == 2 && n == (uzoff_t) -2) { data_start = zftello(in_file); for (kk = 0; kk < 4; kk++) sbuf[kk] = 0; des = 1; } des_good = 0; m = 0; while (des || n == (uzoff_t)(-1L) || m < n) { if (des || n == (uzoff_t)(-1)) brd = CBSZ; else brd = (n - m < CBSZ ? (extent)(n - m) : CBSZ); des_start = zftello(in_file); if ((k = fread(b, 1, brd, in_file)) == 0) { if (fix == 2 && k < brd) { free((zvoid *)b); return ZE_READ; } else if (ferror(in_file)) { free((zvoid *)b); return ZE_READ; } else { break; } } /* end at extended local header (data descriptor) signature */ if (des) { des_crc = 0; des_csize = 0; des_usize = 0; /* If first 4 bytes in buffer are data descriptor signature then try to read the data descriptor. If not, scan for signature and break if found, let bfwrite flush the data and then next read should put the data descriptor at the beginning of the buffer. */ if ( (b[0] != 0x50 /*'P' except EBCDIC*/ || b[1] != 0x4b /*'K' except EBCDIC*/ || b[2] != '\07' || b[3] != '\010')) { /* buffer is not start of data descriptor */ for (kk = 0; kk < k; kk++) { /* add byte to end of sbuf */ for (i = 0; i < 3; i++) sbuf[i] = sbuf[i + 1]; sbuf[3] = b[kk]; /* see if this is signature */ if ( (sbuf[0] == 0x50 /*'P' except EBCDIC*/ && sbuf[1] == 0x4b /*'K' except EBCDIC*/ && sbuf[2] == '\07' && sbuf[3] == '\010')) { kk -= 3; if (zfseeko(in_file, bytes_this_split + kk, SEEK_SET) != 0) { /* seek error */ ZIPERR(ZE_READ, "seek failed reading descriptor"); } des_start = zftello(in_file); k = kk; break; } } } else /* signature at start of buffer */ { des_good = 0; #ifdef ZIP64_SUPPORT if (zip64_entry) { /* read Zip64 data descriptor */ if (k < 24) { /* not enough bytes, so can't be data descriptor as data descriptors can't be split across splits */ } else { /* read the Zip64 descriptor */ des_crc = LG(b + 4); des_csize = LLG(b + 8); des_usize = LLG(b + 16); /* if this is the right data descriptor then the sizes should match */ if ((uzoff_t)des_start - (uzoff_t)data_start != des_csize) { /* apparently this signature does not go with this data so skip */ /* write out signature as data */ k = 4; if (zfseeko(in_file, des_start + k, SEEK_SET) != 0) { /* seek error */ ZIPERR(ZE_READ, "seek failed reading descriptor"); } if (bfwrite(b, 1, k, BFWRITE_DATA) != k) { free((zvoid *)b); fprintf(mesg," fcopy: write error\n"); return ZE_TEMP; } m += k; continue; } else { /* apparently this is the correct data descriptor */ /* we should check the CRC but would need to inflate the data */ /* skip descriptor as will write out later */ des_good = 1; k = 24; data_start = zftello(in_file); if (zfseeko(in_file, des_start + k, SEEK_SET) != 0) { /* seek error */ ZIPERR(ZE_READ, "seek failed reading descriptor"); } data_start = zftello(in_file); } } } else #endif { /* read standard data descriptor */ if (k < 16) { /* not enough bytes, so can't be data descriptor as data descriptors can't be split across splits */ } else { /* read the descriptor */ des_crc = LG(b + 4); des_csize = LG(b + 8); des_usize = LG(b + 12); /* if this is the right data descriptor then the sizes should match */ if ((uzoff_t)des_start - (uzoff_t)data_start != des_csize) { /* apparently this signature does not go with this data so skip */ /* write out signature as data */ k = 4; if (zfseeko(in_file, des_start + k, SEEK_SET) != 0) { /* seek error */ ZIPERR(ZE_READ, "seek failed reading descriptor"); } if (bfwrite(b, 1, k, BFWRITE_DATA) != k) { free((zvoid *)b); fprintf(mesg," fcopy: write error\n"); return ZE_TEMP; } m += k; continue; } else { /* apparently this is the correct data descriptor */ /* we should check the CRC but this does not work for encrypted data */ /* skip descriptor as will write out later */ des_good = 1; data_start = zftello(in_file); k = 16; if (zfseeko(in_file, des_start + k, SEEK_SET) != 0) { /* seek error */ ZIPERR(ZE_READ, "seek failed reading descriptor"); } data_start = zftello(in_file); } } } } } if (des_good) { /* skip descriptor as will write out later */ } else { /* write out apparently wrong descriptor as data */ if (bfwrite(b, 1, k, BFWRITE_DATA) != k) { free((zvoid *)b); fprintf(mesg," fcopy: write error\n"); return ZE_TEMP; } m += k; } if (copy_only && !display_globaldots) { if (dot_size > 0) { /* initial space */ if (noisy && dot_count == -1) { #ifndef WINDLL putc(' ', mesg); fflush(mesg); #else fprintf(stdout,"%c",' '); #endif dot_count++; } dot_count += k; if (dot_size <= dot_count) dot_count = 0; } if ((verbose || noisy) && dot_size && !dot_count) { #ifndef WINDLL putc('.', mesg); fflush(mesg); #else fprintf(stdout,"%c",'.'); #endif mesg_line_started = 1; } } if (des_good) break; if (des) continue; if ((des || n != (uzoff_t)(-1L)) && m < n && feof(in_file)) { /* open next split */ current_in_disk++; if (current_in_disk >= total_disks) { /* done */ break; } else if (current_in_disk == total_disks - 1) { /* last disk is archive.zip */ if ((split_path = malloc(strlen(in_path) + 1)) == NULL) { zipwarn("reading archive: ", in_path); return ZE_MEM; } strcpy(split_path, in_path); } else { /* other disks are archive.z01, archive.z02, ... */ split_path = get_in_split_path(in_path, current_in_disk); } fclose(in_file); /* open the split */ while ((in_file = zfopen(split_path, FOPR)) == NULL) { int r = 0; /* could not open split */ if (fix == 1 && skip_this_disk) { free(split_path); free((zvoid *)b); return ZE_FORM; } /* Ask for directory with split. Updates in_path */ r = ask_for_split_read_path(current_in_disk); if (r == ZE_ABORT) { zipwarn("could not find split: ", split_path); free(split_path); free((zvoid *)b); return ZE_ABORT; } if (r == ZE_EOF) { zipmessage_nl("", 1); zipwarn("user ended reading - closing archive", ""); free(split_path); free((zvoid *)b); return ZE_EOF; } if (fix == 2 && skip_this_disk) { /* user asked to skip this disk */ zipwarn("skipping split file: ", split_path); current_in_disk++; } if (current_in_disk == total_disks - 1) { /* last disk is archive.zip */ if ((split_path = malloc(strlen(in_path) + 1)) == NULL) { zipwarn("reading archive: ", in_path); return ZE_MEM; } strcpy(split_path, in_path); } else { /* other disks are archive.z01, archive.z02, ... */ split_path = get_in_split_path(zipfile, current_in_disk); } } if (fix == 2 && skip_this_disk) { /* user asked to skip this disk */ free(split_path); free((zvoid *)b); return ZE_FORM; } free(split_path); } } free((zvoid *)b); return ZE_OK; } #ifdef NO_RENAME int rename(from, to) ZCONST char *from; ZCONST char *to; { unlink(to); if (link(from, to) == -1) return -1; if (unlink(from) == -1) return -1; return 0; } #endif /* NO_RENAME */ #ifdef ZMEM /************************/ /* Function memset() */ /************************/ /* * memset - for systems without it * bill davidsen - March 1990 */ char * memset(buf, init, len) register char *buf; /* buffer loc */ register int init; /* initializer */ register unsigned int len; /* length of the buffer */ { char *start; start = buf; while (len--) *(buf++) = init; return(start); } /************************/ /* Function memcpy() */ /************************/ char * memcpy(dst,src,len) /* v2.0f */ register char *dst, *src; register unsigned int len; { char *start; start = dst; while (len--) *dst++ = *src++; return(start); } /************************/ /* Function memcmp() */ /************************/ int memcmp(b1,b2,len) /* jpd@usl.edu -- 11/16/90 */ register char *b1, *b2; register unsigned int len; { if (len) do { /* examine each byte (if any) */ if (*b1++ != *b2++) return (*((uch *)b1-1) - *((uch *)b2-1)); /* exit when miscompare */ } while (--len); return(0); /* no miscompares, yield 0 result */ } #endif /* ZMEM */ /*------------------------------------------------------------------ * Split archives */ /* ask_for_split_read_path * * If the next split file is not in the current directory, ask * the user where it is. * * in_path is the base path for reading splits and is usually * the same as zipfile. The path in in_path must be the archive * file ending in .zip as this is assumed by get_in_split_path(). * * Updates in_path if changed. Returns ZE_OK if OK or ZE_ABORT if * user cancels reading archive. * * If fix = 1 then allow skipping disk (user may not have it). */ #define SPLIT_MAXPATH (FNMAX + 4010) int ask_for_split_read_path(current_disk) ulg current_disk; { FILE *f; int is_readable = 0; int i; char *split_dir = NULL; char *archive_name = NULL; char *split_name = NULL; char *split_path = NULL; char buf[SPLIT_MAXPATH + 100]; /* get split path */ split_path = get_in_split_path(in_path, current_disk); /* get the directory */ if ((split_dir = malloc(strlen(in_path) + 40)) == NULL) { ZIPERR(ZE_MEM, "split path"); } strcpy(split_dir, in_path); /* remove any name at end */ for (i = strlen(split_dir) - 1; i >= 0; i--) { if (split_dir[i] == '/' || split_dir[i] == '\\' || split_dir[i] == ':') { split_dir[i + 1] = '\0'; break; } } if (i < 0) split_dir[0] = '\0'; /* get the name of the archive */ if ((archive_name = malloc(strlen(in_path) + 1)) == NULL) { ZIPERR(ZE_MEM, "split path"); } if (strlen(in_path) == strlen(split_dir)) { archive_name[0] = '\0'; } else { strcpy(archive_name, in_path + strlen(split_dir)); } /* get the name of the split */ if ((split_name = malloc(strlen(split_path) + 1)) == NULL) { ZIPERR(ZE_MEM, "split path"); } if (strlen(in_path) == strlen(split_dir)) { split_name[0] = '\0'; } else { strcpy(split_name, split_path + strlen(split_dir)); } if (i < 0) { strcpy(split_dir, "(current directory)"); } fprintf(mesg, "\n\nCould not find:\n"); fprintf(mesg, " %s\n", split_path); /* fprintf(mesg, "Please enter the path directory (. for cur dir) where\n"); fprintf(mesg, " %s\n", split_name); fprintf(mesg, "is located\n"); */ for (;;) { if (is_readable) { fprintf(mesg, "\nHit c (change path to where this split file is)"); fprintf(mesg, "\n q (abort archive - quit)"); fprintf(mesg, "\n or ENTER (continue with this split): "); } else { if (fix == 1) { fprintf(mesg, "\nHit c (change path to where this split file is)"); fprintf(mesg, "\n s (skip this split)"); fprintf(mesg, "\n q (abort archive - quit)"); fprintf(mesg, "\n or ENTER (try reading this split again): "); } else if (fix == 2) { fprintf(mesg, "\nHit c (change path to where this split file is)"); fprintf(mesg, "\n s (skip this split)"); fprintf(mesg, "\n q (abort archive - quit)"); fprintf(mesg, "\n e (end this archive - no more splits)"); fprintf(mesg, "\n z (look for .zip split - the last split)"); fprintf(mesg, "\n or ENTER (try reading this split again): "); } else { fprintf(mesg, "\nHit c (change path to where this split file is)"); fprintf(mesg, "\n q (abort archive - quit)"); fprintf(mesg, "\n or ENTER (try reading this split again): "); } } fflush(mesg); fgets(buf, SPLIT_MAXPATH, stdin); /* remove any newline */ for (i = 0; buf[i]; i++) { if (buf[i] == '\n') { buf[i] = '\0'; break; } } if (toupper(buf[0]) == 'Q') { return ZE_ABORT; } else if ((fix == 1 || fix == 2) && toupper(buf[0]) == 'S') { /* fprintf(mesg, "\nSkip this split/disk? (files in this split will not be recovered) [n/y] "); fflush(mesg); fgets(buf, SPLIT_MAXPATH, stdin); if (buf[0] == 'y' || buf[0] == 'Y') { */ skip_this_disk = current_in_disk + 1; return ZE_FORM; } else if (toupper(buf[0]) == 'C') { fprintf(mesg, "\nEnter path where this split is (ENTER = same dir, . = current dir)"); fprintf(mesg, "\n: "); fflush(mesg); fgets(buf, SPLIT_MAXPATH, stdin); is_readable = 0; /* remove any newline */ for (i = 0; buf[i]; i++) { if (buf[i] == '\n') { buf[i] = '\0'; break; } } if (buf[0] == '\0') { /* Hit ENTER so try old path again - could be removable media was changed */ strcpy(buf, split_path); } } else if (fix == 2 && toupper(buf[0]) == 'E') { /* no more splits to read */ return ZE_EOF; } else if (fix == 2 && toupper(buf[0]) == 'Z') { total_disks = current_disk + 1; free(split_path); split_path = get_in_split_path(in_path, current_disk); buf[0] = '\0'; strncat(buf, split_path, SPLIT_MAXPATH); } if (strlen(buf) > 0) { /* changing path */ /* check if user wants current directory */ if (buf[0] == '.' && buf[1] == '\0') { buf[0] = '\0'; } /* remove any name at end */ for (i = strlen(buf); i >= 0; i--) { if (buf[i] == '/' || buf[i] == '\\' || buf[i] == ':') { buf[i + 1] = '\0'; break; } } /* update base_path to newdir/split_name - in_path is the .zip file path */ free(in_path); if (i < 0) { /* just name so current directory */ strcpy(buf, "(current directory)"); if (archive_name == NULL) { i = 0; } else { i = strlen(archive_name); } if ((in_path = malloc(strlen(archive_name) + 40)) == NULL) { ZIPERR(ZE_MEM, "split path"); } strcpy(in_path, archive_name); } else { /* not the current directory */ /* remove any name at end */ for (i = strlen(buf); i >= 0; i--) { if (buf[i] == '/') { buf[i + 1] = '\0'; break; } } if (i < 0) { buf[0] = '\0'; } if ((in_path = malloc(strlen(buf) + strlen(archive_name) + 40)) == NULL) { ZIPERR(ZE_MEM, "split path"); } strcpy(in_path, buf); strcat(in_path, archive_name); } free(split_path); /* get split path */ split_path = get_in_split_path(in_path, current_disk); free(split_dir); if ((split_dir = malloc(strlen(in_path) + 40)) == NULL) { ZIPERR(ZE_MEM, "split path"); } strcpy(split_dir, in_path); /* remove any name at end */ for (i = strlen(split_dir); i >= 0; i--) { if (split_dir[i] == '/') { split_dir[i + 1] = '\0'; break; } } /* try to open it */ if ((f = fopen(split_path, "r")) == NULL) { fprintf(mesg, "\nCould not find or open\n"); fprintf(mesg, " %s\n", split_path); /* fprintf(mesg, "Please enter the path (. for cur dir) where\n"); fprintf(mesg, " %s\n", split_name); fprintf(mesg, "is located\n"); */ continue; } fclose(f); is_readable = 1; fprintf(mesg, "Found: %s\n", split_path); } else { /* try to open it */ if ((f = fopen(split_path, "r")) == NULL) { fprintf(mesg, "\nCould not find or open\n"); fprintf(mesg, " %s\n", split_path); /* fprintf(mesg, "Please enter the path (. for cur dir) where\n"); fprintf(mesg, " %s\n", split_name); fprintf(mesg, "is located\n"); */ continue; } fclose(f); is_readable = 1; fprintf(mesg, "\nFound: %s\n", split_path); break; } } free(archive_name); free(split_dir); free(split_name); return ZE_OK; } /* ask_for_split_write_path * * Verify the directory for the next split. Called * when -sp is used to pause between writing splits. * * Updates out_path and return 1 if OK or 0 if cancel */ int ask_for_split_write_path(current_disk) ulg current_disk; { unsigned int num = (unsigned int)current_disk + 1; int i; char *split_dir = NULL; char *split_name = NULL; char buf[FNMAX + 40]; /* get the directory */ if ((split_dir = malloc(strlen(out_path) + 40)) == NULL) { ZIPERR(ZE_MEM, "split path"); } strcpy(split_dir, out_path); /* remove any name at end */ for (i = strlen(split_dir); i >= 0; i--) { if (split_dir[i] == '/' || split_dir[i] == '\\' || split_dir[i] == ':') { split_dir[i + 1] = '\0'; break; } } /* get the name of the split */ if ((split_name = malloc(strlen(out_path) + 1)) == NULL) { ZIPERR(ZE_MEM, "split path"); } if (strlen(out_path) == strlen(split_dir)) { split_name[0] = '\0'; } else { strcpy(split_name, out_path + strlen(split_dir)); } if (i < 0) { strcpy(split_dir, "(current directory)"); } if (mesg_line_started) fprintf(mesg, "\n"); fprintf(mesg, "\nOpening disk %d\n", num); fprintf(mesg, "Hit ENTER to write to default path of\n"); fprintf(mesg, " %s\n", split_dir); fprintf(mesg, "or enter a new directory path (. for cur dir) and hit ENTER\n"); for (;;) { fprintf(mesg, "\nPath (or hit ENTER to continue): "); fflush(mesg); fgets(buf, FNMAX, stdin); /* remove any newline */ for (i = 0; buf[i]; i++) { if (buf[i] == '\n') { buf[i] = '\0'; break; } } if (strlen(buf) > 0) { /* changing path */ /* current directory */ if (buf[0] == '.' && buf[1] == '\0') { buf[0] = '\0'; } /* remove any name at end */ for (i = strlen(buf); i >= 0; i--) { if (buf[i] == '/' || buf[i] == '\\' || buf[i] == ':') { buf[i + 1] = '\0'; break; } } /* update out_path to newdir/split_name */ free(out_path); if (i < 0) { /* just name so current directory */ strcpy(buf, "(current directory)"); if (split_name == NULL) { i = 0; } else { i = strlen(split_name); } if ((out_path = malloc(strlen(split_name) + 40)) == NULL) { ZIPERR(ZE_MEM, "split path"); } strcpy(out_path, split_name); } else { /* not the current directory */ /* remove any name at end */ for (i = strlen(buf); i >= 0; i--) { if (buf[i] == '/') { buf[i + 1] = '\0'; break; } } if (i < 0) { buf[0] = '\0'; } if ((out_path = malloc(strlen(buf) + strlen(split_name) + 40)) == NULL) { ZIPERR(ZE_MEM, "split path"); } strcpy(out_path, buf); strcat(out_path, split_name); } fprintf(mesg, "Writing to:\n %s\n", buf); free(split_name); free(split_dir); if ((split_dir = malloc(strlen(out_path) + 40)) == NULL) { ZIPERR(ZE_MEM, "split path"); } strcpy(split_dir, out_path); /* remove any name at end */ for (i = strlen(split_dir); i >= 0; i--) { if (split_dir[i] == '/') { split_dir[i + 1] = '\0'; break; } } if ((split_name = malloc(strlen(out_path) + 1)) == NULL) { ZIPERR(ZE_MEM, "split path"); } strcpy(split_name, out_path + strlen(split_dir)); } else { break; } } free(split_dir); free(split_name); /* for now no way out except Ctrl C */ return 1; } /* split_name * * get name of split being read */ char *get_in_split_path(base_path, disk_number) char *base_path; ulg disk_number; { char *split_path = NULL; int base_len = 0; int path_len = 0; ulg num = disk_number + 1; char ext[6]; #ifdef VMS int vers_len; /* File version length. */ char *vers_ptr; /* File version string. */ #endif /* def VMS */ /* * A split has extension z01, z02, ..., z99, z100, z101, ... z999 * We currently support up to .z99999 * WinZip will also read .100, .101, ... but AppNote 6.2.2 uses above * so use that. Means on DOS can only have 100 splits. */ if (num == total_disks) { /* last disk is base path */ if ((split_path = malloc(strlen(base_path) + 1)) == NULL) { ZIPERR(ZE_MEM, "base path"); } strcpy(split_path, base_path); return split_path; } else { if (num > 99999) { ZIPERR(ZE_BIG, "More than 99999 splits needed"); } sprintf(ext, "z%02lu", num); } /* create path for this split - zip.c checked for .zip extension */ base_len = strlen(base_path) - 3; path_len = base_len + strlen(ext); #ifdef VMS /* On VMS, locate the file version, and adjust base_len accordingly. Note that path_len is correct, as-is. */ vers_ptr = vms_file_version( base_path); vers_len = strlen( vers_ptr); base_len -= vers_len; #endif /* def VMS */ if ((split_path = malloc(path_len + 1)) == NULL) { ZIPERR(ZE_MEM, "split path"); } /* copy base_path except for end zip */ strcpy(split_path, base_path); split_path[base_len] = '\0'; /* add extension */ strcat(split_path, ext); #ifdef VMS /* On VMS, append (preserve) the file version. */ strcat(split_path, vers_ptr); #endif /* def VMS */ return split_path; } /* split_name * * get name of split being written */ char *get_out_split_path(base_path, disk_number) char *base_path; ulg disk_number; { char *split_path = NULL; int base_len = 0; int path_len = 0; ulg num = disk_number + 1; char ext[6]; #ifdef VMS int vers_len; /* File version length. */ char *vers_ptr; /* File version string. */ #endif /* def VMS */ /* * A split has extension z01, z02, ..., z99, z100, z101, ... z999 * We currently support up to .z99999 * WinZip will also read .100, .101, ... but AppNote 6.2.2 uses above * so use that. Means on DOS can only have 100 splits. */ if (num > 99999) { ZIPERR(ZE_BIG, "More than 99999 splits needed"); } sprintf(ext, "z%02lu", num); /* create path for this split - zip.c checked for .zip extension */ base_len = strlen(base_path) - 3; path_len = base_len + strlen(ext); #ifdef VMS /* On VMS, locate the file version, and adjust base_len accordingly. Note that path_len is correct, as-is. */ vers_ptr = vms_file_version( base_path); vers_len = strlen( vers_ptr); base_len -= vers_len; #endif /* def VMS */ if ((split_path = malloc(path_len + 1)) == NULL) { ZIPERR(ZE_MEM, "split path"); } /* copy base_path except for end zip */ strcpy(split_path, base_path); split_path[base_len] = '\0'; /* add extension */ strcat(split_path, ext); #ifdef VMS /* On VMS, append (preserve) the file version. */ strcat(split_path, vers_ptr); #endif /* def VMS */ return split_path; } /* close_split * * close a split - assume that the paths needed for the splits are * available. */ int close_split(disk_number, tempfile, temp_name) ulg disk_number; FILE *tempfile; char *temp_name; { char *split_path = NULL; split_path = get_out_split_path(out_path, disk_number); if (noisy_splits) { zipmessage("\tClosing split ", split_path); } fclose(tempfile); rename_split(temp_name, split_path); set_filetype(split_path); return ZE_OK; } /* bfwrite Does the fwrite but also counts bytes and does splits */ size_t bfwrite(buffer, size, count, mode) ZCONST void *buffer; size_t size; size_t count; int mode; { size_t bytes_written = 0; size_t r; size_t b = size * count; uzoff_t bytes_left_in_split = 0; size_t bytes_to_write = b; /* -------------------------------- */ /* local header */ if (mode == BFWRITE_LOCALHEADER) { /* writing local header - reset entry data count */ bytes_this_entry = 0; /* save start of local header so we can rewrite later */ current_local_file = y; current_local_disk = current_disk; current_local_offset = bytes_this_split; } if (split_size == 0) bytes_left_in_split = bytes_to_write; else bytes_left_in_split = split_size - bytes_this_split; if (bytes_to_write > bytes_left_in_split) { if (mode == BFWRITE_HEADER || mode == BFWRITE_LOCALHEADER || mode == BFWRITE_CENTRALHEADER) { /* if can't write entire header save for next split */ bytes_to_write = 0; } else { /* normal data so fill the split */ bytes_to_write = (size_t)bytes_left_in_split; } } /* -------------------------------- */ /* central header */ if (mode == BFWRITE_CENTRALHEADER) { /* set start disk for CD */ if (cd_start_disk == (ulg)-1) { cd_start_disk = current_disk; cd_start_offset = bytes_this_split; } cd_entries_this_disk++; total_cd_entries++; } /* -------------------------------- */ if (bytes_to_write > 0) { /* write out the bytes for this split */ r = fwrite(buffer, size, bytes_to_write, y); bytes_written += r; bytes_to_write = b - r; bytes_this_split += r; if (mode == BFWRITE_DATA) /* if data descriptor do not include in count */ bytes_this_entry += r; } else { bytes_to_write = b; } if (bytes_to_write > 0) { if (split_method) { /* still bytes to write so close split and open next split */ bytes_prev_splits += bytes_this_split; if (split_method == 1 && ferror(y)) { /* if writing all splits to same place and have problem then bad */ ZIPERR(ZE_WRITE, "Could not write split"); } if (split_method == 2 && ferror(y)) { /* A split must be at least 64K except last .zip split */ if (bytes_this_split < 64 * (uzoff_t)0x400) { ZIPERR(ZE_WRITE, "Not enough space to write split"); } } /* close this split */ if (split_method == 1 && current_local_disk == current_disk) { /* keep split open so can update it */ current_local_tempname = tempzip; } else { /* close split */ close_split(current_disk, y, tempzip); y = NULL; free(tempzip); tempzip = NULL; } cd_entries_this_disk = 0; bytes_this_split = 0; /* increment disk - disks are numbered 0, 1, 2, ... and splits are 01, 02, ... */ current_disk++; if (split_method == 2 && split_bell) { /* bell when pause to ask for next split */ putc('\007', mesg); fflush(mesg); } for (;;) { /* if method 2 pause and allow changing path */ if (split_method == 2) { if (ask_for_split_write_path(current_disk) == 0) { ZIPERR(ZE_ABORT, "could not write split"); } } /* open next split */ #if defined(UNIX) && !defined(NO_MKSTEMP) { int yd; int i; /* use mkstemp to avoid race condition and compiler warning */ if (tempath != NULL) { /* if -b used to set temp file dir use that for split temp */ if ((tempzip = malloc(strlen(tempath) + 12)) == NULL) { ZIPERR(ZE_MEM, "allocating temp filename"); } strcpy(tempzip, tempath); if (lastchar(tempzip) != '/') strcat(tempzip, "/"); } else { /* create path by stripping name and appending template */ if ((tempzip = malloc(strlen(zipfile) + 12)) == NULL) { ZIPERR(ZE_MEM, "allocating temp filename"); } strcpy(tempzip, zipfile); for(i = strlen(tempzip); i > 0; i--) { if (tempzip[i - 1] == '/') break; } tempzip[i] = '\0'; } strcat(tempzip, "ziXXXXXX"); if ((yd = mkstemp(tempzip)) == EOF) { ZIPERR(ZE_TEMP, tempzip); } if ((y = fdopen(yd, FOPW_TMP)) == NULL) { ZIPERR(ZE_TEMP, tempzip); } } #else if ((tempzip = tempname(zipfile)) == NULL) { ZIPERR(ZE_MEM, "allocating temp filename"); } if ((y = zfopen(tempzip, FOPW_TMP)) == NULL) { ZIPERR(ZE_TEMP, tempzip); } #endif r = fwrite((char *)buffer + bytes_written, 1, bytes_to_write, y); bytes_written += r; bytes_this_split += r; if (!(mode == BFWRITE_HEADER || mode == BFWRITE_LOCALHEADER || mode == BFWRITE_CENTRALHEADER)) { bytes_this_entry += r; } if (bytes_to_write > r) { /* buffer bigger than split */ if (split_method == 2) { /* let user choose another disk */ zipwarn("Not enough room on disk", ""); continue; } else { ZIPERR(ZE_WRITE, "Not enough room on disk"); } } if (mode == BFWRITE_LOCALHEADER || mode == BFWRITE_HEADER || mode == BFWRITE_CENTRALHEADER) { if (split_method == 1 && current_local_file && current_local_disk != current_disk) { /* We're opening a new split because the next header did not fit on the last split. We need to now close the last split and update the pointers for the current split. */ close_split(current_local_disk, current_local_file, current_local_tempname); free(current_local_tempname); } current_local_tempname = tempzip; current_local_file = y; current_local_offset = 0; current_local_disk = current_disk; } break; } } else { /* likely have more than fits but no splits */ /* probably already have error "no space left on device" */ /* could let flush_outbuf() handle error but bfwrite() is called for headers also */ if (ferror(y)) ziperr(ZE_WRITE, "write error on zip file"); } } /* display dots for archive instead of for each file */ if (display_globaldots) { if (dot_size > 0) { /* initial space */ if (dot_count == -1) { #ifndef WINDLL putc(' ', mesg); fflush(mesg); #else fprintf(stdout,"%c",' '); #endif /* assume a header will be written first, so avoid 0 */ dot_count = 1; } /* skip incrementing dot count for small buffers like for headers */ if (size * count > 1000) { dot_count++; if (dot_size <= dot_count * (zoff_t)size * (zoff_t)count) dot_count = 0; } } if (dot_size && !dot_count) { dot_count++; #ifndef WINDLL putc('.', mesg); fflush(mesg); #else fprintf(stdout,"%c",'.'); #endif mesg_line_started = 1; } } return bytes_written; } #ifdef UNICODE_SUPPORT /*--------------------------------------------- * Unicode conversion functions * * Provided by Paul Kienitz * * Some modifications to work with Zip * *--------------------------------------------- */ /* NOTES APPLICABLE TO ALL STRING FUNCTIONS: All of the x_to_y functions take parameters for an output buffer and its available length, and return an int. The value returned is the length of the string that the input produces, which may be larger than the provided buffer length. If the returned value is less than the buffer length, then the contents of the buffer will be null-terminated; otherwise, it will not be terminated and may be invalid, possibly stopping in the middle of a multibyte sequence. In all cases you may pass NULL as the buffer and/or 0 as the length, if you just want to learn how much space the string is going to require. The functions will return -1 if the input is invalid UTF-8 or cannot be encoded as UTF-8. */ /* utility functions for managing UTF-8 and UCS-4 strings */ /* utf8_char_bytes * * Returns the number of bytes used by the first character in a UTF-8 * string, or -1 if the UTF-8 is invalid or null. */ local int utf8_char_bytes(utf8) ZCONST char *utf8; { int t, r; unsigned lead; if (!utf8) return -1; /* no input */ lead = (unsigned char) *utf8; if (lead < 0x80) r = 1; /* an ascii-7 character */ else if (lead < 0xC0) return -1; /* error: trailing byte without lead byte */ else if (lead < 0xE0) r = 2; /* an 11 bit character */ else if (lead < 0xF0) r = 3; /* a 16 bit character */ else if (lead < 0xF8) r = 4; /* a 21 bit character (the most currently used) */ else if (lead < 0xFC) r = 5; /* a 26 bit character (shouldn't happen) */ else if (lead < 0xFE) r = 6; /* a 31 bit character (shouldn't happen) */ else return -1; /* error: invalid lead byte */ for (t = 1; t < r; t++) if ((unsigned char) utf8[t] < 0x80 || (unsigned char) utf8[t] >= 0xC0) return -1; /* error: not enough valid trailing bytes */ return r; } /* ucs4_char_from_utf8 * * Given a reference to a pointer into a UTF-8 string, returns the next * UCS-4 character and advances the pointer to the next character sequence. * Returns ~0 and does not advance the pointer when input is ill-formed. * * Since the Unicode standard says 32-bit values won't be used (just * up to the current 21-bit mappings) changed this to signed to allow -1 to * be returned. */ long ucs4_char_from_utf8(utf8) ZCONST char **utf8; { ulg ret; int t, bytes; if (!utf8) return -1; /* no input */ bytes = utf8_char_bytes(*utf8); if (bytes <= 0) return -1; /* invalid input */ if (bytes == 1) ret = **utf8; /* ascii-7 */ else ret = **utf8 & (0x7F >> bytes); /* lead byte of a multibyte sequence */ (*utf8)++; for (t = 1; t < bytes; t++) /* consume trailing bytes */ ret = (ret << 6) | (*((*utf8)++) & 0x3F); return (long) ret; } /* utf8_from_ucs4_char - Convert UCS char to UTF-8 * * Returns the number of bytes put into utf8buf to represent ch, from 1 to 6, * or -1 if ch is too large to represent. utf8buf must have room for 6 bytes. */ local int utf8_from_ucs4_char(utf8buf, ch) char *utf8buf; ulg ch; { int trailing = 0; int leadmask = 0x80; int leadbits = 0x3F; ulg tch = ch; int ret; if (ch > 0x7FFFFFFF) return -1; /* UTF-8 can represent 31 bits */ if (ch < 0x7F) { *utf8buf++ = (char) ch; /* ascii-7 */ return 1; } do { trailing++; leadmask = (leadmask >> 1) | 0x80; leadbits >>= 1; tch >>= 6; } while (tch & ~leadbits); ret = trailing + 1; /* produce lead byte */ *utf8buf++ = (char) (leadmask | (ch >> (6 * trailing))); /* produce trailing bytes */ while (--trailing >= 0) *utf8buf++ = (char) (0x80 | ((ch >> (6 * trailing)) & 0x3F)); return ret; } /*===================================================================*/ /* utf8_to_ucs4_string - convert UTF-8 string to UCS string * * Return UCS count. Now returns int so can return -1. */ local int utf8_to_ucs4_string(utf8, ucs4buf, buflen) ZCONST char *utf8; ulg *ucs4buf; int buflen; { int count = 0; for (;;) { long ch = ucs4_char_from_utf8(&utf8); if (ch == -1) return -1; else { if (ucs4buf && count < buflen) ucs4buf[count] = ch; if (ch == 0) return count; count++; } } } /* ucs4_string_to_utf8 * * */ local int ucs4_string_to_utf8(ucs4, utf8buf, buflen) ZCONST ulg *ucs4; char *utf8buf; int buflen; { char mb[6]; int count = 0; if (!ucs4) return -1; for (;;) { int mbl = utf8_from_ucs4_char(mb, *ucs4++); int c; if (mbl <= 0) return -1; /* We could optimize this a bit by passing utf8buf + count */ /* directly to utf8_from_ucs4_char when buflen >= count + 6... */ c = buflen - count; if (mbl < c) c = mbl; if (utf8buf && count < buflen) strncpy(utf8buf + count, mb, c); if (mbl == 1 && !mb[0]) return count; /* terminating nul */ count += mbl; } } #if 0 /* currently unused */ /* utf8_chars * * Wrapper: counts the actual unicode characters in a UTF-8 string. */ local int utf8_chars(utf8) ZCONST char *utf8; { return utf8_to_ucs4_string(utf8, NULL, 0); } #endif /* --------------------------------------------------- */ /* Unicode Support * * These functions common for all Unicode ports. * * These functions should allocate and return strings that can be * freed with free(). * * 8/27/05 EG * * Use zwchar for wide char which is unsigned long * in zip.h and 32 bits. This avoids problems with * different sizes of wchar_t. */ #ifdef WIN32 zwchar *wchar_to_wide_string(wchar_string) wchar_t *wchar_string; { int i; int wchar_len; zwchar *wide_string; wchar_len = wcslen(wchar_string); if ((wide_string = malloc((wchar_len + 1) * sizeof(zwchar))) == NULL) { ZIPERR(ZE_MEM, "wchar to wide conversion"); } for (i = 0; i <= wchar_len; i++) { wide_string[i] = wchar_string[i]; } return wide_string; } /* is_ascii_stringw * Checks if a wide string is all ascii */ int is_ascii_stringw(wstring) wchar_t *wstring; { wchar_t *pw; wchar_t cw; if (wstring == NULL) return 0; for (pw = wstring; (cw = *pw) != '\0'; pw++) { if (cw > 0x7F) { return 0; } } return 1; } #endif /* is_ascii_string * Checks if a string is all ascii */ int is_ascii_string(mbstring) char *mbstring; { char *p; uch c; if (mbstring == NULL) return 0; for (p = mbstring; (c = (uch)*p) != '\0'; p++) { if (c > 0x7F) { return 0; } } return 1; } /* local to UTF-8 */ char *local_to_utf8_string(local_string) char *local_string; { zwchar *wide_string = local_to_wide_string(local_string); char *utf8_string = wide_to_utf8_string(wide_string); free(wide_string); return utf8_string; } /* wide_char_to_escape_string provides a string that represents a wide char not in local char set An initial try at an algorithm. Suggestions welcome. If not an ASCII char, probably need 2 bytes at least. So if a 2-byte wide encode it as 4 hex digits with a leading #U. Since the Unicode standard has been frozen, it looks like 3 bytes should be enough for any large Unicode character. In these cases prefix the string with #L. So #U1234 is a 2-byte wide character with bytes 0x12 and 0x34 while #L123456 is a 3-byte wide with bytes 0x12, 0x34, and 0x56. On Windows, wide that need two wide characters as a surrogate pair to represent them need to be converted to a single number. */ /* set this to the max bytes an escape can be */ #define MAX_ESCAPE_BYTES 8 char *wide_char_to_escape_string(wide_char) zwchar wide_char; { int i; zwchar w = wide_char; uch b[9]; char e[7]; int len; char *r; /* fill byte array with zeros */ for (len = 0; len < sizeof(zwchar); len++) { b[len] = 0; } /* get bytes in right to left order */ for (len = 0; w; len++) { b[len] = (char)(w % 0x100); w /= 0x100; } if ((r = malloc(MAX_ESCAPE_BYTES + 8)) == NULL) { ZIPERR(ZE_MEM, "wide_char_to_escape_string"); } strcpy(r, "#"); /* either 2 bytes or 4 bytes */ if (len < 3) { len = 2; strcat(r, "U"); } else { len = 3; strcat(r, "L"); } for (i = len - 1; i >= 0; i--) { sprintf(e, "%02x", b[i]); strcat(r, e); } return r; } #if 0 /* returns the wide character represented by the escape string */ zwchar escape_string_to_wide(escape_string) char *escape_string; { int i; zwchar w; char c; char u; int len; char *e = escape_string; if (e == NULL) { return 0; } if (e[0] != '#') { /* no leading # */ return 0; } len = strlen(e); /* either #U1234 or #L123456 format */ if (len != 6 && len != 8) { return 0; } w = 0; if (e[1] == 'L') { if (len != 8) { return 0; } /* 3 bytes */ for (i = 2; i < 8; i++) { c = e[i]; u = toupper(c); if (u >= 'A' && u <= 'F') { w = w * 0x10 + (zwchar)(u + 10 - 'A'); } else if (c >= '0' && c <= '9') { w = w * 0x10 + (zwchar)(c - '0'); } else { return 0; } } } else if (e[1] == 'U') { /* 2 bytes */ for (i = 2; i < 6; i++) { c = e[i]; u = toupper(c); if (u >= 'A' && u <= 'F') { w = w * 0x10 + (zwchar)(u + 10 - 'A'); } else if (c >= '0' && c <= '9') { w = w * 0x10 + (zwchar)(c - '0'); } else { return 0; } } } return w; } #endif char *local_to_escape_string(local_string) char *local_string; { zwchar *wide_string = local_to_wide_string(local_string); char *escape_string = wide_to_escape_string(wide_string); free(wide_string); return escape_string; } #ifdef WIN32 char *wchar_to_local_string(wstring) wchar_t *wstring; { zwchar *wide_string = wchar_to_wide_string(wstring); char *local_string = wide_to_local_string(wide_string); free(wide_string); return local_string; } #endif #ifndef WIN32 /* The Win32 port uses a system-specific variant. */ /* convert wide character string to multi-byte character string */ char *wide_to_local_string(wide_string) zwchar *wide_string; { int i; wchar_t wc; int b; int state_dependent; int wsize = 0; int max_bytes = MB_CUR_MAX; char buf[9]; char *buffer = NULL; char *local_string = NULL; for (wsize = 0; wide_string[wsize]; wsize++) ; if (MAX_ESCAPE_BYTES > max_bytes) max_bytes = MAX_ESCAPE_BYTES; if ((buffer = (char *)malloc(wsize * max_bytes + 1)) == NULL) { ZIPERR(ZE_MEM, "wide_to_local_string"); } /* convert it */ buffer[0] = '\0'; /* set initial state if state-dependent encoding */ wc = (wchar_t)'a'; b = wctomb(NULL, wc); if (b == 0) state_dependent = 0; else state_dependent = 1; for (i = 0; i < wsize; i++) { if (sizeof(wchar_t) < 4 && wide_string[i] > 0xFFFF) { /* wchar_t probably 2 bytes */ /* could do surrogates if state_dependent and wctomb can do */ wc = zwchar_to_wchar_t_default_char; } else { wc = (wchar_t)wide_string[i]; } b = wctomb(buf, wc); if (unicode_escape_all) { if (b == 1 && (uch)buf[0] <= 0x7f) { /* ASCII */ strncat(buffer, buf, b); } else { /* use escape for wide character */ char *e = wide_char_to_escape_string(wide_string[i]); strcat(buffer, e); free(e); } } else if (b > 0) { /* multi-byte char */ strncat(buffer, buf, b); } else { /* no MB for this wide */ if (use_wide_to_mb_default) { /* default character */ strcat(buffer, wide_to_mb_default_string); } else { /* use escape for wide character */ char *e = wide_char_to_escape_string(wide_string[i]); strcat(buffer, e); free(e); } } } if ((local_string = (char *)malloc(strlen(buffer) + 1)) == NULL) { free(buffer); ZIPERR(ZE_MEM, "wide_to_local_string"); } strcpy(local_string, buffer); free(buffer); return local_string; } #endif /* !WIN32 */ /* convert wide character string to escaped string */ char *wide_to_escape_string(wide_string) zwchar *wide_string; { int i; int wsize = 0; char buf[9]; char *buffer = NULL; char *escape_string = NULL; for (wsize = 0; wide_string[wsize]; wsize++) ; if ((buffer = (char *)malloc(wsize * MAX_ESCAPE_BYTES + 1)) == NULL) { ZIPERR(ZE_MEM, "wide_to_escape_string"); } /* convert it */ buffer[0] = '\0'; for (i = 0; i < wsize; i++) { if (wide_string[i] <= 0x7f && isprint((char)wide_string[i])) { /* ASCII */ buf[0] = (char)wide_string[i]; buf[1] = '\0'; strcat(buffer, buf); } else { /* use escape for wide character */ char *e = wide_char_to_escape_string(wide_string[i]); strcat(buffer, e); free(e); } } if ((escape_string = (char *)malloc(strlen(buffer) + 1)) == NULL) { ZIPERR(ZE_MEM, "wide_to_escape_string"); } strcpy(escape_string, buffer); free(buffer); return escape_string; } /* convert local string to display character set string */ char *local_to_display_string(local_string) char *local_string; { char *temp_string; char *display_string; /* For Windows, OEM string should never be bigger than ANSI string, says CharToOem description. On UNIX, non-printable characters (0x00 - 0xFF) will be replaced by "^x", so more space may be needed. Note that "^" itself is a valid name character, so this leaves an ambiguity, but UnZip displays names this way, too. (0x00 is not possible, I hope.) For all other ports, just make a copy of local_string. */ #ifdef UNIX char *cp_dst; /* Character pointers used in the */ char *cp_src; /* copying/changing procedure. */ #endif if ((temp_string = (char *)malloc(2 * strlen(local_string) + 1)) == NULL) { ZIPERR(ZE_MEM, "local_to_display_string"); } #ifdef WIN32 /* convert to OEM display character set */ local_to_oem_string(temp_string, local_string); #else # ifdef UNIX /* Copy source string, expanding non-printable characters to "^x". */ cp_dst = temp_string; cp_src = local_string; while (*cp_src != '\0') { if ((unsigned char)*cp_src < ' ') { *cp_dst++ = '^'; *cp_dst++ = '@'+ *cp_src++; } else { *cp_dst++ = *cp_src++; } } *cp_dst = '\0'; # else /* not UNIX */ strcpy(temp_string, local_string); # endif /* UNIX */ #endif #ifdef EBCDIC { char *ebc; if ((ebc = malloc(strlen(display_string) + 1)) == NULL) { ZIPERR(ZE_MEM, "local_to_display_string"); } strtoebc(ebc, display_string); free(display_string); display_string = ebc; } #endif if ((display_string = (char *)malloc(strlen(temp_string) + 1)) == NULL) { ZIPERR(ZE_MEM, "local_to_display_string"); } strcpy(display_string, temp_string); free(temp_string); return display_string; } /* UTF-8 to local */ char *utf8_to_local_string(utf8_string) char *utf8_string; { zwchar *wide_string = utf8_to_wide_string(utf8_string); char *loc = wide_to_local_string(wide_string); if (wide_string) free(wide_string); return loc; } /* UTF-8 to local */ char *utf8_to_escape_string(utf8_string) char *utf8_string; { zwchar *wide_string = utf8_to_wide_string(utf8_string); char *escape_string = wide_to_escape_string(wide_string); free(wide_string); return escape_string; } #ifndef WIN32 /* The Win32 port uses a system-specific variant. */ /* convert multi-byte character string to wide character string */ zwchar *local_to_wide_string(local_string) char *local_string; { int wsize; wchar_t *wc_string; zwchar *wide_string; /* for now try to convert as string - fails if a bad char in string */ wsize = mbstowcs(NULL, local_string, MB_CUR_MAX ); if (wsize == (size_t)-1) { /* could not convert */ return NULL; } /* convert it */ if ((wc_string = (wchar_t *)malloc((wsize + 1) * sizeof(wchar_t))) == NULL) { ZIPERR(ZE_MEM, "local_to_wide_string"); } wsize = mbstowcs(wc_string, local_string, strlen(local_string) + 1); wc_string[wsize] = (wchar_t) 0; /* in case wchar_t is not zwchar */ if ((wide_string = (zwchar *)malloc((wsize + 1) * sizeof(zwchar))) == NULL) { ZIPERR(ZE_MEM, "local_to_wide_string"); } for (wsize = 0; (wide_string[wsize] = (zwchar)wc_string[wsize]); wsize++) ; wide_string[wsize] = (zwchar)0; free(wc_string); return wide_string; } #endif /* !WIN32 */ #if 0 /* All wchar functions are only used by Windows and are now in win32zip.c so that the Windows functions can be used and multiple character wide characters can be handled easily. */ # ifndef WIN32 char *wchar_to_utf8_string(wstring) wchar_t *wstring; { zwchar *wide_string = wchar_to_wide_string(wstring); char *local_string = wide_to_utf8_string(wide_string); free(wide_string); return local_string; } # endif #endif /* convert wide string to UTF-8 */ char *wide_to_utf8_string(wide_string) zwchar *wide_string; { int mbcount; char *utf8_string; /* get size of utf8 string */ mbcount = ucs4_string_to_utf8(wide_string, NULL, 0); if (mbcount == -1) return NULL; if ((utf8_string = (char *) malloc(mbcount + 1)) == NULL) { ZIPERR(ZE_MEM, "wide_to_utf8_string"); } mbcount = ucs4_string_to_utf8(wide_string, utf8_string, mbcount + 1); if (mbcount == -1) return NULL; return utf8_string; } /* convert UTF-8 string to wide string */ zwchar *utf8_to_wide_string(utf8_string) char *utf8_string; { int wcount; zwchar *wide_string; wcount = utf8_to_ucs4_string(utf8_string, NULL, 0); if (wcount == -1) return NULL; if ((wide_string = (zwchar *) malloc((wcount + 2) * sizeof(zwchar))) == NULL) { ZIPERR(ZE_MEM, "utf8_to_wide_string"); } wcount = utf8_to_ucs4_string(utf8_string, wide_string, wcount + 1); return wide_string; } #endif /* UNICODE_SUPPORT */ /*--------------------------------------------------------------- * Long option support * 8/23/2003 * * Defines function get_option() to get and process the command * line options and arguments from argv[]. The caller calls * get_option() in a loop to get either one option and possible * value or a non-option argument each loop. * * This version does not include argument file support and can * work directly on argv. The argument file code complicates things and * it seemed best to leave it out for now. If argument file support (reading * in command line arguments stored in a file and inserting into * command line where @filename is found) is added later the arguments * can change and a freeable copy of argv will be needed and can be * created using copy_args in the left out code. * * Supports short and long options as defined in the array options[] * in zip.c, multiple short options in an argument (like -jlv), long * option abbreviation (like --te for --temp-file if --te unique), * short and long option values (like -b filename or --temp-file filename * or --temp-file=filename), optional and required values, option negation * by trailing - (like -S- to not include hidden and system files in MSDOS), * value lists (like -x a b c), argument permuting (returning all options * and values before any non-option arguments), and argument files (where any * non-option non-value argument in form @path gets substituted with the * white space separated arguments in the text file at path). In this * version argument file support has been removed to simplify development but * may be added later. * * E. Gordon */ /* message output - char casts are needed to handle constants */ #define oWARN(message) zipwarn((char *) message, "") #define oERR(err,message) ZIPERR(err, (char *) message) /* Although the below provides some support for multibyte characters the proper thing to do may be to use wide characters and support Unicode. May get to it soon. EG */ /* For now stay with muti-byte characters. May support wide characters in Zip 3.1. */ /* multibyte character set support Multibyte characters use typically two or more sequential bytes to represent additional characters than can fit in a single byte character set. The code used here is based on the ANSI mblen function. */ #ifdef MULTIBYTE_GETOPTNS int mb_clen(ptr) ZCONST char *ptr; { /* return the number of bytes that the char pointed to is. Return 1 if null character or error like not start of valid multibyte character. */ int cl; cl = mblen(ptr, MB_CUR_MAX); return (cl > 0) ? cl : 1; } #endif /* moved to zip.h */ #if 0 #ifdef UNICODE_SUPPORT # define MB_CLEN(ptr) (1) # define MB_NEXTCHAR(ptr) ((ptr)++) # ifdef MULTIBYTE_GETOPTNS # undef MULTIBYTE_GETOPTNS # endif #else # ifdef _MBCS # ifndef MULTIBYTE_GETOPTNS # define MULTIBYTE_GETOPTNS # endif # endif /* multibyte character set support Multibyte characters use typically two or more sequential bytes to represent additional characters than can fit in a single byte character set. The code used here is based on the ANSI mblen function. */ # ifdef MULTIBYTE_GETOPTNS local int mb_clen OF((ZCONST char *)); /* declare proto first */ local int mb_clen(ptr) ZCONST char *ptr; { /* return the number of bytes that the char pointed to is. Return 1 if null character or error like not start of valid multibyte character. */ int cl; cl = mblen(ptr, MB_CUR_MAX); return (cl > 0) ? cl : 1; } # define MB_CLEN(ptr) mb_clen(ptr) # define MB_NEXTCHAR(ptr) ((ptr) += MB_CLEN(ptr)) # else # define MB_CLEN(ptr) (1) # define MB_NEXTCHAR(ptr) ((ptr)++) # endif #endif #endif /* constants */ /* function get_args_from_arg_file() can return this in depth parameter */ #define ARG_FILE_ERR -1 /* internal settings for optchar */ #define SKIP_VALUE_ARG -1 #define THIS_ARG_DONE -2 #define START_VALUE_LIST -3 #define IN_VALUE_LIST -4 #define NON_OPTION_ARG -5 #define STOP_VALUE_LIST -6 /* 7/25/04 EG */ #define READ_REST_ARGS_VERBATIM -7 /* global veriables */ int enable_permute = 1; /* yes - return options first */ /* 7/25/04 EG */ int doubledash_ends_options = 1; /* when -- what follows are not options */ /* buffer for error messages (this sizing is a guess but must hold 2 paths) */ #define OPTIONERR_BUF_SIZE (FNMAX * 2 + 4000) local char Far optionerrbuf[OPTIONERR_BUF_SIZE + 1]; /* error messages */ static ZCONST char Far op_not_neg_err[] = "option %s not negatable"; static ZCONST char Far op_req_val_err[] = "option %s requires a value"; static ZCONST char Far op_no_allow_val_err[] = "option %s does not allow a value"; static ZCONST char Far sh_op_not_sup_err[] = "short option '%c' not supported"; static ZCONST char Far oco_req_val_err[] = "option %s requires one character value"; static ZCONST char Far oco_no_mbc_err[] = "option %s does not support multibyte values"; static ZCONST char Far num_req_val_err[] = "option %s requires number value"; static ZCONST char Far long_op_ambig_err[] = "long option '%s' ambiguous"; static ZCONST char Far long_op_not_sup_err[] = "long option '%s' not supported"; static ZCONST char Far no_arg_files_err[] = "argument files not enabled\n"; /* below removed as only used for processing argument files */ /* get_nextarg */ /* get_args_from_string */ /* insert_args */ /* get_args_from_arg_file */ /* copy error, option name, and option description if any to buf */ local int optionerr(buf, err, optind, islong) char *buf; ZCONST char *err; int optind; int islong; { char optname[50]; if (options[optind].name && options[optind].name[0] != '\0') { if (islong) sprintf(optname, "'%s' (%s)", options[optind].longopt, options[optind].name); else sprintf(optname, "'%s' (%s)", options[optind].shortopt, options[optind].name); } else { if (islong) sprintf(optname, "'%s'", options[optind].longopt); else sprintf(optname, "'%s'", options[optind].shortopt); } sprintf(buf, err, optname); return 0; } /* copy_args * * Copy arguments in args, allocating storage with malloc. * Copies until a NULL argument is found or until max_args args * including args[0] are copied. Set max_args to 0 to copy * until NULL. Always terminates returned args[] with NULL arg. * * Any argument in the returned args can be freed with free(). Any * freed argument should be replaced with either another string * allocated with malloc or by NULL if last argument so that free_args * will properly work. */ char **copy_args(args, max_args) char **args; int max_args; { int j; char **new_args; if (args == NULL) { return NULL; } /* count args */ for (j = 0; args[j] && (max_args == 0 || j < max_args); j++) ; if ((new_args = (char **) malloc((j + 1) * sizeof(char *))) == NULL) { oERR(ZE_MEM, "ca"); } for (j = 0; args[j] && (max_args == 0 || j < max_args); j++) { if (args[j] == NULL) { /* null argument is end of args */ new_args[j] = NULL; break; } if ((new_args[j] = malloc(strlen(args[j]) + 1)) == NULL) { free_args(new_args); oERR(ZE_MEM, "ca"); } strcpy(new_args[j], args[j]); } new_args[j] = NULL; return new_args; } /* free args - free args created with one of these functions */ int free_args(args) char **args; { int i; if (args == NULL) { return 0; } for (i = 0; args[i]; i++) { free(args[i]); } free(args); return i; } /* insert_arg * * Insert the argument arg into the array args before argument at_arg. * Return the new count of arguments (argc). * * If free_args is true, this function frees the old args array * (but not the component strings). DO NOT set free_args on original * argv but only on args allocated with malloc. */ int insert_arg(pargs, arg, at_arg, free_args) char ***pargs; ZCONST char *arg; int at_arg; int free_args; { char *newarg = NULL; char **args; char **newargs = NULL; int argnum; int newargnum; int argcnt; int newargcnt; if (pargs == NULL) { return 0; } args = *pargs; /* count args */ if (args == NULL) { argcnt = 0; } else { for (argcnt = 0; args[argcnt]; argcnt++) ; } if (arg == NULL) { /* done */ return argcnt; } newargcnt = argcnt + 1; /* get storage for new args */ if ((newargs = (char **) malloc((newargcnt + 1) * sizeof(char *))) == NULL) { oERR(ZE_MEM, "ia"); } /* copy argument pointers from args to position at_arg, copy arg, then rest args */ argnum = 0; newargnum = 0; if (args) { for (; args[argnum] && argnum < at_arg; argnum++) { newargs[newargnum++] = args[argnum]; } } /* copy new arg */ if ((newarg = (char *) malloc(strlen(arg) + 1)) == NULL) { oERR(ZE_MEM, "ia"); } strcpy(newarg, arg); newargs[newargnum++] = newarg; if (args) { for ( ; args[argnum]; argnum++) { newargs[newargnum++] = args[argnum]; } } newargs[newargnum] = NULL; /* free old args array but not component strings - this assumes that args was allocated with malloc as copy_args does. DO NOT DO THIS on the original argv. */ if (free_args) free(args); *pargs = newargs; return newargnum; } /* ------------------------------------- */ /* get_shortopt * * Get next short option from arg. The state is stored in argnum, optchar, and * option_num so no static storage is used. Returns the option_ID. * * parameters: * args - argv array of arguments * argnum - index of current arg in args * optchar - pointer to index of next char to process. Can be 0 or * const defined at top of this file like THIS_ARG_DONE * negated - on return pointer to int set to 1 if option negated or 0 otherwise * value - on return pointer to string set to value of option if any or NULL * if none. If value is returned then the caller should free() * it when not needed anymore. * option_num - pointer to index in options[] of returned option or * o_NO_OPTION_MATCH if none. Do not change as used by * value lists. * depth - recursion depth (0 at top level, 1 or more in arg files) */ local unsigned long get_shortopt(args, argnum, optchar, negated, value, option_num, depth) char **args; int argnum; int *optchar; int *negated; char **value; int *option_num; int depth; { char *shortopt; int clen; char *nextchar; char *s; char *start; int op; char *arg; int match = -1; /* get arg */ arg = args[argnum]; /* current char in arg */ nextchar = arg + (*optchar); clen = MB_CLEN(nextchar); /* next char in arg */ (*optchar) += clen; /* get first char of short option */ shortopt = arg + (*optchar); /* no value */ *value = NULL; if (*shortopt == '\0') { /* no more options in arg */ *optchar = 0; *option_num = o_NO_OPTION_MATCH; return 0; } /* look for match in options */ clen = MB_CLEN(shortopt); for (op = 0; options[op].option_ID; op++) { s = options[op].shortopt; if (s && s[0] == shortopt[0]) { if (s[1] == '\0' && clen == 1) { /* single char match */ match = op; } else { /* 2 wide short opt. Could support more chars but should use long opts instead */ if (s[1] == shortopt[1]) { /* match 2 char short opt or 2 byte char */ match = op; if (clen == 1) (*optchar)++; break; } } } } if (match > -1) { /* match */ clen = MB_CLEN(shortopt); nextchar = arg + (*optchar) + clen; /* check for trailing dash negating option */ if (*nextchar == '-') { /* negated */ if (options[match].negatable == o_NOT_NEGATABLE) { if (options[match].value_type == o_NO_VALUE) { optionerr(optionerrbuf, op_not_neg_err, match, 0); if (depth > 0) { /* unwind */ oWARN(optionerrbuf); return o_ARG_FILE_ERR; } else { oERR(ZE_PARMS, optionerrbuf); } } } else { *negated = 1; /* set up to skip negating dash */ (*optchar) += clen; clen = 1; } } /* value */ clen = MB_CLEN(arg + (*optchar)); /* optional value, one char value, and number value must follow option */ if (options[match].value_type == o_ONE_CHAR_VALUE) { /* one char value */ if (arg[(*optchar) + clen]) { /* has value */ if (MB_CLEN(arg + (*optchar) + clen) > 1) { /* multibyte value not allowed for now */ optionerr(optionerrbuf, oco_no_mbc_err, match, 0); if (depth > 0) { /* unwind */ oWARN(optionerrbuf); return o_ARG_FILE_ERR; } else { oERR(ZE_PARMS, optionerrbuf); } } if ((*value = (char *) malloc(2)) == NULL) { oERR(ZE_MEM, "gso"); } (*value)[0] = *(arg + (*optchar) + clen); (*value)[1] = '\0'; *optchar += clen; clen = 1; } else { /* one char values require a value */ optionerr(optionerrbuf, oco_req_val_err, match, 0); if (depth > 0) { oWARN(optionerrbuf); return o_ARG_FILE_ERR; } else { oERR(ZE_PARMS, optionerrbuf); } } } else if (options[match].value_type == o_NUMBER_VALUE) { /* read chars until end of number */ start = arg + (*optchar) + clen; if (*start == '+' || *start == '-') { start++; } s = start; for (; isdigit(*s); MB_NEXTCHAR(s)) ; if (s == start) { /* no digits */ optionerr(optionerrbuf, num_req_val_err, match, 0); if (depth > 0) { oWARN(optionerrbuf); return o_ARG_FILE_ERR; } else { oERR(ZE_PARMS, optionerrbuf); } } start = arg + (*optchar) + clen; if ((*value = (char *) malloc((int)(s - start) + 1)) == NULL) { oERR(ZE_MEM, "gso"); } *optchar += (int)(s - start); strncpy(*value, start, (int)(s - start)); (*value)[(int)(s - start)] = '\0'; clen = MB_CLEN(s); } else if (options[match].value_type == o_OPTIONAL_VALUE) { /* optional value */ /* This seemed inconsistent so now if no value attached to argument look to the next argument if that argument is not an option for option value - 11/12/04 EG */ if (arg[(*optchar) + clen]) { /* has value */ /* add support for optional = - 2/6/05 EG */ if (arg[(*optchar) + clen] == '=') { /* skip = */ clen++; } if (arg[(*optchar) + clen]) { if ((*value = (char *)malloc(strlen(arg + (*optchar) + clen) + 1)) == NULL) { oERR(ZE_MEM, "gso"); } strcpy(*value, arg + (*optchar) + clen); } *optchar = THIS_ARG_DONE; } else if (args[argnum + 1] && args[argnum + 1][0] != '-') { /* use next arg for value */ if ((*value = (char *)malloc(strlen(args[argnum + 1]) + 1)) == NULL) { oERR(ZE_MEM, "gso"); } /* using next arg as value */ strcpy(*value, args[argnum + 1]); *optchar = SKIP_VALUE_ARG; } } else if (options[match].value_type == o_REQUIRED_VALUE || options[match].value_type == o_VALUE_LIST) { /* see if follows option */ if (arg[(*optchar) + clen]) { /* has value following option as -ovalue */ /* add support for optional = - 6/5/05 EG */ if (arg[(*optchar) + clen] == '=') { /* skip = */ clen++; } if ((*value = (char *)malloc(strlen(arg + (*optchar) + clen) + 1)) == NULL) { oERR(ZE_MEM, "gso"); } strcpy(*value, arg + (*optchar) + clen); *optchar = THIS_ARG_DONE; } else { /* use next arg for value */ if (args[argnum + 1]) { if ((*value = (char *)malloc(strlen(args[argnum + 1]) + 1)) == NULL) { oERR(ZE_MEM, "gso"); } strcpy(*value, args[argnum + 1]); if (options[match].value_type == o_VALUE_LIST) { *optchar = START_VALUE_LIST; } else { *optchar = SKIP_VALUE_ARG; } } else { /* no value found */ optionerr(optionerrbuf, op_req_val_err, match, 0); if (depth > 0) { oWARN(optionerrbuf); return o_ARG_FILE_ERR; } else { oERR(ZE_PARMS, optionerrbuf); } } } } *option_num = match; return options[match].option_ID; } sprintf(optionerrbuf, sh_op_not_sup_err, *shortopt); if (depth > 0) { /* unwind */ oWARN(optionerrbuf); return o_ARG_FILE_ERR; } else { oERR(ZE_PARMS, optionerrbuf); } return 0; } /* get_longopt * * Get the long option in args array at argnum. * Parameters same as for get_shortopt. */ local unsigned long get_longopt(args, argnum, optchar, negated, value, option_num, depth) char **args; int argnum; int *optchar; int *negated; char **value; int *option_num; int depth; { char *longopt; char *lastchr; char *valuestart; int op; char *arg; int match = -1; *value = NULL; if (args == NULL) { *option_num = o_NO_OPTION_MATCH; return 0; } if (args[argnum] == NULL) { *option_num = o_NO_OPTION_MATCH; return 0; } /* copy arg so can chop end if value */ if ((arg = (char *)malloc(strlen(args[argnum]) + 1)) == NULL) { oERR(ZE_MEM, "glo"); } strcpy(arg, args[argnum]); /* get option */ longopt = arg + 2; /* no value */ *value = NULL; /* find = */ for (lastchr = longopt, valuestart = longopt; *valuestart && *valuestart != '='; lastchr = valuestart, MB_NEXTCHAR(valuestart)) ; if (*valuestart) { /* found =value */ *valuestart = '\0'; valuestart++; } else { valuestart = NULL; } if (*lastchr == '-') { /* option negated */ *negated = 1; *lastchr = '\0'; } else { *negated = 0; } /* look for long option match */ for (op = 0; options[op].option_ID; op++) { if (options[op].longopt && strcmp(options[op].longopt, longopt) == 0) { /* exact match */ match = op; break; } if (options[op].longopt && strncmp(options[op].longopt, longopt, strlen(longopt)) == 0) { if (match > -1) { sprintf(optionerrbuf, long_op_ambig_err, longopt); free(arg); if (depth > 0) { /* unwind */ oWARN(optionerrbuf); return o_ARG_FILE_ERR; } else { oERR(ZE_PARMS, optionerrbuf); } } match = op; } } if (match == -1) { sprintf(optionerrbuf, long_op_not_sup_err, longopt); free(arg); if (depth > 0) { oWARN(optionerrbuf); return o_ARG_FILE_ERR; } else { oERR(ZE_PARMS, optionerrbuf); } } /* one long option an arg */ *optchar = THIS_ARG_DONE; /* if negated then see if allowed */ if (*negated && options[match].negatable == o_NOT_NEGATABLE) { optionerr(optionerrbuf, op_not_neg_err, match, 1); free(arg); if (depth > 0) { /* unwind */ oWARN(optionerrbuf); return o_ARG_FILE_ERR; } else { oERR(ZE_PARMS, optionerrbuf); } } /* get value */ if (options[match].value_type == o_OPTIONAL_VALUE) { /* optional value in form option=value */ if (valuestart) { /* option=value */ if ((*value = (char *)malloc(strlen(valuestart) + 1)) == NULL) { free(arg); oERR(ZE_MEM, "glo"); } strcpy(*value, valuestart); } } else if (options[match].value_type == o_REQUIRED_VALUE || options[match].value_type == o_NUMBER_VALUE || options[match].value_type == o_ONE_CHAR_VALUE || options[match].value_type == o_VALUE_LIST) { /* handle long option one char and number value as required value */ if (valuestart) { /* option=value */ if ((*value = (char *)malloc(strlen(valuestart) + 1)) == NULL) { free(arg); oERR(ZE_MEM, "glo"); } strcpy(*value, valuestart); } else { /* use next arg */ if (args[argnum + 1]) { if ((*value = (char *)malloc(strlen(args[argnum + 1]) + 1)) == NULL) { free(arg); oERR(ZE_MEM, "glo"); } /* using next arg as value */ strcpy(*value, args[argnum + 1]); if (options[match].value_type == o_VALUE_LIST) { *optchar = START_VALUE_LIST; } else { *optchar = SKIP_VALUE_ARG; } } else { /* no value found */ optionerr(optionerrbuf, op_req_val_err, match, 1); free(arg); if (depth > 0) { /* unwind */ oWARN(optionerrbuf); return o_ARG_FILE_ERR; } else { oERR(ZE_PARMS, optionerrbuf); } } } } else if (options[match].value_type == o_NO_VALUE) { /* this option does not accept a value */ if (valuestart) { /* --option=value */ optionerr(optionerrbuf, op_no_allow_val_err, match, 1); free(arg); if (depth > 0) { oWARN(optionerrbuf); return o_ARG_FILE_ERR; } else { oERR(ZE_PARMS, optionerrbuf); } } } free(arg); *option_num = match; return options[match].option_ID; } /* get_option * * Main interface for user. Use this function to get options, values and * non-option arguments from a command line provided in argv form. * * To use get_option() first define valid options by setting * the global variable options[] to an array of option_struct. Also * either change defaults below or make variables global and set elsewhere. * Zip uses below defaults. * * Call get_option() to get an option (like -b or --temp-file) and any * value for that option (like filename for -b) or a non-option argument * (like archive name) each call. If *value* is not NULL after calling * get_option() it is a returned value and the caller should either store * the char pointer or free() it before calling get_option() again to avoid * leaking memory. If a non-option non-value argument is returned get_option() * returns o_NON_OPTION_ARG and value is set to the entire argument. * When there are no more arguments get_option() returns 0. * * The parameters argnum (after set to 0 on initial call), * optchar, first_nonopt_arg, option_num, and depth (after initial * call) are set and maintained by get_option() and should not be * changed. The parameters argc, negated, and value are outputs and * can be used by the calling program. get_option() returns either the * option_ID for the current option, a special value defined in * zip.h, or 0 when no more arguments. * * The value returned by get_option() is the ID value in the options * table. This value can be duplicated in the table if different * options are really the same option. The index into the options[] * table is given by option_num, though the ID should be used as * option numbers change when the table is changed. The ID must * not be 0 for any option as this ends the table. If get_option() * finds an option not in the table it calls oERR to post an * error and exit. Errors also result if the option requires a * value that is missing, a value is present but the option does * not take one, and an option is negated but is not * negatable. Non-option arguments return o_NON_OPTION_ARG * with the entire argument in value. * * For Zip, permuting is on and all options and their values are * returned before any non-option arguments like archive name. * * The arguments "-" alone and "--" alone return as non-option arguments. * Note that "-" should not be used as part of a short option * entry in the table but can be used in the middle of long * options such as in the long option "a-long-option". Now "--" alone * stops option processing, returning any arguments following "--" as * non-option arguments instead of options. * * Argument file support is removed from this version. It may be added later. * * After each call: * argc is set to the current size of args[] but should not change * with argument file support removed, * argnum is the index of the current arg, * value is either the value of the returned option or non-option * argument or NULL if option with no value, * negated is set if the option was negated by a trailing dash (-) * option_num is set to either the index in options[] for the option or * o_NO_OPTION_MATCH if no match. * Negation is checked before the value is read if the option is negatable so * that the - is not included in the value. If the option is not negatable * but takes a value then the - will start the value. If permuting then * argnum and first_nonopt_arg are unreliable and should not be used. * * Command line is read from left to right. As get_option() finds non-option * arguments (arguments not starting with - and that are not values to options) * it moves later options and values in front of the non-option arguments. * This permuting is turned off by setting enable_permute to 0. Then * get_option() will return options and non-option arguments in the order * found. Currently permuting is only done after an argument is completely * processed so that any value can be moved with options they go with. All * state information is stored in the parameters argnum, optchar, * first_nonopt_arg and option_num. You should not change these after the * first call to get_option(). If you need to back up to a previous arg then * set argnum to that arg (remembering that args may have been permuted) and * set optchar = 0 and first_nonopt_arg to the first non-option argument if * permuting. After all arguments are returned the next call to get_option() * returns 0. The caller can then call free_args(args) if appropriate. * * get_option() accepts arguments in the following forms: * short options * of 1 and 2 characters, e.g. a, b, cc, d, and ba, after a single * leading -, as in -abccdba. In this example if 'b' is followed by 'a' * it matches short option 'ba' else it is interpreted as short option * b followed by another option. The character - is not legal as a * short option or as part of a 2 character short option. * * If a short option has a value it immediately follows the option or * if that option is the end of the arg then the next arg is used as * the value. So if short option e has a value, it can be given as * -evalue * or * -e value * and now * -e=value * but now that = is optional a leading = is stripped for the first. * This change allows optional short option values to be defaulted as * -e= * Either optional or required values can be specified. Optional values * now use both forms as ignoring the later got confusing. Any * non-value short options can preceed a valued short option as in * -abevalue * Some value types (one_char and number) allow options after the value * so if oc is an option that takes a character and n takes a number * then * -abocVccn42evalue * returns value V for oc and value 42 for n. All values are strings * so programs may have to convert the "42" to a number. See long * options below for how value lists are handled. * * Any short option can be negated by following it with -. Any - is * handled and skipped over before any value is read unless the option * is not negatable but takes a value and then - starts the value. * * If the value for an optional value is just =, then treated as no * value. * * long options * of arbitrary length are assumed if an arg starts with -- but is not * exactly --. Long options are given one per arg and can be abbreviated * if the abbreviation uniquely matches one of the long options. * Exact matches always match before partial matches. If ambiguous an * error is generated. * * Values are specified either in the form * --longoption=value * or can be the following arg if the value is required as in * --longoption value * Optional values to long options must be in the first form. * * Value lists are specified by o_VALUE_LIST and consist of an option * that takes a value followed by one or more value arguments. * The two forms are * --option=value * or * -ovalue * for a single value or * --option value1 value2 value3 ... --option2 * or * -o value1 value2 value3 ... * for a list of values. The list ends at the next option, the * end of the command line, or at a single "@" argument. * Each value is treated as if it was preceeded by the option, so * --option1 val1 val2 * with option1 value_type set to o_VALUE_LIST is the same as * --option1=val1 --option1=val2 * * Long options can be negated by following the option with - as in * --longoption- * Long options with values can also be negated if this makes sense for * the caller as: * --longoption-=value * If = is not followed by anything it is treated as no value. * * @path * When an argument in the form @path is encountered, the file at path * is opened and white space separated arguments read from the file * and inserted into the command line at that point as if the contents * of the file were directly typed at that location. The file can * have options, files to zip, or anything appropriate at that location * in the command line. Since Zip has permuting enabled, options and * files will propagate to the appropriate locations in the command * line. * * Argument files support has been removed from this version. It may * be added back later. * * non-option argument * is any argument not given above. If enable_permute is 1 then * these are returned after all options, otherwise all options and * args are returned in order. Returns option ID o_NON_OPTION_ARG * and sets value to the argument. * * * Arguments to get_option: * char ***pargs - pointer to arg array in the argv form * int *argc - returns the current argc for args incl. args[0] * int *argnum - the index of the current argument (caller * should set = 0 on first call and not change * after that) * int *optchar - index of next short opt in arg or special * int *first_nonopt_arg - used by get_option to permute args * int *negated - option was negated (had trailing -) * char *value - value of option if any (free when done with it) or NULL * int *option_num - the index in options of the last option returned * (can be o_NO_OPTION_MATCH) * int recursion_depth - current depth of recursion * (always set to 0 by caller) * (always 0 with argument files support removed) * * Caller should only read the returned option ID and the value, negated, * and option_num (if required) parameters after each call. * * Ed Gordon * 24 August 2003 (last updated 2 April 2008 EG) * */ unsigned long get_option(pargs, argc, argnum, optchar, value, negated, first_nonopt_arg, option_num, recursion_depth) char ***pargs; int *argc; int *argnum; int *optchar; char **value; int *negated; int *first_nonopt_arg; int *option_num; int recursion_depth; { char **args; unsigned long option_ID; int argcnt; int first_nonoption_arg; char *arg = NULL; int h; int optc; int argn; int j; int v; int read_rest_args_verbatim = 0; /* 7/25/04 - ignore options and arg files for rest args */ /* value is outdated. The caller should free value before calling get_option again. */ *value = NULL; /* if args is NULL then done */ if (pargs == NULL) { *argc = 0; return 0; } args = *pargs; if (args == NULL) { *argc = 0; return 0; } /* count args */ for (argcnt = 0; args[argcnt]; argcnt++) ; /* if no provided args then nothing to do */ if (argcnt < 1 || (recursion_depth == 0 && argcnt < 2)) { *argc = argcnt; /* return 0 to note that no args are left */ return 0; } *negated = 0; first_nonoption_arg = *first_nonopt_arg; argn = *argnum; optc = *optchar; if (optc == READ_REST_ARGS_VERBATIM) { read_rest_args_verbatim = 1; } if (argn == -1 || (recursion_depth == 0 && argn == 0)) { /* first call */ /* if depth = 0 then args[0] is argv[0] so skip */ *option_num = o_NO_OPTION_MATCH; optc = THIS_ARG_DONE; first_nonoption_arg = -1; } /* if option_num is set then restore last option_ID in case continuing value list */ option_ID = 0; if (*option_num != o_NO_OPTION_MATCH) { option_ID = options[*option_num].option_ID; } /* get next option if any */ for (;;) { if (read_rest_args_verbatim) { /* rest of args after "--" are non-option args if doubledash_ends_options set */ argn++; if (argn > argcnt || args[argn] == NULL) { /* done */ option_ID = 0; break; } arg = args[argn]; if ((*value = (char *)malloc(strlen(arg) + 1)) == NULL) { oERR(ZE_MEM, "go"); } strcpy(*value, arg); *option_num = o_NO_OPTION_MATCH; option_ID = o_NON_OPTION_ARG; break; /* permute non-option args after option args so options are returned first */ } else if (enable_permute) { if (optc == SKIP_VALUE_ARG || optc == THIS_ARG_DONE || optc == START_VALUE_LIST || optc == IN_VALUE_LIST || optc == STOP_VALUE_LIST) { /* moved to new arg */ if (first_nonoption_arg > -1 && args[first_nonoption_arg]) { /* do the permuting - move non-options after this option */ /* if option and value separate args or starting list skip option */ if (optc == SKIP_VALUE_ARG || optc == START_VALUE_LIST) { v = 1; } else { v = 0; } for (h = first_nonoption_arg; h < argn; h++) { arg = args[first_nonoption_arg]; for (j = first_nonoption_arg; j < argn + v; j++) { args[j] = args[j + 1]; } args[j] = arg; } first_nonoption_arg += 1 + v; } } } else if (optc == NON_OPTION_ARG) { /* if not permuting then already returned arg */ optc = THIS_ARG_DONE; } /* value lists */ if (optc == STOP_VALUE_LIST) { optc = THIS_ARG_DONE; } if (optc == START_VALUE_LIST || optc == IN_VALUE_LIST) { if (optc == START_VALUE_LIST) { /* already returned first value */ argn++; optc = IN_VALUE_LIST; } argn++; arg = args[argn]; /* if end of args and still in list and there are non-option args then terminate list */ if (arg == NULL && (optc == START_VALUE_LIST || optc == IN_VALUE_LIST) && first_nonoption_arg > -1) { /* terminate value list with @ */ /* this is only needed for argument files */ /* but is also good for show command line so command lines with lists can always be read back in */ argcnt = insert_arg(&args, "@", first_nonoption_arg, 1); argn++; if (first_nonoption_arg > -1) { first_nonoption_arg++; } } arg = args[argn]; if (arg && arg[0] == '@' && arg[1] == '\0') { /* inserted arguments terminator */ optc = STOP_VALUE_LIST; continue; } else if (arg && arg[0] != '-') { /* not option */ /* - and -- are not allowed in value lists unless escaped */ /* another value in value list */ if ((*value = (char *)malloc(strlen(args[argn]) + 1)) == NULL) { oERR(ZE_MEM, "go"); } strcpy(*value, args[argn]); break; } else { argn--; optc = THIS_ARG_DONE; } } /* move to next arg */ if (optc == SKIP_VALUE_ARG) { argn += 2; optc = 0; } else if (optc == THIS_ARG_DONE) { argn++; optc = 0; } if (argn > argcnt) { break; } if (args[argn] == NULL) { /* done unless permuting and non-option args */ if (first_nonoption_arg > -1 && args[first_nonoption_arg]) { /* return non-option arguments at end */ if (optc == NON_OPTION_ARG) { first_nonoption_arg++; } /* after first pass args are permuted but skipped over non-option args */ /* swap so argn points to first non-option arg */ j = argn; argn = first_nonoption_arg; first_nonoption_arg = j; } if (argn > argcnt || args[argn] == NULL) { /* done */ option_ID = 0; break; } } /* after swap first_nonoption_arg points to end which is NULL */ if (first_nonoption_arg > -1 && (args[first_nonoption_arg] == NULL)) { /* only non-option args left */ if (optc == NON_OPTION_ARG) { argn++; } if (argn > argcnt || args[argn] == NULL) { /* done */ option_ID = 0; break; } if ((*value = (char *)malloc(strlen(args[argn]) + 1)) == NULL) { oERR(ZE_MEM, "go"); } strcpy(*value, args[argn]); optc = NON_OPTION_ARG; option_ID = o_NON_OPTION_ARG; break; } arg = args[argn]; /* is it an option */ if (arg[0] == '-') { /* option */ if (arg[1] == '\0') { /* arg = - */ /* treat like non-option arg */ *option_num = o_NO_OPTION_MATCH; if (enable_permute) { /* permute args to move all non-option args to end */ if (first_nonoption_arg < 0) { first_nonoption_arg = argn; } argn++; } else { /* not permute args so return non-option args when found */ if ((*value = (char *)malloc(strlen(arg) + 1)) == NULL) { oERR(ZE_MEM, "go"); } strcpy(*value, arg); optc = NON_OPTION_ARG; option_ID = o_NON_OPTION_ARG; break; } } else if (arg[1] == '-') { /* long option */ if (arg[2] == '\0') { /* arg = -- */ if (doubledash_ends_options) { /* Now -- stops permuting and forces the rest of the command line to be read verbatim - 7/25/04 EG */ /* never permute args after -- and return as non-option args */ if (first_nonoption_arg < 1) { /* -- is first non-option argument - 8/7/04 EG */ argn--; } else { /* go back to start of non-option args - 8/7/04 EG */ argn = first_nonoption_arg - 1; } /* disable permuting and treat remaining arguments as not options */ read_rest_args_verbatim = 1; optc = READ_REST_ARGS_VERBATIM; } else { /* treat like non-option arg */ *option_num = o_NO_OPTION_MATCH; if (enable_permute) { /* permute args to move all non-option args to end */ if (first_nonoption_arg < 0) { first_nonoption_arg = argn; } argn++; } else { /* not permute args so return non-option args when found */ if ((*value = (char *)malloc(strlen(arg) + 1)) == NULL) { oERR(ZE_MEM, "go"); } strcpy(*value, arg); optc = NON_OPTION_ARG; option_ID = o_NON_OPTION_ARG; break; } } } else { option_ID = get_longopt(args, argn, &optc, negated, value, option_num, recursion_depth); if (option_ID == o_ARG_FILE_ERR) { /* unwind as only get this if recursion_depth > 0 */ return option_ID; } break; } } else { /* short option */ option_ID = get_shortopt(args, argn, &optc, negated, value, option_num, recursion_depth); if (option_ID == o_ARG_FILE_ERR) { /* unwind as only get this if recursion_depth > 0 */ return option_ID; } if (optc == 0) { /* if optc = 0 then ran out of short opts this arg */ optc = THIS_ARG_DONE; } else { break; } } #if 0 /* argument file code left out so for now let filenames start with @ */ } else if (allow_arg_files && arg[0] == '@') { /* arg file */ oERR(ZE_PARMS, no_arg_files_err); #endif } else { /* non-option */ if (enable_permute) { /* permute args to move all non-option args to end */ if (first_nonoption_arg < 0) { first_nonoption_arg = argn; } argn++; } else { /* no permute args so return non-option args when found */ if ((*value = (char *)malloc(strlen(arg) + 1)) == NULL) { oERR(ZE_MEM, "go"); } strcpy(*value, arg); *option_num = o_NO_OPTION_MATCH; optc = NON_OPTION_ARG; option_ID = o_NON_OPTION_ARG; break; } } } *pargs = args; *argc = argcnt; *first_nonopt_arg = first_nonoption_arg; *argnum = argn; *optchar = optc; return option_ID; } zip30/file_id.diz0100644000076400000060000000105510625513170012065 0ustar ediskInfo-ZIP's Zip 3.0: generic C sources. Complete C source code for Info-ZIP's PKZIP-compatible .zip archiver, for all supported compilers and platforms (Unix, OS/2, MS-DOS, NT, VMS, Amiga, Atari, Mac, Acorn, VM/CMS, etc.), plus lots of pretty decent documentation. Includes Info-ZIP's ZCrypt 2.9 for PKWARE-compatible standard encryption and decryption support for Info-ZIP's Zip 2.32, Zip 3.0, UnZip 5.52, UnZip 6.0, and WiZ 5.02 (and later). This is FREE (but copyrighted) software. See LICENSE for details on distribution and reuse. zip30/globals.c0100644000076400000060000002717711016320516011561 0ustar edisk/* globals.c - Zip 3 Copyright (c) 1990-2008 Info-ZIP. All rights reserved. See the accompanying file LICENSE, version 2007-Mar-4 or later (the contents of which are also included in zip.h) for terms of use. If, for some reason, all these files are missing, the Info-ZIP license also may be found at: ftp://ftp.info-zip.org/pub/infozip/license.html */ /* * globals.c by Mark Adler */ #define __GLOBALS_C #define GLOBALS /* include definition of errors[] in zip.h */ #ifndef UTIL #define UTIL /* do not declare the read_buf variable */ #endif #include "zip.h" /* Handy place to build error messages */ char errbuf[FNMAX+4081]; /* Argument processing globals */ int recurse = 0; /* 1=recurse into directories encountered */ int dispose = 0; /* 1=remove files after put in zip file */ int pathput = 1; /* 1=store path with name */ #ifdef RISCOS int scanimage = 1; /* 1=scan through image files */ #endif int method = BEST; /* one of BEST, DEFLATE (only), or STORE (only) */ int dosify = 0; /* 1=make new entries look like MSDOS */ int verbose = 0; /* 1=report oddities in zip file structure */ int fix = 0; /* 1=fix the zip file, 2=FF, 3=ZipNote */ int filesync = 0; /* 1=file sync, delete entries not on file system */ int adjust = 0; /* 1=adjust offsets for sfx'd file (keep preamble) */ int level = 6; /* 0=fastest compression, 9=best compression */ int translate_eol = 0; /* Translate end-of-line LF -> CR LF */ #ifdef VMS int vmsver = 0; /* 1=append VMS version number to file names */ int vms_native = 0; /* 1=store in VMS format */ int vms_case_2 = 0; /* ODS2 file name case in VMS. -1: down. */ int vms_case_5 = 0; /* ODS5 file name case in VMS. +1: preserve. */ #endif /* VMS */ #if defined(OS2) || defined(WIN32) int use_longname_ea = 0; /* 1=use the .LONGNAME EA as the file's name */ #endif /* 9/26/04 */ int no_wild = 0; /* 1 = wildcards are disabled */ int allow_regex = 0; /* 1 = allow [list] matching */ #ifdef WILD_STOP_AT_DIR int wild_stop_at_dir = 1; /* default wildcards do not include / in matches */ #else int wild_stop_at_dir = 0; /* default wildcards do include / in matches */ #endif #ifdef UNICODE_SUPPORT int using_utf8 = 0; /* 1 if current character set UTF-8 */ # ifdef WIN32 int no_win32_wide = -1; /* 1 = no wide functions, like GetFileAttributesW() */ # endif #endif ulg skip_this_disk = 0; int des_good = 0; /* Good data descriptor found */ ulg des_crc = 0; /* Data descriptor CRC */ uzoff_t des_csize = 0; /* Data descriptor csize */ uzoff_t des_usize = 0; /* Data descriptor usize */ /* dots 10/20/04 */ zoff_t dot_size = 0; /* bytes processed in deflate per dot, 0 = no dots */ zoff_t dot_count = 0; /* buffers seen, recyles at dot_size */ /* status 10/30/04 */ int display_counts = 0; /* display running file count */ int display_bytes = 0; /* display running bytes remaining */ int display_globaldots = 0; /* display dots for archive instead of each file */ int display_volume = 0; /* display current input and output volume (disk) numbers */ int display_usize = 0; /* display uncompressed bytes */ ulg files_so_far = 0; /* files processed so far */ ulg bad_files_so_far = 0; /* bad files skipped so far */ ulg files_total = 0; /* files total to process */ uzoff_t bytes_so_far = 0; /* bytes processed so far (from initial scan) */ uzoff_t good_bytes_so_far = 0;/* good bytes read so far */ uzoff_t bad_bytes_so_far = 0; /* bad bytes skipped so far */ uzoff_t bytes_total = 0; /* total bytes to process (from initial scan) */ /* logfile 6/5/05 */ int logall = 0; /* 0 = warnings/errors, 1 = all */ FILE *logfile = NULL; /* pointer to open logfile or NULL */ int logfile_append = 0; /* append to existing logfile */ char *logfile_path = NULL; /* pointer to path of logfile */ int hidden_files = 0; /* process hidden and system files */ int volume_label = 0; /* add volume label */ int dirnames = 1; /* include directory entries by default */ int filter_match_case = 1; /* 1=match case when filter() */ int diff_mode = 0; /* 1=require --out and only store changed and add */ #if defined(WIN32) int only_archive_set = 0; /* include only files with DOS archive bit set */ int clear_archive_bits = 0; /* clear DOS archive bit of included files */ #endif int linkput = 0; /* 1=store symbolic links as such */ int noisy = 1; /* 0=quiet operation */ int extra_fields = 1; /* 0=create minimum, 1=don't copy old, 2=keep old */ int use_descriptors = 0; /* 1=use data descriptors 12/29/04 */ int zip_to_stdout = 0; /* output zipfile to stdout 12/30/04 */ int allow_empty_archive = 0; /* if no files, create empty archive anyway 12/28/05 */ int copy_only = 0; /* 1=copying archive entries only */ int allow_fifo = 0; /* 1=allow reading Unix FIFOs, waiting if pipe open */ int show_files = 0; /* show files to operate on and exit (=2 log only) */ int output_seekable = 1; /* 1 = output seekable 3/13/05 EG */ #ifdef ZIP64_SUPPORT /* zip64 support 10/4/03 */ int force_zip64 = -1; /* if 1 force entries to be zip64, 0 force not zip64 */ /* mainly for streaming from stdin */ int zip64_entry = 0; /* current entry needs Zip64 */ int zip64_archive = 0; /* if 1 then at least 1 entry needs zip64 */ #endif #ifdef NTSD_EAS int use_privileges = 0; /* 1=use security privilege overrides */ #endif #ifndef RISCOS #ifndef QDOS #ifndef TANDEM char *special = ".Z:.zip:.zoo:.arc:.lzh:.arj"; /* List of special suffixes */ #else /* TANDEM */ char *special = " Z: zip: zoo: arc: lzh: arj"; /* List of special suffixes */ #endif #else /* QDOS */ char *special = "_Z:_zip:_zoo:_arc:_lzh:_arj"; /* List of special suffixes */ #endif #else /* RISCOS */ char *special = "DDC:D96:68E"; #endif /* ?RISCOS */ char *key = NULL; /* Scramble password if scrambling */ char *tempath = NULL; /* Path for temporary files */ FILE *mesg; /* stdout by default, stderr for piping */ #ifdef UNICODE_SUPPORT int utf8_force = 0; /* 1=force storing UTF-8 as standard per AppNote bit 11 */ #endif int unicode_escape_all = 0; /* 1=escape all non-ASCII characters in paths */ int unicode_mismatch = 1; /* unicode mismatch is 0=error, 1=warn, 2=ignore, 3=no */ time_t scan_delay = 5; /* seconds before display Scanning files message */ time_t scan_dot_time = 2; /* time in seconds between Scanning files dots */ time_t scan_start = 0; /* start of scan */ time_t scan_last = 0; /* time of last message */ int scan_started = 0; /* scan has started */ uzoff_t scan_count = 0; /* Used for Scanning files ... message */ ulg before = 0; /* 0=ignore, else exclude files before this time */ ulg after = 0; /* 0=ignore, else exclude files newer than this time */ /* Zip file globals */ char *zipfile; /* New or existing zip archive (zip file) */ /* zip64 support 08/31/2003 R.Nausedat */ /* all are across splits - subtract bytes_prev_splits to get offsets for current disk */ uzoff_t zipbeg; /* Starting offset of zip structures */ uzoff_t cenbeg; /* Starting offset of central dir */ uzoff_t tempzn; /* Count of bytes written to output zip files */ /* 10/28/05 */ char *tempzip = NULL; /* name of temp file */ FILE *y = NULL; /* output file now global so can change in splits */ FILE *in_file = NULL; /* current input file for splits */ char *in_path = NULL; /* base name of input archive file */ char *in_split_path = NULL; /* in split path */ char *out_path = NULL; /* base name of output file, usually same as zipfile */ int zip_attributes = 0; /* in split globals */ ulg total_disks = 0; /* total disks in archive */ ulg current_in_disk = 0; /* current read split disk */ uzoff_t current_in_offset = 0; /* current offset in current read disk */ ulg skip_current_disk = 0; /* if != 0 and fix then skip entries on this disk */ /* out split globals */ ulg current_local_disk = 0; /* disk with current local header */ ulg current_disk = 0; /* current disk number */ ulg cd_start_disk = (ulg)-1; /* central directory start disk */ uzoff_t cd_start_offset = 0; /* offset of start of cd on cd start disk */ uzoff_t cd_entries_this_disk = 0; /* cd entries this disk */ uzoff_t total_cd_entries = 0; /* total cd entries in new/updated archive */ ulg zip64_eocd_disk = 0; /* disk with Zip64 End Of Central Directory Record */ uzoff_t zip64_eocd_offset = 0; /* offset for Zip64 EOCD Record */ /* for split method 1 (keep split with local header open and update) */ char *current_local_tempname = NULL; /* name of temp file */ FILE *current_local_file = NULL; /* file pointer for current local header */ uzoff_t current_local_offset = 0; /* offset to start of current local header */ /* global */ uzoff_t bytes_this_split = 0; /* bytes written to the current split */ int read_split_archive = 0; /* 1=scanzipf_reg detected spanning signature */ int split_method = 0; /* 0=no splits, 1=seekable, 2=data desc, -1=no */ uzoff_t split_size = 0; /* how big each split should be */ int split_bell = 0; /* when pause for next split ring bell */ uzoff_t bytes_prev_splits = 0; /* total bytes written to all splits before this */ uzoff_t bytes_this_entry = 0; /* bytes written for this entry across all splits */ int noisy_splits = 0; /* note when splits are being created */ int mesg_line_started = 0; /* 1=started writing a line to mesg */ int logfile_line_started = 0; /* 1=started writing a line to logfile */ #ifdef WIN32 int nonlocal_name = 0; /* Name has non-local characters */ int nonlocal_path = 0; /* Path has non-local characters */ #endif #ifdef UNICODE_SUPPORT int use_wide_to_mb_default = 0; #endif struct zlist far *zfiles = NULL; /* Pointer to list of files in zip file */ /* The limit for number of files using the Zip64 format is 2^64 - 1 (8 bytes) but extent is used for many internal sorts and other tasks and is generally long on 32-bit systems. Because of that, but more because of various memory utilization issues limiting the practical number of central directory entries that can be sorted, the number of actual entries that can be stored probably can't exceed roughly 2^30 on 32-bit systems so extent is probably sufficient. */ extent zcount; /* Number of files in zip file */ int zipfile_exists = 0; /* 1 if zipfile exists */ ush zcomlen; /* Length of zip file comment */ char *zcomment = NULL; /* Zip file comment (not zero-terminated) */ struct zlist far **zsort; /* List of files sorted by name */ #ifdef UNICODE_SUPPORT struct zlist far **zusort; /* List of files sorted by zuname */ #endif /* Files to operate on that are not in zip file */ struct flist far *found = NULL; /* List of names found */ struct flist far * far *fnxt = &found; /* Where to put next name in found list */ extent fcount; /* Count of files in list */ /* Patterns to be matched */ struct plist *patterns = NULL; /* List of patterns to be matched */ unsigned pcount = 0; /* number of patterns */ unsigned icount = 0; /* number of include only patterns */ unsigned Rcount = 0; /* number of -R include patterns */ #ifdef IZ_CHECK_TZ int zp_tz_is_valid; /* signals "timezone info is available" */ #endif zip30/human68k/0040755000076400000060000000000011033727770011434 5ustar ediskzip30/human68k/crc_68.s0100644000076400000060000001005707076030744012704 0ustar edisk;=========================================================================== ; Copyright (c) 1990-2000 Info-ZIP. All rights reserved. ; ; See the accompanying file LICENSE, version 2000-Apr-09 or later ; (the contents of which are also included in zip.h) for terms of use. ; If, for some reason, all these files are missing, the Info-ZIP license ; also may be found at: ftp://ftp.info-zip.org/pub/infozip/license.html ;=========================================================================== ; crc_68 created by Paul Kienitz, last modified 04 Jan 96. ; ; Return an updated 32 bit CRC value, given the old value and a block of data. ; The CRC table used to compute the value is gotten by calling get_crc_table(). ; This replaces the older updcrc() function used in Zip and fUnZip. The ; prototype of the function is: ; ; ulg crc32(ulg crcval, uch *text, extent textlen); ; ; On the Amiga, type extent is always unsigned long, not unsigned int, because ; int can be short or long at whim, but size_t is long. ; ; If using this source on a non-Amiga 680x0 system, note that we treat ; a0/a1/d0/d1 as scratch registers not preserved across function calls. ; We do not bother to support registerized arguments for crc32() -- the ; textlen parm is usually large enough so that savings outside the loop ; are pointless. ; ; Define NO_UNROLLED_LOOPS to use a simple short loop which might be more ; efficient on certain machines with dinky instruction caches ('020?), or for ; processing short strings. If loops are unrolled, the textlen parm must be ; less than 512K; if not unrolled, it must be less than 64K. ; ; 1999/09/23: for Human68k: Modified by Shimazaki Ryo. xdef _crc32 ; (ulg val, uch *buf, extent bufsize) DO_CRC0 MACRO moveq #0,ltemp move.b (textbuf)+,ltemp eor.b crcval,ltemp lsl.w #2,ltemp move.l (crc_table,ltemp.w),ltemp lsr.l #8,crcval eor.l ltemp,crcval ENDM DO_CRC2 MACRO move.b (textbuf)+,btemp eor.b crcval,btemp lsr.l #8,crcval move.l (crc_table,btemp.w*4),ltemp eor.l ltemp,crcval ENDM crc_table reg a0 array of unsigned long crcval reg d0 unsigned long initial value textbuf reg a1 array of unsigned char textbufsize reg d1 unsigned long (count of bytes in textbuf) btemp reg d2 ltemp reg d3 xref _get_crc_table ; ulg *get_crc_table(void) quad _crc32: move.l 8(sp),d0 bne.s valid ;;;;; moveq #0,d0 rts valid: movem.l btemp/ltemp,-(sp) jsr _get_crc_table movea.l d0,crc_table move.l 12(sp),crcval move.l 16(sp),textbuf move.l 20(sp),textbufsize not.l crcval ifdef NO_UNROLLED_LOOPS if CPU==68000 bra.s decr loop: DO_CRC0 decr: dbra textbufsize,loop bra.s done else twenty: moveq #0,btemp bra.s decr2 loop2: DO_CRC2 decr2: dbra textbufsize,loop2 endif ELSE ; !NO_UNROLLED_LOOPS if CPU==68000 moveq #7,btemp and textbufsize,btemp lsr.l #3,textbufsize bra decr8 loop8: DO_CRC0 DO_CRC0 DO_CRC0 DO_CRC0 DO_CRC0 DO_CRC0 DO_CRC0 DO_CRC0 decr8: dbra textbufsize,loop8 bra.s decr1 loop1: DO_CRC0 decr1: dbra btemp,loop1 bra done else twenty: moveq #0,btemp move.l textbufsize,-(sp) lsr.l #3,textbufsize bra decr82 quad loop82: DO_CRC2 DO_CRC2 DO_CRC2 DO_CRC2 DO_CRC2 DO_CRC2 DO_CRC2 DO_CRC2 decr82: dbra textbufsize,loop82 moveq #7,textbufsize and.l (sp)+,textbufsize bra.s decr12 loop12: DO_CRC2 decr12: dbra textbufsize,loop12 endif ENDC ; ?NO_UNROLLED_LOOPS done: movem.l (sp)+,btemp/ltemp not.l crcval ;;;;; move.l crcval,d0 ; crcval already is d0 rts zip30/human68k/deflate.s0100644000076400000060000010656707011110746013226 0ustar edisk;=========================================================================== ; Copyright (c) 1990-1999 Info-ZIP. All rights reserved. ; ; See the accompanying file LICENSE, version 1999-Oct-05 or later ; (the contents of which are also included in zip.h) for terms of use. ; If, for some reason, both of these files are missing, the Info-ZIP license ; also may be found at: ftp://ftp.cdrom.com/pub/infozip/license.html ;=========================================================================== ; This is a 680x0 assembly language translation of the Info-ZIP source file ; deflate.c, by Paul Kienitz. No rights reserved. The function longest_match ; is based in part on match.a by Carsten Steger, which in turn is partly based ; on match.s for 386 by Jean-loup Gailly and Kai Uwe Rommel. Mostly, however, ; this material is based on deflate.c, by Gailly, Rommel, and Igor Mandrichenko. ; This code is not commented very much; see deflate.c for comments that explain ; what the functions are doing. ; ; The symbols that can be used to select different versions are as follows: ; ; CPU020 if defined, use 68020 instructions always. ; ; CPUTEST if defined, check at runtime for CPU type. Another symbol ; specifying the platform-specific test must be used with this. ; If neither of these is defined, use 68000 instructions only. ; Runtime test is nonportable; it is different for each OS. ; ; AMIGA use Amiga-specific test for 68020, if CPUTEST defined. Also ; tells it that registers d0/a0/d1/a1 are not preserved by ; function calls. At present, if AMIGA is not defined, it ; causes functions to preserve all registers. ALL OF THIS CODE ; CURRENTLY ASSUMES THAT REGISTERS D2-D7/A2-A6 WILL BE PRESERVED ; BY ANY FUNCTIONS THAT IT CALLS. ; ; DYN_ALLOC should be defined here if it is defined for C source; tells us ; that big arrays are allocated instead of static. ; ; WSIZE must be defined as the same number used for WSIZE in the C ; source, and must be a power of two <= 32768. As elsewhere, ; the default value is 32768. ; ; INT16 define this if ints are 16 bits; otherwise 32 bit ints assumed. ; ; SMALL_MEM define this if it is defined in the C source; otherwise it uses ; the MEDIUM_MEM model. BIG_MEM and MMAP are *not* supported. ; The FULL_SEARCH option in deflate.c is also not supported. ; ; DEBUG activates some tracing output, as in the C source. ; ; QUADLONG this selects a different version of the innermost longest_match ; loop code for 68020 operations, comparing bytes four at a time ; instead of two at a time. It seems to be a tiny bit faster on ; average, but it's slower often enough that one can't generalize. ; ; This code currently assumes that function results are returned in D0 for ; all platforms. It assumes that args to functions are pushed onto the stack, ; last arg first. It also currently assumes that all C symbols have an ; underscore prepended when referenced from assembly. ; ; 1999/09/23: for Human68k: Modified by Shimazaki Ryo. IFNDEF CPU020 IFNDEF CPUTEST CPU000 equ 1 ENDC ENDC ; Use these macros for accessing variables of type int: IFDEF INT16 MOVINT MACRO _1,_2 move.w _1,_2 ENDM CLRINT MACRO _1 clr.w _1 ENDM INTSIZE equ 2 ELSE ; !INT16 MOVINT MACRO _1,_2 move.l _1,_2 ENDM CLRINT MACRO _1 clr.l _1 ENDM INTSIZE equ 4 ENDC IFDEF DYN_ALLOC BASEPTR MACRO _1,_2 move.l _1,_2 ENDM ELSE BASEPTR MACRO _1,_2 lea _1,_2 ENDM ENDC ; constants we use, many of them adjustable: MAX_MATCH equ 258 MIN_MATCH equ 3 TOO_FAR equ 4096 IFNDEF WSIZE WSIZE equ 32768 ENDC WMASK equ WSIZE-1 MAX_DIST equ WSIZE-MAX_MATCH-MIN_MATCH-1 MIN_LOOKAHEAD equ MAX_MATCH+MIN_MATCH+1 ; IFD BIG_MEM ; NOT supported -- type Pos needs to be 32 bits ;HASH_BITS equ 15 ; ELSE IFDEF SMALL_MEM HASH_BITS equ 13 ELSE HASH_BITS equ 14 ; default -- MEDIUM_MEM ENDC ; ENDC ; BIG_MEM HASH_SIZE equ 1< MOVINT Strst,_strstart ; ct_tally reads this variable moveq #0,d0 move.b -1(Window,Strst.l),d0 movem.l d2/a2,-(sp) MOVINT d0,-(sp) CLRINT -(sp) jsr _ct_tally addq #2*INTSIZE,sp movem.l (sp)+,d2/a2 tst.w d0 beq.s skipliteral FLUSH_B 0 move.l Strst,_block_start skipliteral: addq.w #1,Strst subq.w #1,Look refill: cmp.w #MIN_LOOKAHEAD,Look bhs look_loop bsr fill_window bra look_loop last_tally: tst.w Avail beq last_flush MOVINT Strst,_strstart ; ct_tally reads this variable moveq #0,d0 move.b -1(Window,Strst.l),d0 movem.l d2/a2,-(sp) MOVINT d0,-(sp) CLRINT -(sp) jsr _ct_tally addq #2*INTSIZE,sp movem.l (sp)+,d2/a2 last_flush: FLUSH_B 1 bra deflate_exit ; ================== This is another version used for low compression levels: deflate_fast: moveq #0,MatchL moveq #MIN_MATCH-1,PrevL flook_loop: tst.w Look beq flast_flush IN_STR a0,d0 tst.w Head beq.s fno_new_match move.w Strst,d0 sub.w Head,d0 cmp.w #MAX_DIST,d0 bhi.s fno_new_match move.w PrevL,prev_length ; longest_match reads these variables MOVINT Strst,_strstart MOVINT Head,d0 ; parm for longest_match bsr longest_match ; sets match_start cmp.w Look,d0 ; does length exceed valid data? bls.s fstml move.w Look,d0 fstml: move.w d0,MatchL ; valid length of match fno_new_match: cmp.w #MIN_MATCH,MatchL blo fliteral ; CHECK_MATCH Strst,match_start,MatchL MOVINT Strst,_strstart ; ct_tally reads this variable move.l MatchL,d0 subq.w #MIN_MATCH,d0 movem.l d2/a2,-(sp) MOVINT d0,-(sp) move.l Strst,d0 sub.w (match_start,pc),d0 MOVINT d0,-(sp) jsr _ct_tally ; sets d0 true if we have to flush addq #2*INTSIZE,sp movem.l (sp)+,d2/a2 sub.w MatchL,Look cmp.w (max_lazy_match,pc),MatchL bhi ftoolong subq.w #2,MatchL finsertmatch: addq.w #1,Strst IN_STR a0,d1 ; preserve d0 dbra MatchL,finsertmatch moveq #0,MatchL ; not needed? addq.w #1,Strst bra.s flushfill ftoolong: add.w MatchL,Strst moveq #0,MatchL moveq #0,d1 ; preserve d0 move.b (Window,Strst.l),d1 move.w d1,ins_h ; My assembler objects to passing <1(Window,Strst.l)> directly to UP_HASH... move.b 1(Window,Strst.l),Avail ; Avail is not used in deflate_fast UP_HASH d1,Avail ; preserve d0 IFNE MIN_MATCH-3 FAIL needs to UP_HASH another MIN_MATCH-3 times, but with what arg? ENDC bra.s flushfill fliteral: TRACE_C <(Window,Strst.l)> MOVINT Strst,_strstart ; ct_tally reads this variable moveq #0,d0 move.b (Window,Strst.l),d0 movem.l d2/a2,-(sp) MOVINT d0,-(sp) CLRINT -(sp) jsr _ct_tally ; d0 set if we need to flush addq #2*INTSIZE,sp movem.l (sp)+,d2/a2 addq.w #1,Strst subq.w #1,Look flushfill: tst.w d0 beq.s frefill FLUSH_B 0 move.l Strst,_block_start frefill: cmp.w #MIN_LOOKAHEAD,Look bhs flook_loop bsr fill_window bra flook_loop flast_flush: FLUSH_B 1 ; sets our return value deflate_exit: MOVINT Strst,_strstart ; save back cached values move.w PrevL,prev_length move.w Look,lookahead movem.l (sp)+,DEFREGS rts ; ========================================================================= ; void fill_window(void) calls the input function to refill the sliding ; window that we use to find substring matches in. More reg Head ; local variable in fill_window WindTop reg Prev ; local variable used for sliding SlidIx reg PrevL ; local variable used for sliding FWREGS reg d2-d5/a2-a6 ; does NOT include Look and Strst ; all registers available to be clobbered by the sliding operation: ; we exclude More, WindTop, SlidIx, Look, Strst, Window, a4 and a7. SPAREGS reg d0-d3/a0-a1/a5-a6 SPCOUNT equ 8 ; number of registers in SPAREGS _fill_window: ; C-callable entry point movem.l Look/Strst,-(sp) IFDEF INT16 moveq #0,Strst ; Strst must be valid as a long ENDC MOVINT (_strstart,pc),Strst move.w (lookahead,pc),Look BASEPTR _window,Window bsr.s fill_window MOVINT Strst,_strstart move.w Look,lookahead movem.l (sp)+,Look/Strst rts ; strstart, lookahead, and window must be cached in Strst, Look, and Window: fill_window: ; asm-callable entry point movem.l FWREGS,-(sp) move.w (eofile,pc),d0 ; we put this up here for speed bne fwdone and.l #$FFFF,Look ; make sure Look is valid as long fw_refill: move.l (_window_size,pc),More ; <= 64K sub.l Look,More sub.l Strst,More ; Strst is already valid as long cmp.w #EOF,More bne.s notboundary subq.w #1,More bra checkend notboundary: move.w (sliding,pc),d0 beq checkend cmp.w #WSIZE+MAX_DIST,Strst blo checkend IF (32768-WSIZE)>0 lea WSIZE(Window),WindTop ; WindTop is aligned when Window is ELSE move.l Window,WindTop add.l #WSIZE,WindTop ENDC move.l Window,d0 and.w #3,d0 beq.s isaligned subq.w #1,d0 align: move.b (WindTop)+,(Window)+ ; copy up to a longword boundary dbra d0,align isaligned: ; This is faster than a simple move.l (WindTop)+,(Window)+ / dbra loop: move.w #(WSIZE-1)/(4*SPCOUNT),SlidIx slide: movem.l (WindTop)+,SPAREGS ; copy, 32 bytes at a time! movem.l SPAREGS,(Window) ; a slight overshoot doesn't matter. lea 4*SPCOUNT(Window),Window ; can't use (aN)+ as movem.l dest dbra SlidIx,slide BASEPTR _window,Window ; restore cached value sub.w #WSIZE,match_start sub.w #WSIZE,Strst sub.l #WSIZE,_block_start add.w #WSIZE,More BASEPTR _head,a0 move.w #HASH_SIZE-1,d0 fixhead: move.w (a0),d1 sub.w #WSIZE,d1 bpl.s headok moveq #0,d1 headok: move.w d1,(a0)+ dbra d0,fixhead BASEPTR _prev,a0 move.w #WSIZE-1,d0 fixprev: move.w (a0),d1 sub.w #WSIZE,d1 bpl.s prevok moveq #0,d1 prevok: move.w d1,(a0)+ dbra d0,fixprev TRACE_C #'.' move _verbose+INTSIZE-2,d0 beq checkend movem.l d2/a2,-(sp) xref _print_period jsr _print_period movem.l (sp)+,d2/a2 checkend: ; assert eofile is false movem.l d2/a2,-(sp) MOVINT More,-(sp) ; assert More's upper word is zero move.l Strst,d0 add.w Look,d0 add.l Window,d0 move.l d0,-(sp) move.l _read_buf,a0 jsr (a0) ; refill the upper part of the window addq #4+INTSIZE,sp movem.l (sp)+,d2/a2 tst.w d0 beq.s iseof cmp.w #EOF,d0 beq.s iseof add.w d0,Look cmp.w #MIN_LOOKAHEAD,Look blo fw_refill ; eofile is still false bra.s fwdone iseof: move.w #1,eofile fwdone: movem.l (sp)+,FWREGS rts ; ========================================================================= ; void lm_free(void) frees dynamic arrays in the DYN_ALLOC version. ;;; xdef _lm_free ; the entry point _lm_free: IFDEF DYN_ALLOC move.l _window,d0 beq.s lf_no_window movem.l d2/a2,-(sp) move.l d0,-(sp) jsr _free addq #4,sp movem.l (sp)+,d2/a2 clr.l _window lf_no_window: move.l _prev,d0 beq.s lf_no_prev movem.l d2/a2,-(sp) move.l d0,-(sp) jsr _free move.l _head,(sp) ; reuse the same stack arg slot jsr _free addq #4,sp movem.l (sp)+,d2/a2 clr.l _prev clr.l _head lf_no_prev: ENDC rts ; ============================================================================ ; void lm_init(int pack_level, unsigned short *flags) allocates dynamic arrays ; if any, and initializes all variables so that deflate() is ready to go. ;;; xdef _lm_init ; the entry point Level reg d2 ;Window reg a2 ; as in deflate() _lm_init: MOVINT 4(sp),d0 move.l 4+INTSIZE(sp),a0 move.w d0,Level cmp.w #1,Level blt.s levelerr bgt.s try9 bset.b #B_FAST,1(a0) try9: cmp.w #9,Level bgt.s levelerr blt.s levelok bset.b #B_SLOW,1(a0) bra.s levelok levelerr: pea (level_message,pc) jsr _error ; never returns levelok: clr.w sliding move.l (_window_size,pc),d0 bne.s gotawindowsize move.w #1,sliding move.l #2*WSIZE,_window_size gotawindowsize: BASEPTR _window,Window IFDEF DYN_ALLOC move.l Window,d0 ; fake tst.l bne.s gotsomewind CAL_SH WSIZE move.l d0,Window move.l d0,_window bne.s gotsomewind pea (window_message,pc) bra error gotsomewind: tst.l _prev bne.s gotsomehead CAL_SH WSIZE move.l d0,_prev beq.s nohead CAL_SH HASH_SIZE move.l d0,_head bne.s gotfreshhead ; newly calloc'd memory is zeroed nohead: pea (hash_message,pc) error: MOVINT #ZE_MEM,-(sp) jsr _ziperr ; never returns gotsomehead: ENDC ; DYN_ALLOC move.w #(HASH_SIZE/2)-1,d0 ; two shortwords per loop BASEPTR _head,a0 wipeh: clr.l (a0)+ dbra d0,wipeh gotfreshhead: move.l Level,d0 IFEQ Sizeof_config-8 asl.l #3,d0 ELSE mulu #Sizeof_config,d0 ENDC lea (config_table,pc),a0 add.l d0,a0 move.w Max_lazy(a0),max_lazy_match move.w Good_length(a0),good_match move.w Nice_length(a0),nice_match move.w Max_chain(a0),max_chain_len CLRINT _strstart clr.l _block_start bsr match_init clr.w eofile movem.l d2/a2,-(sp) MOVINT #WSIZE,-(sp) ; We read only 32K because lookahead is short move.l Window,-(sp) ; even when int size is long, as if deflate.c move.l _read_buf,a0 ; were compiled with MAXSEG_64K defined. jsr (a0) addq #4+INTSIZE,sp movem.l (sp)+,d2/a2 move.w d0,lookahead beq.s noread cmp.w #EOF,d0 bne.s irefill noread: move.w #1,eofile clr.w lookahead bra.s init_done irefill: move.w (lookahead,pc),d0 cmp.w #MIN_LOOKAHEAD,d0 bhs.s hashify bsr _fill_window ; use the C-callable version hashify: clr.w ins_h moveq #MIN_MATCH-2,d0 hash1: move.b (Window)+,d1 UP_HASH Level,d1 dbra d0,hash1 init_done: rts ; strings for error messages: IFDEF DYN_ALLOC hash_message dc.b 'hash table allocation',0 window_message dc.b 'window allocation',0 ENDC level_message dc.b 'bad pack level',0 end zip30/human68k/human68k.c0100644000076400000060000002272110154331770013234 0ustar edisk/* Copyright (c) 1990-1999 Info-ZIP. All rights reserved. See the accompanying file LICENSE, version 1999-Oct-05 or later (the contents of which are also included in zip.h) for terms of use. If, for some reason, both of these files are missing, the Info-ZIP license also may be found at: ftp://ftp.cdrom.com/pub/infozip/license.html */ #include "zip.h" #include #include #include #ifndef UTIL #include #endif #define MATCH shmatch #define PAD 0 #ifndef UTIL /* Library functions not in (most) header files */ int utime OF((char *, ztimbuf *)); /* Local functions */ local char *readd OF((DIR *)); local char *readd(DIR* d) { struct dirent* e = readdir(d); return e == NULL ? NULL : e->d_name; } int wild(char* w) { struct _filbuf inf; /* convert FNAMX to malloc - 11/08/04 EG */ char *name; char *p; if (strcmp(w, "-") == 0) /* if compressing stdin */ return newname(w, 0, 0); if ((name = malloc(strlen(w) + 1)) == NULL) { ZIPERR(ZE_MEM, "wild"); } strcpy(name, w); _toslash(name); if ((p = strrchr(name, '/')) == NULL && (p = strrchr(name, ':')) == NULL) p = name; else p++; if (_dos_lfiles (&inf, w, 0xff) < 0) { free(name); return ZE_MISS; } do { int r; strcpy(p, inf.name); r = procname(name, 0); if (r != ZE_OK) { free(name); return r; } } while (_dos_nfiles(&inf) >= 0); free(name); return ZE_OK; } int procname(n, caseflag) char *n; /* name to process */ int caseflag; /* true to force case-sensitive match */ /* Process a name or sh expression to operate on (or exclude). Return an error code in the ZE_ class. */ { char *a; /* path and name for recursion */ DIR *d; /* directory stream from opendir() */ char *e; /* pointer to name from readd() */ int m; /* matched flag */ char *p; /* path for recursion */ struct stat s; /* result of stat() */ struct zlist far *z; /* steps through zfiles list */ if (strcmp(n, "-") == 0) /* if compressing stdin */ return newname(n, 0, caseflag); else if (LSSTAT(n, &s)) { /* Not a file or directory--search for shell expression in zip file */ p = ex2in(n, 0, (int *)NULL); /* shouldn't affect matching chars */ m = 1; for (z = zfiles; z != NULL; z = z->nxt) { if (MATCH(p, z->iname, caseflag)) { z->mark = pcount ? filter(z->zname, caseflag) : 1; if (verbose) fprintf(mesg, "zip diagnostic: %scluding %s\n", z->mark ? "in" : "ex", z->name); m = 0; } } free((zvoid *)p); return m ? ZE_MISS : ZE_OK; } /* Live name--use if file, recurse if directory */ _toslash(n); if ((s.st_mode & S_IFDIR) == 0) { /* add or remove name of file */ if ((m = newname(n, 0, caseflag)) != ZE_OK) return m; } else { /* Add trailing / to the directory name */ if ((p = malloc(strlen(n)+2)) == NULL) return ZE_MEM; if (strcmp(n, ".") == 0) { *p = '\0'; /* avoid "./" prefix and do not create zip entry */ } else { strcpy(p, n); a = p + strlen(p); if (a[-1] != '/') strcpy(a, "/"); if (dirnames && (m = newname(p, 1, caseflag)) != ZE_OK) { free((zvoid *)p); return m; } } /* recurse into directory */ if (recurse && (d = opendir(n)) != NULL) { while ((e = readd(d)) != NULL) { if (strcmp(e, ".") && strcmp(e, "..")) { if ((a = malloc(strlen(p) + strlen(e) + 1)) == NULL) { closedir(d); free((zvoid *)p); return ZE_MEM; } strcat(strcpy(a, p), e); if ((m = procname(a, caseflag)) != ZE_OK) /* recurse on name */ { if (m == ZE_MISS) zipwarn("name not matched: ", a); else ziperr(m, a); } free((zvoid *)a); } } closedir(d); } free((zvoid *)p); } /* (s.st_mode & S_IFDIR) == 0) */ return ZE_OK; } char *ex2in(x, isdir, pdosflag) char *x; /* external file name */ int isdir; /* input: x is a directory */ int *pdosflag; /* output: force MSDOS file attributes? */ /* Convert the external file name to a zip file name, returning the malloc'ed string or NULL if not enough memory. */ { char *n; /* internal file name (malloc'ed) */ char *t; /* shortened name */ /* Find starting point in name before doing malloc */ t = (x[0] && x[1] == (char)':') ? x + 2 : x; while (*t == (char)'/') t++; /* Make changes, if any, to the copied name (leave original intact) */ _toslash(t); if (!pathput) t = last(t, '/'); /* Malloc space for internal name and copy it */ if ((n = malloc(strlen(t) + 1)) == NULL) return NULL; strcpy(n, t); if (dosify) msname(n); /* Returned malloc'ed name */ if (pdosflag) *pdosflag = dosify; return n; } char *in2ex(n) char *n; /* internal file name */ /* Convert the zip file name to an external file name, returning the malloc'ed string or NULL if not enough memory. */ { char *x; /* external file name */ if ((x = malloc(strlen(n) + 1 + PAD)) == NULL) return NULL; return strcpy(x, n); } void stamp(f, d) char *f; /* name of file to change */ ulg d; /* dos-style time to change it to */ /* Set last updated and accessed time of file f to the DOS time d. */ { ztimbuf u; /* argument for utime() */ /* Convert DOS time to time_t format in u */ u.actime = u.modtime = dos2unixtime(d); /* Set updated and accessed times of f */ utime(f, &u); } ulg filetime(f, a, n, t) char *f; /* name of file to get info on */ ulg *a; /* return value: file attributes */ long *n; /* return value: file size */ iztimes *t; /* return value: access, modific. and creation times */ /* If file *f does not exist, return 0. Else, return the file's last modified date and time as an MSDOS date and time. The date and time is returned in a long with the date most significant to allow unsigned integer comparison of absolute times. Also, if a is not a NULL pointer, store the file attributes there, with the high two bytes being the Unix attributes, and the low byte being a mapping of that to DOS attributes. If n is not NULL, store the file size there. If t is not NULL, the file's access, modification and creation times are stored there as UNIX time_t values. If f is "-", use standard input as the file. If f is a device, return a file size of -1 */ { struct stat s; /* results of stat() */ /* convert FNMAX to malloc - 11/8/04 EG */ char *name; int len = strlen(f); isstdin = !strcmp(f, "-"); if ((name = malloc(len + 1)) == NULL) { ZIPERR(ZE_MEM, "filetime"); } strcpy(name, f); if (name[len - 1] == '/') name[len - 1] = '\0'; /* not all systems allow stat'ing a file with / appended */ if (isstdin) { if (fstat(fileno(stdin), &s) != 0) { free(name); error("fstat(stdin)"); } } else if (LSSTAT(name, &s) != 0) { /* Accept about any file kind including directories * (stored with trailing / with -r option) */ free(name); return 0; } if (a != NULL) { int atr = _dos_chmod(name, -1); if (atr < 0) atr = 0x20; *a = ((ulg)s.st_mode << 16) | (isstdin ? 0L : (ulg)atr); } free(name); if (n != NULL) *n = S_ISVOL(s.st_mode) ? -2L : S_ISREG(s.st_mode) ? s.st_size : -1L; if (t != NULL) { t->atime = s.st_atime; t->mtime = s.st_mtime; t->ctime = s.st_ctime; } return unix2dostime(&s.st_mtime); } int set_extra_field(z, z_utim) struct zlist far *z; iztimes *z_utim; /* create extra field and change z->att if desired */ { #ifdef USE_EF_UT_TIME if ((z->extra = (char *)malloc(EB_HEADSIZE+EB_UT_LEN(1))) == NULL) return ZE_MEM; z->extra[0] = 'U'; z->extra[1] = 'T'; z->extra[2] = EB_UT_LEN(1); /* length of data part of e.f. */ z->extra[3] = 0; z->extra[4] = EB_UT_FL_MTIME; z->extra[5] = (char)(z_utim->mtime); z->extra[6] = (char)(z_utim->mtime >> 8); z->extra[7] = (char)(z_utim->mtime >> 16); z->extra[8] = (char)(z_utim->mtime >> 24); z->cext = z->ext = (EB_HEADSIZE+EB_UT_LEN(1)); z->cextra = z->extra; return ZE_OK; #else /* !USE_EF_UT_TIME */ return (int)(z-z); #endif /* ?USE_EF_UT_TIME */ } int deletedir(d) char *d; /* directory to delete */ /* Delete the directory *d if it is empty, do nothing otherwise. Return the result of rmdir(), delete(), or system(). For VMS, d must be in format [x.y]z.dir;1 (not [x.y.z]). */ { return rmdir(d); } void print_period(void) { fputc('.', stderr); } #endif /* !UTIL */ /******************************/ /* Function version_local() */ /******************************/ void version_local() { static ZCONST char CompiledWith[] = "Compiled with %s%s for %s%s%s%s.\n\n"; #if 0 char buf[40]; #endif printf(CompiledWith, #ifdef __GNUC__ "gcc ", __VERSION__, #else # if 0 "cc ", (sprintf(buf, " version %d", _RELEASE), buf), # else "unknown compiler", "", # endif #endif "Human68k", #ifdef __MC68020__ " (X68030)", #else " (X680x0)", #endif #ifdef __DATE__ " on ", __DATE__ #else "", "" #endif ); } /* end function version_local() */ zip30/human68k/Makefile0100644000076400000060000000422110550050742013057 0ustar edisk# Makefile for Zip, ZipCloak, ZipNote and ZipSplit for human68k # Written by NIIMI Satoshi # # 1999/09/23: Modified by Shimazaki Ryo. ifeq "$(TARGET)" "X68030" COPT = -m68020-40 AOPT = -m68020 -sCPU020 LDFLAGS = -L/usr/local/lib/lib060 endif VPATH = human68k CC = gcc2 CFLAGS = $(COPT) -I. -Wall -O2 -fomit-frame-pointer -fstrength-reduce \ -DASM_CRC -D__DOS_INLINE__ #LDFLAGS = -Wl,-x LIBS = -lhmem -lttyi -lsignal AS = g2as ASFLAGS = $(AOPT) -1 -c4 -y -w2 # object file lists OBJZ = zip.o zipfile.o zipup.o fileio.o util.o globals.o crypt.o ttyio.o \ crc32.o human68k.o crc_68.o OBJI = deflate.o trees.o OBJA = OBJU = zipfile_.o fileio_.o util_.o globals.o human68k_.o OBJN = zipnote.o $(OBJU) OBJC = zipcloak.o $(OBJU) crc32_.o crypt_.o ttyio.o OBJS = zipsplit.o $(OBJU) ZIP_H = zip.h ziperr.h tailor.h human68k/osdep.h all: zips .SUFFIXES: _.o .o .c .c_.o: $(CC) $(CFLAGS) -DUTIL -c $< -o $@ .c.o: $(CC) $(CFLAGS) -c $< -o $@ ZIPS = zip.x zipnote.x zipsplit.x zipcloak.x zips: $(ZIPS) zip.x: $(OBJZ) $(OBJI) $(OBJA) $(CC) $(LDFLAGS) -o $@ $(OBJZ) $(OBJI) $(OBJA) $(LIBS) zipnote.x: $(OBJN) $(CC) $(LDFLAGS) -o $@ $(OBJN) $(LIBS) zipcloak.x: $(OBJC) $(CC) $(LDFLAGS) -o $@ $(OBJC) $(LIBS) zipsplit.x: $(OBJS) $(CC) $(LDFLAGS) -o $@ $(OBJS) $(LIBS) human68k.o: human68k/human68k.c $(CC) $(CFLAGS) -c -o $@ $< human68k_.o: human68k/human68k.c $(CC) $(CFLAGS) -c -o $@ $< -DUTIL #match.o: human68k/match.s # $(AS) $(ASFLAGS) -o $@ $< deflate.o: human68k/deflate.s $(AS) $(ASFLAGS) -o $@ $< crc_68.o: human68k/crc_68.s $(AS) $(ASFLAGS) -o $@ $< clean: rm -f *.o $(ZIPS) zip.bfd: $(ZIPS) rm -f $@ for file in $(ZIPS); do \ bdif -A -R uploaded/$$file $$file $@; \ done # rules for zip, zipnote, zipcloak, zipsplit. $(OBJZ): $(ZIP_H) $(OBJI): $(ZIP_H) $(OBJN): $(ZIP_H) $(OBJS): $(ZIP_H) $(OBJC): $(ZIP_H) zip.o crc32.o crypt.o fileio.o zipfile.o zipup.o: crc32.h zipcloak.o crc32_.o crypt_.o fileio_.o zipfile_.o: crc32.h zip.o zipup.o crypt.o ttyio.o zipcloak.o crypt_.o: crypt.h zip.o zipup.o zipnote.o zipcloak.o zipsplit.o: revision.h zip.o crypt.o ttyio.o zipcloak.o crypt_.o: ttyio.h zipup.o: human68k/zipup.h # EOF zip30/human68k/Makefile.gcc0100644000076400000060000000357310550050742013623 0ustar edisk# Makefile for Zip, ZipCloak, ZipNote and ZipSplit for human68k # Written by NIIMI Satoshi VPATH = human68k CC = gcc AS = as # if you are using mc68030 (or higher) based X68000, # uncomment following defines #CC = gcc -DUNALIGNED_OK #AS = as -s UNALIGNED_OK CFLAGS = -Wall -O -fomit-frame-pointer -fstrength-reduce -DASMV LDFLAGS = -s LIBS = -lsignal -lmb -ldos # object file lists OBJZ = zip.o zipfile.o zipup.o fileio.o util.o crc32.o globals.o \ crypt.o ttyio.o OBJI = deflate.o trees.o OBJA = match.o human68k.o OBJU = zipfile_.o fileio_.o util_.o globals.o human68_.o OBJN = zipnote.o $(OBJU) OBJC = zipcloak.o $(OBJU) crc32_.o crypt_.o ttyio.o OBJS = zipsplit.o $(OBJU) ZIP_H = zip.h ziperr.h tailor.h human68k/osdep.h all: zips .SUFFIXES: _.o .o .c .c_.o: $(CC) $(CFLAGS) -DUTIL -c $< -o $@ .c.o: $(CC) $(CFLAGS) -c $< -o $@ ZIPS = zip.x zipnote.x zipsplit.x zipcloak.x zips: $(ZIPS) zip.x: $(OBJZ) $(OBJI) $(OBJA) $(CC) -o zip.x $(LDFLAGS) $(OBJZ) $(OBJI) $(OBJA) $(LIBS) zipnote.x: $(OBJN) $(CC) -o zipnote.x $(LDFLAGS) $(OBJN) $(LIBS) zipcloak.x: $(OBJC) $(CC) -o zipcloak.x $(LDFLAGS) $(OBJC) $(LIBS) zipsplit.x: $(OBJS) $(CC) -o zipsplit.x $(LDFLAGS) $(OBJS) $(LIBS) match.o: human68k/match.s $(AS) -o $@ $< human68_.o: human68k/human68k.c $(CC) $(CFLAGS) -DUTIL -c -o $@ $< clean: rm -f *.o $(ZIPS) zip.bfd: $(ZIPS) rm -f $@ for file in $(ZIPS); do \ bdif -A -R uploaded/$$file $$file $@; \ done # rules for zip, zipnote, zipcloak, zipsplit. $(OBJZ): $(ZIP_H) $(OBJI): $(ZIP_H) $(OBJN): $(ZIP_H) $(OBJS): $(ZIP_H) $(OBJC): $(ZIP_H) zip.o crc32.o crypt.o fileio.o zipfile.o zipup.o: crc32.h zipcloak.o crc32_.o crypt_.o fileio_.o zipfile_.o: crc32.h zip.o zipup.o crypt.o ttyio.o zipcloak.o crypt_.o: crypt.h zip.o zipup.o zipnote.o zipcloak.o zipsplit.o: revision.h zip.o crypt.o ttyio.o zipcloak.o crypt_.o: ttyio.h zipup.o: human68k/zipup.h zip30/human68k/match.s0100644000076400000060000001103207011111014012661 0ustar edisk*=========================================================================== * Copyright (c) 1990-1999 Info-ZIP. All rights reserved. * * See the accompanying file LICENSE, version 1999-Oct-05 or later * (the contents of which are also included in zip.h) for terms of use. * If, for some reason, both of these files are missing, the Info-ZIP license * also may be found at: ftp://ftp.cdrom.com/pub/infozip/license.html *=========================================================================== * * match.s -- optional optimized asm version of longest match in deflate.c * Written by Jean-loup Gailly * * Adapted for X68000 by NIIMI Satoshi * Adapted for the Amiga by Carsten Steger * using the code in match.S. * The major change in this code consists of removing all unaligned * word accesses, because they cause 68000-based machines to crash. * For maximum speed, UNALIGNED_OK can be defined. * The program will then only run on 68020-based machines, though. Cur_Match reg d0 ; Must be in d0! Best_Len reg d1 Loop_Counter reg d2 Scan_Start reg d3 Scan_End reg d4 Limit reg d5 Chain_Length reg d6 Scan_Test reg d7 Scan reg a0 Match reg a1 Prev_Address reg a2 Scan_Ini reg a3 Match_Ini reg a4 MAX_MATCH equ 258 MIN_MATCH equ 3 WSIZE equ 32768 MAX_DIST equ WSIZE-MAX_MATCH-MIN_MATCH-1 .xref _max_chain_length .xref _prev_length .xref _prev .xref _window .xref _strstart .xref _good_match .xref _match_start .xref _nice_match .xdef _match_init .xdef _longest_match .text .even _match_init: rts _longest_match: move.l 4(sp),Cur_Match .ifdef UNALIGNED_OK movem.l d2-d6/a2-a4,-(sp) .else movem.l d2-d7/a2-a4,-(sp) .endif move.l _max_chain_length,Chain_Length move.l _prev_length,Best_Len lea _prev,Prev_Address lea _window+MIN_MATCH,Match_Ini move.l _strstart,Limit move.l Match_Ini,Scan_Ini add.l Limit,Scan_Ini subi.w #MAX_DIST,Limit bhi.b limit_ok moveq #0,Limit limit_ok: cmp.l _good_match,Best_Len bcs.b length_ok lsr.l #2,Chain_Length length_ok: subq.l #1,Chain_Length .ifdef UNALIGNED_OK move.w -MIN_MATCH(Scan_Ini),Scan_Start move.w -MIN_MATCH-1(Scan_Ini,Best_Len.w),Scan_End .else move.b -MIN_MATCH(Scan_Ini),Scan_Start lsl.w #8,Scan_Start move.b -MIN_MATCH+1(Scan_Ini),Scan_Start move.b -MIN_MATCH-1(Scan_Ini,Best_Len.w),Scan_End lsl.w #8,Scan_End move.b -MIN_MATCH(Scan_Ini,Best_Len.w),Scan_End .endif bra.b do_scan long_loop: .ifdef UNALIGNED_OK move.w -MIN_MATCH-1(Scan_Ini,Best_Len.w),Scan_End .else move.b -MIN_MATCH-1(Scan_Ini,Best_Len.w),Scan_End lsl.w #8,Scan_End move.b -MIN_MATCH(Scan_Ini,Best_Len.w),Scan_End .endif short_loop: lsl.w #1,Cur_Match move.w 0(Prev_Address,Cur_Match.l),Cur_Match cmp.w Limit,Cur_Match dbls Chain_Length,do_scan bra.b return do_scan: move.l Match_Ini,Match add.l Cur_Match,Match .ifdef UNALIGNED_OK cmp.w -MIN_MATCH-1(Match,Best_Len.w),Scan_End bne.b short_loop cmp.w -MIN_MATCH(Match),Scan_Start bne.b short_loop .else move.b -MIN_MATCH-1(Match,Best_Len.w),Scan_Test lsl.w #8,Scan_Test move.b -MIN_MATCH(Match,Best_Len.w),Scan_Test cmp.w Scan_Test,Scan_End bne.b short_loop move.b -MIN_MATCH(Match),Scan_Test lsl.w #8,Scan_Test move.b -MIN_MATCH+1(Match),Scan_Test cmp.w Scan_Test,Scan_Start bne.b short_loop .endif move.w #(MAX_MATCH-MIN_MATCH),Loop_Counter move.l Scan_Ini,Scan scan_loop: cmpm.b (Match)+,(Scan)+ dbne Loop_Counter,scan_loop sub.l Scan_Ini,Scan addq.l #(MIN_MATCH-1),Scan cmp.l Best_Len,Scan bls.b short_loop move.l Scan,Best_Len move.l Cur_Match,_match_start cmp.l _nice_match,Best_Len bcs.b long_loop return: move.l Best_Len,d0 .ifdef UNALIGNED_OK movem.l (sp)+,d2-d6/a2-a4 .else movem.l (sp)+,d2-d7/a2-a4 .endif rts end zip30/human68k/osdep.h0100644000076400000060000000146607011111022012675 0ustar edisk/* Copyright (c) 1990-1999 Info-ZIP. All rights reserved. See the accompanying file LICENSE, version 1999-Oct-05 or later (the contents of which are also included in zip.h) for terms of use. If, for some reason, both of these files are missing, the Info-ZIP license also may be found at: ftp://ftp.cdrom.com/pub/infozip/license.html */ #include #include #include #ifdef ZCRYPT_INTERNAL # include /* getpid() declaration for srand seed */ #endif #define USE_CASE_MAP #define ROUNDED_TIME(time) (((time) + 1) & (~1)) #define PROCNAME(n) (action == ADD || action == UPDATE ? wild(n) : \ procname(n, 1)) #ifdef HAVE_MBCTYPE_H # include #else # define ismbblead(c) (0x80 <= (c) && ((c) < 0xa0 || 0xe0 <= (c))) #endif zip30/human68k/zipup.h0100644000076400000060000000106207011111030012721 0ustar edisk/* Copyright (c) 1990-1999 Info-ZIP. All rights reserved. See the accompanying file LICENSE, version 1999-Oct-05 or later (the contents of which are also included in zip.h) for terms of use. If, for some reason, both of these files are missing, the Info-ZIP license also may be found at: ftp://ftp.cdrom.com/pub/infozip/license.html */ #define fhow (O_RDONLY|O_BINARY) #define fbad (-1) typedef int ftype; #define zopen(n,p) open(n,p) #define zread(f,b,n) read(f,b,n) #define zclose(f) close(f) #define zerr(f) (k == (extent)(-1L)) #define zstdin 0 zip30/INSTALL0100644000076400000060000003652411031716504011022 0ustar ediskHOW TO INSTALL ZIP Zip is distributed as C source code that can be compiled on a wide range of systems: Unix, VMS, MSDOS, OS/2, NT, Amiga, Atari, BeOS, VM/CMS, ... You will need Unzip 5.0p1 or later (under any system) or PKUNZIP 2.04g or later (under MSDOS) to unpack the distribution file, in this case zip30.zip. But since you read this, you have unpacked it already, or you cheated and got a tar.Z file... Note: Zip 3.0 distribution kits (unlike previously distributed Zip 2.x kits) are created with a top-level directory ("zip30") in the archive, making the creating of the zipsrc directory optional. Installation on Unix (see below for installation on other systems) Let's assume that you start from scratch and have not yet unpacked the sources. First step, then, is to unpack Zip. The following assumes that you have zip30.zip in the current directory. For example, to extract to a new zipsrc directory (assuming zip30.zip is in the current directory): mkdir zipsrc cd zipsrc cp ../zip30.zip . unzip zip30.zip cd zip30 To extract in an existing directory, such as /usr/local/src/zip: cd /usr/local/src/zip (copy zip30.zip here) unzip zip30.zip cd zip30 The first extracts all source files and documentation to the directory "zipsrc/zip30". The second places the zip30 directory in the "/usr/local/src/zip" directory. Both then cd in to the zip30 directory where Zip will be built. Note: This release now includes the standard encryption code previously in the separate package zcrypt29.zip, but you still can decide whether to activate the crypt code or not. Crypt is enabled by default, but you may disable it by specifying the option -DNO_CRYPT in the LOCAL_ZIP environment variable (or by adding this option to the compilation options in the appropiate makefile). See README.CR for more on crypt. You then do: make -f unix/Makefile system where "system" is one of: generic, generic_gcc, att6300, coherent, cray_v3, minix, sco_x286, xenix, zilog. For Unix systems where "cc" is the preferred C compiler command, try make -f unix/Makefile generic first. If "gcc" is preferred, specify "generic_gcc" instead of "generic". This should work on most systems and automatically selects compilation options based on a set of tests (in unix/configure), including detection of large file support sufficient to enable Zip64 large archive features. If "generic" (or "generic_gcc" if that is used) fail, then one of the special targets given above may work. Among other special systems are Cray Unicos, Zilog Zeus and MINIX. The optimization settings for many systems should be close, but if you see optimization for your system is not ideal, send in the changes so we can improve it. By default, Zip uses the "deflate" compression method. To add the additional optional "bzip2" compression method, see the file bzip2/install.txt. Note that bzip2 support is provided by compiling or linking in the bzip2 library. See the bzip2 site (http://www.bzip.org/) for more on bzip2. If you get error messages such as "constant expected" in deflate.c, add -DDYN_ALLOC to CFLAGS in your makefile entry. If you have lots of memory, try compiling with -DBIG_MEM. If your system supports mmap(), try compiling with -DMMAP. This generally gives faster compression but uses more memory. See the unix/Makefile entry mmap_gcc for an example. If none of these compiles, links, and functions properly on your Unix system, then your system apparently has specific requirements we did not account for. See the file README for how to get help. If the appropriate system was selected, then the executables zip, zipnote, zipcloak, and zipsplit will be created. You can copy them to an appropriate directory in the search path using: make -f unix/Makefile install The defaults are /usr/local/bin for the executables and /usr/local/man/man1 for the manual pages. Change the macros BINDIR and MANDIR in makefile to change these if needed. If necessary, add the directory with the Zip executables to your shell's PATH (or "path") variable. (C-shell users may need to use the "rehash" command so csh can find the new command in the path.) You should now be ready to use Zip. You can get rid of the now unnecessary source and object files with: cd .. rm -r zip30 This will remove the directory zip30 and its contents created by unzip. You should keep the zip30.zip file around though, in case you need to build it again or want to give it to a colleague. You can add the following lines to the file /etc/magic for usage by the 'file' command: 0 string PK Zip archive >4 byte 011 (at least v0.9 to extract) >4 byte 012 (at least v1.0 to extract) >4 byte 013 (at least v1.1 to extract) >4 byte 024 (at least v2.0 to extract) >4 byte 025 (at least v2.1 to extract) Installation on other systems The steps for installation under VMS, MSDOS, OS/2, NT, Amiga and Atari are similar to the above: first unzip the distribution files into their own directory. The system-dependent files are stored in special subdirectories. For all the non-Unix ports which support the creation of "UT" extra fields (these ports contain USE_EF_UT_TIME in the list of optional features displayed with "zip -v"), the timezone environment variable TZ should be set according to the local timezone in order for the -f, -u, -o, and similar options to work correctly. This is not needed for the WIN32 and WinDLL ports, since they get the timezone information from the OS by other means. MSDOS: Do one of: make msdos\makefile.msc (Microsoft C 5.1) nmake -f msdos\makefile.msc (Microsoft C 6.0 and newer) make -fmsdos\makefile.bor -DCC_REV=1 (Borland Turbo C++ 1.0) make -fmsdos\makefile.bor (Borland C++ 2.0 and newer) make -fmsdos\makefile.tc (Borland Turbo C 2.0x) make -f msdos/makefile.dj1 (DJGPP v1.12m4) make -f msdos/makefile.dj2 (DJGPP v2.01 and newer) make -f msdos/makefile.emx (gcc/emx 0.9b and newer) make -f os2/makefile.os2 gccdos (gcc/emx 0.9b and newer) wmake -f msdos\makefile.wat (Watcom C 11.x 16-bit) wmake -f msdos\makefile.wat PM=1 (Watcom C 11.x 32-bit, PMODE/W) for Microsoft, Borland C++ and Turbo C, Watcom C/C++ and the various free GNU C implementations, respectively. More detailed instructions can be found in the respective makefiles. WIN32 (Windows NT/2K/XP/2K3 and Windows 95/98/ME): Supported compilers are Microsoft Visual C++, Borland C++, Watcom C/C++, and miscellaneous free GNU C implementations (gcc/mingw, CygWin, ...). The makefiles supplied in the win32/ subdirectory contain further information. Windows DLL (WIN32): Supported environments are Visual C++ (32-bit only, 5.x and newer). For instructions how to build the DLLs and where find the makefiles, look into windll/contents. OS/2: Type {make} -f os2/makefile.os2 to get a list of supported targets/compiling environments. (replace "{make}" with the name of your OS/2 make utility.) To initiate the actual compiling process, you have to specify a system target: {make} -f os2/makefile.os2 {system} An example: type nmake -f os2/makefile.os2 msc for Microsoft C 6.00. VMS (OpenVMS): The most complete information on building and installing Zip on VMS is in [.vms]install_vms.txt. Optimists in a hurry may wish to try commands like these: @ [.VMS]BUILD_ZIP.COM or: MMS /DESCRIP = [.VMS]DESCRIP.MMS CLEAN ! Or MMK ... MMS /DESCRIP = [.VMS]DESCRIP.MMS ! Or MMK ... When the executables have been created (or located if already installed), most users define foreign command symbols for the Zip executables, like this: ZIP :== $ dev:[dir]ZIP.EXE ! UNIX-like command line. or: ZIP :== $ dev:[dir]ZIP_CLI.EXE ! VMS-like command line. Such symbol definitions are often added to a user's SYS$LOGIN:LOGIN.COM procedure, or to a common, site-specific procedure, like SYS$MANAGER:SYLOGIN.COM. Additional installation options are described in install_vms.txt. The builders create help text files, ZIP.HLP and ZIP_CLI.HLP. Also see install_vms.txt for how to create the help libraries. Mac OS: Mac OS X is part of the Unix port, so use the Unix installation above. Mac OS before Mac OS X use the Mac OS port, though little testing has been done for that port recently. See macos/README.TXT for more on this port. Compiler Flags Zip should compile fine out of the box for your port. In particular, for Unix the command make -f unix/Makefile generic should automatically detect the features available on your system and set the flags appropriately. In some cases, however, you may need to set one or more compiler flags yourself to get Zip to compile or to add features you want or remove features that cause trouble for your port. Below are the more common compiler macros you can set. LARGE_FILE_SUPPORT Tell Zip that the OS supports large files (generally files larger than 4 GB). Zip will try to compile in the large file calls (typically 64-bit) for the OS instead of using the standard (typically 32-bit) file calls. On Unix Zip tries to switch over to the 64-bit file environment. If setting this flag causes errors or Zip still can't handle large files on that port, then probably either Zip doesn't have the code to support large files on your OS (write a patch and send it in to us) or your OS doesn't support large files. Note that the flag ZIP64_SUPPORT must also be set to create archives with large files. This flag should be set automatically on Unix, Win32, and some other ports. Setting NO_LARGE_FILE_SUPPORT turns this flag off. ZIP64_SUPPORT Enable the Zip64 code in Zip that supports the Zip64 extensions noted in the PKWare AppNote. These extensions allow storing files larger than 4 GB in archives and the creating of archives larger than 4 GB. They also allow storing more than 64K files in an archive. Currently Zip does not handle archives of PKZip version 4.5 or later unless this flag is set. To enable large file support in Zip, you generally need to set both LARGE_FILE_SUPPORT (to read and write large files) and ZIP64_SUPPORT (to store them in and read them from archives). Files larger than 4 GB may be invisible to Zip (directory scans don't see them) if LARGE_FILE_SUPPORT is not enabled. Keeping LARGE_FILE_SUPPORT and ZIP64_SUPPORT separate allows easier debugging of these features. When testing large file support on an OS, first set just LARGE_FILE_SUPPORT to test the file calls (all should compile and work as before with small files), then turn on ZIP64_SUPPORT to let Zip recognize and handle large files. This flag should be set automatically on most ports if LARGE_FILE_SUPPORT is set. Setting NO_ZIP64_SUPPORT turns this flag off. UNICODE_SUPPORT Enable storing and using UTF-8 paths. These paths are stored in a backward-compatible way so that archives with UTF-8 paths still work on zips and unzips that don't support Unicode. This support follows the recent additions to the PKWare AppNote for Unicode support, except that Unicode comments on systems where UTF-8 is not the current character set is not implemented in this release. On some ports UNICODE_SUPPORT is set automatically if wide characters are supported. Setting NO_UNICODE_SUPPORT turns off this flag. USE_EF_UT_TIME Enables storing UT time in an extra field. This becomes useful for ports that normally store file times as local time, resulting in problems when files are moved across time zones and when there are daylight savings time changes. Zip and UnZip will automatically correct for time zone changes when UT time is stored. This is usually set by default. Use NO_EF_UT_TIME to turn this off. NTSD_EAS (Win32 only) Enable storing Windows NT file security descriptors. This allows restoring the descriptors (file ACL's, etc.). This is on by default for Win32. Use NO_NTSD_EAS to turn this off. BZIP2_SUPPORT Enable compressing zip entries using the bzip2 library. You must get the bzip2 library from somewhere else as we only provide a way to compile or link the library in and compress files using bzip2. Enables a new compression method, bzip2, that can be used instead of the default Zip compression method deflate. This flag is set on Unix, including Mac OS X, when compiling using generic if the bzip2 library is found. Set on Win32 if the bzip2 projects are used. See the VMS documentation for when VMS sets this flag. Setting NO_BZIP2_SUPPORT turns this off. See bzip2/install.txt for more on installing bzip2 support. WIN32_OEM (Win32 only) Enable saving paths on Win32 in the OEM character set. Zip has stored paths using the standard ANSI local character set, but other zips have used the OEM character set on MSDOS and Win32. This flag should make Zip more compatible with other DOS and Win32 zips and unzips. It also enables the translation of OEM paths in DOS archives to ANSI and should eliminate some problems with funny characters showing up in path names. If Unicode is enabled and used, Unicode paths generally override local paths using OEM character sets. This flag is on by default on most Win32 ports. Some ports apparently have problems with OEM conversions. If your port or compiler does funny things with file names, you may want to turn this off. Defining NO_WIN32_OEM turns this flag off. NO_STREAMING_STORE Because storing zip archives inside a zip entry adds "false" signatures and this causes problems when using data descriptors if the archive needs fixing, this option is provided to force deflating when streaming. This version of Zip includes an advanced algorithm for correctly finding these signatures, but if an archive is "broke", there is no telling what's where. This is only a problem if an archive becomes broke for some reason, but to be safe define this. ALLOW_REGEX For MSDOS and Windows, now "[list]" wildcard matching (where any character between [ and ] can be used to match the character at that position) is turned off unless the new -RE option is used. Defining this flag forces "[list]" matching to be always on as in previous releases. For command help on any of the zip* utilities, simply enter the name with no arguments. zip30/LICENSE0100644000076400000060000000652410572405422010776 0ustar ediskThis is version 2007-Mar-4 of the Info-ZIP license. The definitive version of this document should be available at ftp://ftp.info-zip.org/pub/infozip/license.html indefinitely and a copy at http://www.info-zip.org/pub/infozip/license.html. Copyright (c) 1990-2007 Info-ZIP. All rights reserved. For the purposes of this copyright and license, "Info-ZIP" is defined as the following set of individuals: Mark Adler, John Bush, Karl Davis, Harald Denker, Jean-Michel Dubois, Jean-loup Gailly, Hunter Goatley, Ed Gordon, Ian Gorman, Chris Herborth, Dirk Haase, Greg Hartwig, Robert Heath, Jonathan Hudson, Paul Kienitz, David Kirschbaum, Johnny Lee, Onno van der Linden, Igor Mandrichenko, Steve P. Miller, Sergio Monesi, Keith Owens, George Petrov, Greg Roelofs, Kai Uwe Rommel, Steve Salisbury, Dave Smith, Steven M. Schweda, Christian Spieler, Cosmin Truta, Antoine Verheijen, Paul von Behren, Rich Wales, Mike White. This software is provided "as is," without warranty of any kind, express or implied. In no event shall Info-ZIP or its contributors be held liable for any direct, indirect, incidental, special or consequential damages arising out of the use of or inability to use this software. Permission is granted to anyone to use this software for any purpose, including commercial applications, and to alter it and redistribute it freely, subject to the above disclaimer and the following restrictions: 1. Redistributions of source code (in whole or in part) must retain the above copyright notice, definition, disclaimer, and this list of conditions. 2. Redistributions in binary form (compiled executables and libraries) must reproduce the above copyright notice, definition, disclaimer, and this list of conditions in documentation and/or other materials provided with the distribution. The sole exception to this condition is redistribution of a standard UnZipSFX binary (including SFXWiz) as part of a self-extracting archive; that is permitted without inclusion of this license, as long as the normal SFX banner has not been removed from the binary or disabled. 3. Altered versions--including, but not limited to, ports to new operating systems, existing ports with new graphical interfaces, versions with modified or added functionality, and dynamic, shared, or static library versions not from Info-ZIP--must be plainly marked as such and must not be misrepresented as being the original source or, if binaries, compiled from the original source. Such altered versions also must not be misrepresented as being Info-ZIP releases--including, but not limited to, labeling of the altered versions with the names "Info-ZIP" (or any variation thereof, including, but not limited to, different capitalizations), "Pocket UnZip," "WiZ" or "MacZip" without the explicit permission of Info-ZIP. Such altered versions are further prohibited from misrepresentative use of the Zip-Bugs or Info-ZIP e-mail addresses or the Info-ZIP URL(s), such as to imply Info-ZIP will provide support for the altered versions. 4. Info-ZIP retains the right to use the names "Info-ZIP," "Zip," "UnZip," "UnZipSFX," "WiZ," "Pocket UnZip," "Pocket Zip," and "MacZip" for its own source and binary releases. zip30/macos/0040755000076400000060000000000011033727770011075 5ustar ediskzip30/macos/Contents0100644000076400000060000000514606677115714012627 0ustar ediskContents of the "macos" sub-archive for Zip 2.3 and later: MacOS: Contents this file readme.1st Instruction to unpack mac specific files README.TXT Dirk Haase's infos on updated MacIntosh ports of Zip/UnZip HISTORY.TXT Dirk Haase's MacOS specific ChangeLog zipup.h MacOS osdep.h MacOS specific configuration and declarations ZipLib.h used to build a static library, global to the project ZipSx.h used to build a standalone App with MW Sioux, global to the project ZpPrj.hqx Metrowerks CodeWarrior pro3 project file (BinHex) source/ subdirectory containing all sources: a) Zip specific code extrafld.c contains all code related to the mac extra field extrafld.h macglob.h macopen.c replaces fopen() and open() macopen.h macos.c Macintosh-specific routines for use with Info-ZIP's Zip MatWild.c Pattern matching function recurse.c Functions to go through the directories recurse.h unixlike.c This file provides a unix like file-stat routine unixlike.h VolWarn.h contains the warning message, about volumes with the same name zip_rc.hqx resource file for Macintosh unzip (BinHex) b) general utilities shared between Zip and UnZip charmap.h character mapping tables ISO 8859-1 <--> MacRoman helpers.c some helper functions helpers.h macstuff.c Mac filemanager routines copied from MoreFiles 1.4.8 macstuff.h mactime.c replacement for broken Metrowerks RTL time functions pathname.c functions for handling MacOS HFS path- /filenames pathname.h The new ZpPrj.hqx project file should be "un-BinHex'ed" into ZpPrj, which builds the following targets: - Zip Lib (68K) -> static library 68k - Zip Lib (PPC) -> static library PPC - Zip Sioux (68K) -> MW Sioux standalone App, good for debugging - Zip Sioux (PPC) -> MW Sioux standalone App, good for debugging The resource files and the compiler project files are in BinHex form because they contain Macintosh resource forks. The resource info cannot be maintained when handling (e.g. repacking) the master source collection on non-Macintosh systems. The BinHex form is the traditional way for transferring such files via non-Macintosh systems. It's also the safest since it uses only printable characters. The ".hqx" files must be converted with StuffitExpander or BinHex 4.0 (or equivalent) on a Macintosh system before using them. zip30/macos/HISTORY.TXT0100644000076400000060000004172007246602562012642 0ustar ediskA free Macintosh Port of Info-ZIP's Zip and UnZip By Dirk Haase, d_haase@sitec.net Home page: www.sitec.net/maczip Mirror page: www.haase-online.de/dirk/maczip ================================ Release MacZip ver1.07 beta 1 22. Februray 2001 ----------------- 1) CHG: {unzip} switch to latest final release unzip 5.42 2) CHG: {zip} switch to latest beta release zip 2.40a Release MacZip ver1.06 final 22. Februray 2001 ----------------- 1) CHG: {unzip} switch to latest final release unzip 5.42 2) CHG: switch to latest release of Apples Universal Interfaces 3.3.2 3) CHG: switch to latest release of Morefiles 1.5 Release MacZip ver1.06 beta 2 02. August 2000 --------------- 1) CHG: {unzip} switch to latest beta release unzip 5.42d Release MacZip ver1.06 beta 1 27. July 2000 ------------- 1) CHG: {zip} switch to latest beta release unzip 2.30 2) CHG: {unzip} switch to latest beta release unzip 5.42c Release MacZip ver1.05 final 27. July 2000 ------------- 1) CHG: {unzip} switch to latest final release unzip 5.41 2) FIX: {unzip} Fixed "unique unzip folder" foldername handling 3) FIX: {unzip} added prototype crc32() in macbin3.c 4) CHG: {unzip/zip} added exported Codewarrior project-file in xml-format 5) ADD: {unzip} added extra-field recognition for Mac SmartZip in zipinfo.c and unzpriv.h. Release MacZip ver1.04 final 25. January 2000 ---------------- Final release of MacZip. All parts now in final release state !! 1) Switch to MW Codewarrior pro 5.3 2) CHG: {zip} switch (back) to latest final release unzip 2.30 3) CHG: {unzip} switch (back) to latest final release unzip 5.40 Release MacZip ver1.04 beta 3 05. October 1999 ---------------- 1) CHG: {zip} switch to latest source level unzip 2.30o beta release 2) CHG: {unzip} switch to latest source level unzip 5.41c beta release 3) ADD: {console} added menu to print the license Release MacZip ver1.04 beta 2 02. June 1999 -------------- 1) FIX: {unzip} added one more criteria to make the recognition of macbinary more save. 2) FIX: {unzip} sometimes, archive entries without any extra field caused problems; the default setting of the extra field was not set back to 'unknown' properly. 3) FIX: {zip} Archive filename with invalid characters like '/' gets renamed. However, I do not check the complete path - needs some more work here. 4) FIX: {zip} Filename match was case sensitive. 6) CHG: {zip} switch to latest source level unzip 2.30m beta release 7) CHG: {unzip} switch to latest source level unzip 5.41b beta release 8) FIX: {zip/unzip 68k only) I have found a wrong compiler setting for the 68k version. Because of this wrong setting the 68k version crashed. Release MacZip ver1.04 beta 1 30. March 1999 -------------- 1) CHG: {unzip) switch to latest source level unzip 5.41a beta release 2) ADD: {all} Added message logging support for Syslogd by Brian Bergstrand. Syslogd can be found at http://www.classicalguitar.net/brian/apps/syslogd/ This feature is 'under construction'. 3) FIX: {all} many small fixes and code cleanups Release MacZip ver1.03 27. March 1999 -------------- 1) CHG: {console} Like Stuffit Expander MacZip quits automatically when used with drag'n drop or as Helper App (Web-Browser). 2) CHG: {console} Since Macintosh users are used to be guided by their software in order not to do something stupid, I added a check to post an extra warning if the options -m and data fork only are both checked. This behavior can be disabled: See Applescript example and "maczip.env". 3) CHG: {zip} switch from immediate deletion to moving to the trash. Immediate deletion is now an option in "maczip.env". 4) CHG: {zip} enhanced progress display. 5) CHG: {zip) switch to latest source level zip 2.3l beta release 6) CHG: {unzip} The zip archive contains file names greater than 31 characters. When MacZip tries to unzip the file, the FSpCreate command fails because the filename length is to long. MacZip correct this problem by trying to truncate the file names to the 31 character limit. 7) FIX: {zip/console} A couple of minor fixes 8) CHG: {zip} Switched file-globbing to the Info-ZIP version. Release MacZip ver1.02 14. February 1999 ----------------- 1) CHG: {zip} Changed the rule of file inclusion if switch '-X' is set. Following conditions are checked: a) if length of resource-fork is equal zero *and* the length of data-fork is equal zero include the file. b) if length of resource-fork greater zero *and* the length of data-fork is equal zero don't include the file. c) if length of data-fork greater zero include the file. 2) CHG: {Console} Some users are very confused by the buttons "START PATH" and "ZIP ARCHIVE". Somehow, it wasn't clear what the intended meaning was. I changed the buttons to more clear labels on them like: "file or folder to compress" and "location of compressed file" 3) CHG: {Console} I changed the menu structure to be more intuitive. 4) FIX: {Console} Found a nasty bug which sometimes caused crashes when the Zip / Unzip Dialogbox was used. 5) CHG: {Console} Handling of file dialog is now a bit more restricted: e.g: it's not possible to select a file if you have to select a folder. Release MacZip ver1.01 30. January 1999 ---------------------- 1) CHG: {console} The use of the "Current App" mechanism was clumsy and forces the user into the Zip or Unzip modes. This kind of modality is not so good for the command line. It's now neccessary to enter zip or unzip to choose the action. 2) FIX: {console} When Applescript sends quit to MacZip the script that is running shows a spinning cursor and MacZip does not quit. 3) FIX: {console} MacZip gots accidentally the wrong creator code (from BBedit) Final Release MacZip ver1.0 --------------------------- Released 21. January 1999 9. Beta release 06.December.1998 --------------------------------- 1) CHG: {console} The checkbox of Filedialog (for extract path and file path) "Show all files" is now selected by default. 2) CHG: {unzip/standalone} changed prototypes of mac[f]printf() to return an int number (better ANSI conformance); 3) FIX: {unzip} repaired "stdout/stderr" mode of macwrite(). So func MacMessagePrnt() is now obsolete and removed. 4) ADD: {zip/unzip} Compressed Mac3 extra-fields are now supported (Thanks to Christian Spieler) 5) ADD: {unzip} Extraction of ZipIt archive are now supported. This support is not complete: Filenames are correct but folder names are only restored with the public directory names. 6) ADD: {zip/unzip} Improved documentation. 7) FIX: {unzip} Function isZipfile() is completely rewritten. 8) CHG: {zip/unzip) switch to latest source level zip 2.3i beta and unzip 5.4 final release 9) ADD: Applescript event "do_cmd". Unless there are big bugs found, this release will be the last beta release. The final release will come out in January 1999. 8. Beta release 20.November.1998 --------------------------------- 1) CHG: {zip/unzip) switch to latest source level zip 2.3h beta and unzip 5.4 final release 2) ADD: {zip} Zip finds "namelocked" files also, if switch "-S" is set. 3) FIX: {unzip} Function isZipfile() fails if the zip archive has a comment. 4) CHG: {zip} added some small speed improvements to pattern matching and isZipFile() function. 5) FIX: {unzip} Display of comments is fixed. UzpMessagePrnt() is replaced by MacMessagePrnt(). I do not care about ansi-bombs. I'm not sure, so this fix may be changed later. 6) RMV: {unzip} Buildin More capability is removed since it's already built into the GUI-App. 7. Beta release 09.November.1998 --------------------------------- 1) CHG: {all} switched to Metrowerks Codewarrior Pro 4 2) FIX: {unzip} Display of comments stored in the zip-file is now fixed 3) FIX: {zip} Fixed display of the zip help-screen. 4) CHG: {zip/unzip} Changed special dir 'Re$0urce.Fk' to 'XtraStuf.mac' (see entry at 13.June.1998 item 3). I found it more descriptive for users outside the mac-community. 5) CHG: {all} switched to MoreFiles 1.4.9. 6) CHG: {console} changed behaivor of the file open dialog: The select button is now always enabled. 7) ADD: {all} Environment variables are now supported. Basically, it is possible to add timezone (= TZ environment variable) support here, but it's not yet implemented. See "MacZip.Env" for further info. 8) RMV: {console} Targets "zip only" and "unzip only" are removed. 6. Beta release 09.September.1998 --------------------------------- 1) CHG: {Zip/Unzip} Metrowerks Standardlibrary time funktions are rather broken and incomplete so I was forced to rewrite the funktions: mktime(), localtime(), gmtime() and time(). 2) ADD: {Console} Added Pause Funktion for screen output. The Pause-Function is selfadjusting: Count of lines is depending on the window size. 3) CHG: Extra-Field layout is changed: All datas are now in little-endian format (see appnote) 4) ADD: {Console} Added an option to test the archive automatically after zipping. This option is only via Zip-Dialogbox available because it needs the unzip-module also. 5) CHG: {Zip} code is now up to date with the latest beta 2.3f. 6) ADD: {Console} Added (drag'n) drop support. Drop on the MacZip icon. The following situations are supported: 1. drop of one or more zipfiles (action = unzip) each archive will be extracted in a separate folder 2. drop of a folder (action = zip -r ) The complete folder (inclusive sub-folders) will be zipped Not (yet) supported is currently: dropping more than one file to compress. Workaround: Put all your files in one folder and drop that folder on MacZip. MacZip recognize zip-archives automatically. 5. Beta release 21.Aug.1998 ---------------------------- 1) ADD: {Console} Userinterface has now a Statusbar to show the Progress. 2) ADD: {Console} It's now possible to stop the run of Zip/Unzip with the well known shortcut [Command] + [.] 3) CHG: {Console} Improved user-entry routine. 4) ADD: {Zip/Unzip} Crypt-code added. It's now possible to encrypt/decrypt archives. 5) RMV: {Unzip} Removed the warning of PKZip/Mac archive. Unzip gets confused with the extra field of PKZip/Mac. So I assume the extra field isn't compatible with Info-ZIP's definition. 6) CHG: switched to Metrowerks Codewarrior Pro 3 this includes: - new Universal Interfaces 3.1 Headers - improved codegeneration 7) CHG: {Zip} code is now up to date with the latest beta 2.3e. 8) CHG: {Unzip} changed function names wprintf, wgets .. to macprintf, macgets .. to avoid naming conflict standart library. 9) ADD: {Zip/Unzip} FXinfo, Mac-Pathname, file-dates and Finder-Comments are now stored in the extra-field. Extra-field layout is changed accordingly. Unzip uses now the filename stored in the extra-field when unzipping. 10) CHG: {Unzip} code is now up to date with the latest beta 5.33g. 11) CHG: {Unzip} code is (again) up to date with the latest beta 5.33h. 12) ADD: {Unzip} following switches were added: -J [MacOS only] ignore mac extra info. All macintosh info are not restored. Datafork and resource-fork are restored separatly. -i [MacOS only] ignore filenames stored in mac extra field. Use the most compatible filename stored in the public field. -E [MacOS only] show mac extra field during restoring 13) ADD: {Zip/Unzip} Charset MacRoman to ISO8859 Latin and vice versa 14) RMV: {Zip} -N option removed. This MacZip crashes using this option. I will fix it later. I think I'm very close for a final release of "MacZip 1.0" :-) 4. Beta release 27.June.1998 ---------------------------- 26.June.1998 ------------ 1) FIX: {Zip} extra field size value was wrong. 25.June.1998 ------------ 1) CHG: {Zip} code is now up to date with the latest beta 2.3d. So both modules, zip & unzip, uses now latest beta. 2) ADD: {Zip} added a UT extra-field for better compatibility. 3) CHG: {Unzip} changed the code to find the mac extra-field. Unzip has to look for a mac extra-field because mac-archives has now two extra-fields (UT + M3). 4) CHG: {Unzip} changed the method to move extra-field data to the internal extra-structure. Old method was just BlockMove of the ef_structptr to ef_memptr. This method was dangerous because not all members of the structure seamless aligned. There are may be some fill bytes in the structure depending on the compiler setting. 5) ADD: {Unzip} added a warning if unzipping a ZipIt/PKZip archive. ZipIt/PKZip archives are usually additionally coded somehow. InfoZip's Unzip will *not* decode the files. So extracted files are may be not decoded. (see also 6. and 7.) 6) ADD: ZipIt (the Shareware Tool) has now a new extra-field signature: 0x2705. Found in "ZipIt 1.3.8". I added a new macro: EF_ZIPIT2 7) ADD: Added PKWare's extra-field signature: 0xCF77. Found in "PKZIP v2.03". I added a new macro: EF_PKMAC 8) ADD: {console} It's now possible to save all screen outputs to the disk. 9) RMV: {console} this is the first beta without expire-date. 16.June.1998 ------------ 1) FIX: {Unzip/console} Extract path now defaults to current-dir if no path is given. 2> CHG: {Unzip} creates now a extract-folder by default. This behavior differs to the commandline tool of Unzip on other platforms. However, for a mac-user is this behavior more convenient. 3. Beta release 15.June.1998 ---------------------------- 15.June.1998 ------------ 1) CHG: {unzip/zip} I changed the layout of the extra field to support more data. 14.June.1998 ------------ 1) FIX: {Unzip} adjusted time_t value with an correct offset value. 2) FIX: {Unzip} removed all unused code based on unfinished ideas by former porter(s). 3) CHG: use of shared code izshr 032. 13.June.1998 ------------ 1) FIX: {Unzip} Filenames are only converted when needed. When zipping with the switch 'datafork only' the filenames are shorted which was wrong. 2) CHG: {Unzip} code is now up to date with the latest beta 5.33f. 3) CHG: {Zip} Changed the naming rule of filenames from old Johnny Lee's to my implementation. Johnny Lee's idea is based on change of the filenames which cases several problems when unziping on a non mac plattform. My idea is to add a special directory: 'Re$0urce.Fk'. For the future: Zip will create archives according the new nameing rule. However unzip will be compatible with old nameing rule. See also 4. 4} ADD: {Unzip} Added a new nameing rule for resource forks filename. Resource forks are now stored in a special directory: 'Re$0urce.Fk'. This naming rule make it easier to for other platforms to use mac zip-files. 11.June.1998 ------------ 1) FIX: {Zip} Internal file attribute is set to BINARY by default when zipping resource forks otherwise Unzip will create sometimes wrong resource-forks. 2) CHG: {Unzip} code is now up to date with the latest beta 5.33e. 2. Beta release 10.June.1998 -------------------------- 1) FIX: {Unzip} Long pathname fix solved. Unzip is now able to extract archives with path longer than 256 chars. 2) CHG: {Unzip} removed all conversion from c-style string to pascal-string (see fix 1) 3) ADD: {Unzip} Finderinfo of folders are also restored. 4) ADD: {Console} Added info about current path in the command-line box. 5) FIX: {Console} Construction of the command-line of the unzip-dialog box fixed. First beta release 06.June.1998 ----------------------------- no history. Just to many code was neccessary to build the first mac-port. Start of the port MacZip February 1998 -------------------------------------------------------------------------------- Legende: FIX: fixes a bug CHG: inform about changed items. ADD: added feature RMV: removed Item {Unzip} -> only related to the Unzip-module {Zip} -> only related to the Zip-module These are just libraries and are linked into the console-app. {Console} -> only related to the Userinterface (not SIOUX) MacOS has no tool like a command-line. So it's neccessary to write wrapper around the command-line tools. Dirk Haase zip30/macos/osdep.h0100644000076400000060000000451610655035152012356 0ustar edisk/* Copyright (c) 1990-2007 Info-ZIP. All rights reserved. See the accompanying file LICENSE, version 2007-Mar-4 or later (the contents of which are also included in zip.h) for terms of use. If, for some reason, all these files are missing, the Info-ZIP license also may be found at: ftp://ftp.info-zip.org/pub/infozip/license.html */ #ifndef __MACOS_OSDEP_H #define __MACOS_OSDEP_H 1 #ifndef MACOS # define MACOS #endif #include #include #include #include #include #include #include #include #include #include #include "unixlike.h" #include "macglob.h" #define NO_MKTEMP 1 #define PASSWD_FROM_STDIN 1 #define NO_SYMLINKS 1 #define USE_ZIPMAIN 1 #define USE_CASE_MAP 1 /* case_map is used to ignore case in comparisons */ /* #define DEBUG_TIME */ #if (!defined(NO_EF_UT_TIME) && !defined(USE_EF_UT_TIME)) # define USE_EF_UT_TIME #endif #undef IZ_CHECK_TZ #ifndef ZP_NEED_MEMCOMPR # define ZP_NEED_MEMCOMPR #endif #define EXDEV 18 #define PATHCUT ':' /* file operations use "b" for binary */ #define FOPR "rb" #define FOPM "r+b" #define FOPW "wb" /* #define DEBUG */ /* These functions are defined as a macro instead of a function. so we have to undefine them for replacing (see printf.c) */ #undef getc #undef getchar #undef putchar void setfiletype(char *file, unsigned long Creator, unsigned long Type); char *GetZipVersionsInfo(void); char *GetZipVersionLocal(void); char *GetZipCopyright(void); void InitAllVars(void); void PrintFileInfo(void); int fprintf(FILE *file, const char *format, ...); int printf(const char *format, ...); void perror(const char *parm1); int macgetch(void); int MacOpen(const char *path,int oflag,...); FILE *MacFopen(const char *path,const char *mode); #define fopen(path, mode) MacFopen(path, mode) #define open(path, oflag) MacOpen(path, oflag) char *GetComment(char *filename); int readlink(char *path, char *buf, int size); void PrintStatProgress(char *msg); void InformProgress(const long progressMax, const long progressSoFar ); void ShowCounter(Boolean reset); void leftStatusString(char *status); #define PROCNAME(n) (action == ADD || action == UPDATE ? wild(n) : \ procname(n, 1)) #endif /* __MACOS_OSDEP_H */ zip30/macos/readme.1st0100644000076400000060000000125611022424022012742 0ustar ediskThis port is for Mac versions before Mac OS X. As Mac OS X is build on Unix, use the Unix port for Mac OS X. - 7 June 2008 Before you start: Extract "*.hqx" and "source:*.hqx" first and read the Readme.txt. The resource file and the compiler project files are in BinHex form because they contain Macintosh resource forks and as such can not be simply stored a normal file on a non-Macintosh system. BinHex form is the traditional way for transferring such files via non-Macintosh systems. It's also the safest since it uses only printable characters. The ".hqx" files must be converted with StuffitExpander or BinHex 4.0 (or equivalent) on a Macintosh system before using them. zip30/macos/README.TXT0100644000076400000060000005204307321744012012425 0ustar ediskA free Macintosh Port of Info-ZIP's Zip and UnZip By Dirk Haase, d_haase@sitec.net Home page: www.sitec.net/maczip Mirror page: www.haase-online.de/dirk/maczip ================================ Abstract: --------- MacZip is a cross-platform compatible tool that includes both Zip (for compression) and UnZip (for extraction). Zip is a compression and file packaging utility for Unix, VMS, MSDOS, OS/2, Windows 9x, Windows NT, Atari, Macintosh, Amiga, Acorn RISC OS, and other systems. UnZip unpacks zip archives. The Zip and UnZip programs can process archives produced by PKZIP, and PKZIP and PKUNZIP can work with archives produced by zip. Zip version 2.2 is compatible with PKZIP 2.04. If you are new to MacZip please read first the file "ReadMe.1st". License: -------- Copyright (c) 1990-2001 Info-ZIP. All rights reserved. See the accompanying file LICENSE, version 2000-Apr-09 or later (the contents of which are also included in unzip.h) for terms of use. If, for some reason, all these files are missing, the Info-ZIP license also may be found at: ftp://ftp.info-zip.org/pub/infozip/license.html Requirements ------------ MacZip requires at least System 7 and a Macintosh with a minimum of a Motorola 68020 or PowerPC 601 processor. Other configurations may work but it is not tested at all. The application is distributed as a fat binary with both regular 68K and native PowerPC versions included. Installation ------------ Move the executable(s) somewhere--for example, drag it (or them) to your Applications folder. For easy access, make an alias in the Launcher Control Panel or directly on your desktop. The GUI is very simple. It was not my intention to make a full-blown GUI, however I think it is comfortable enough to use it as regular tool. This port supports also Apple-event. So you can install it in your WWW-Browser as a helper app. For more Info about the contents of this package, take a look into the "macos/Contents" (or :macos:Contents) file. Some notes on how to rebuild the Macintosh applications can be found in INSTALL. Usage: ------ Basically there are four ways to start MacZip: a) Drag'n Drop b) using the Dialog box (Menu: File -> Zip/Unzip): Please read the file "ReadMe.1st" for the description of the items a and b. c) Using the Command line (Menu: File->Command Line): The Zip & UnZip tools are command line tools. So the behavior is exactly the same like the Zip & UnZip tools on Unix or Windows/DOS. This means, if you want to zip some files, you have to write a command line like this: "zip [switches] path_to_zip_archive path_to_files_folders" - Go to "File", select "Command Line" and the "MacZip Entry box" Dialog Box appears. An example: a: your zip may be created at Macintosh HD:applications:archive.zip b: your files may be found at Macintosh HD:somewhere:my_folder_to_archive:* Note: At the end of the path there must be a filename or a wild card ! (see Footnotes: 1 wild card, 2 Mac path names) So the command line should look like (one line!): zip "Macintosh HD:applications:archive.zip" "Macintosh HD:somewhere:my_folder_to_archive:*" - Click on "Enter" to start the task. Since you can not set a default folder you have to enter always a full qualified path names. Full-qualified path names are path names including the Volume name ! (see Footnote: 2 Mac path names) d) Using Applescript: There is only one additional event defined: "do_cmd". You can enter every valid command line. The first word must be "zip" or "unzip" to select the action (compress or extraction). See sample Applescript: tell application "MacZip (PPC)" activate with timeout of 90000 seconds do_cmd "zip -rjjN Volume:archive \"My Volume:*\" " end timeout end tell This script opens MacZip, brings it to the foreground on the Mac, starts the zip action with the command line: zip -rjjN Volume:archive "My Volume:*" . A short introduction is also available online: http://www.sitec.net/maczip/How-To-Do/ It's possible to stop the run of Zip/Unzip with the well known shortcut [Command] + [.]. --------------------------------------------------------------------------- There are some Mac-specific switches available. Zip Module: -df [MacOS] Include only data-fork of files zipped into the archive. Good for exporting files to foreign operating-systems. Resource-forks will be ignored at all. -jj [MacOS] record Fullpath (+ Volname). The complete path including volume will be stored. By default the relative path will be stored. -S [MSDOS, OS/2, WIN32 and ATARI] Include system and hidden files. [MacOS] Includes finder invisible files, which are ignored otherwise. Unzip Module: -E [MacOS only] display contents of MacOS extra field during restore operation. -i [MacOS only] ignore filenames stored in MacOS extra fields. Instead, the most compatible filename stored in the generic part of the entry's header is used. -J [MacOS only] ignore MacOS extra fields. All Macin- tosh specific info is skipped. Data-fork and resource-fork are restored as separate files. Select [File]->[Get Help on Zip/Unzip] for a complete list of switches. Limitations / Problems: ----------------------- - Aliases are not supported. I tried, but I got broken aliases. This port will silently ignore all aliases. It's on my to-do list for future releases. - Zip needs much memory to compress many files: You may need to increase the 'Preferred Size' in 'Get Info'. Values of 12 Megabytes or more are possible - Unzip needs about 500 Kbytes of memory to unzip no matter how many files were compressed and expanded. - and finally one big macintosh-related problem: This port has one weak point: It's based on path names. As you may be already know: Path names are not unique on a Mac ! The main reason is that an attempt to implement support exact saving of the MacOS specific internal file structures would require a throughout rewrite of major parts of shared code, probably sacrifying compatibility with other systems. I have no solution at the moment. The port will just warn you if you try zip from / to a volume which has a duplicate name. MacZip has problems to find the archive or the files. My (Big) recommendation: Name all your volumes with a unique name and MacZip will run without any problem. Known Bugs: - crypted files in a zip archive are sometimes corrupt: I get an error message: invalid compressed data to inflate. Appearance of this error is purely be chance: I did a small test: Unzipping an archive containing 3589 files 56 files fails to unzip, so about 1.5%. Root cause is completely unclear to me :( I strongly recommend to test your archive (e.g. unzip -t archive). Zip Programs / Macintosh Extra-Data: ----------------------------------------- A brief overview: Currently, as far as I know, there are 6 Zip programs available for the Macintosh platform. These programs build (of course) different variants of Zip files: - Info-ZIP's first Port of Zip. Ported by Johnny Lee This port is rather outdated and no longer supported (since 1992). 68K only. Only minimal Mac-info is stored (Creator/Type, Finder attributes). Creator/Type: '????' / '????' Until year 1998, only UnZip 5.32 survived. - ZipIt by Tom Brown. This is Shareware and still supported I think. ZipIt has a nice GUI, but I found it can't handle large Zip files quite well. ZipIt compresses Macintosh files using the Mac Binary format. So, transferring files to other platforms is not so easy. Only minimal Mac-info is stored (Creator/Type, Finder attributes). Mac filenames are changed to a most compatible filename. Creator/Type: 'ZIP ' / 'ZIP ' - PKZIP/mac v2.03/210d. This is Shareware. This Zip implementation for the Mac can be found on ASI's web site (http://www.asizip.com/products/products.htm). The name of this program is misleading, it is NOT a product from PKWARE. ASI's last release version is v2.03, and they also offer a newer beta version PKZIP/mac 210d. But even the Beta version is rather outdated (1995). Only minimal Mac-info is stored (Creator/Type, Finder attributes). The Zipfile format looks like incompatible to other platforms. (More details about the compatibility issue can be found in proginfo/3rdparty.bug!). Type: 'PKz1' Mac filenames are restored without any change. - Aladdin DropZip 1999, This is Shareware. Aladdin chose the format of ZipIt. Therefore, it has the some drawbacks like ZipIt. Creator/Type: 'SITx' / 'ZIP ' - SmartZip 1.0 1999 - by Marco Bambini Vampire Software. This is Shareware. SmartZip compresses Macintosh files using the Mac Binary. Therefore, it has the same drawbacks like ZipIt. Creator/Type: 'dZIP' / 'ZIP ' and finally: - Info-ZIP's latest Port of Zip. MacZip 1.0. Ported by me :-) It is supported (of course) and up to date. Full set of macintosh info is stored: Creator/Type, Finder attributes, Finder comments, MacOS 8.0 Folder settings, Icon/Folder Positions ... Mac filenames are restored without any change. Creator/Type: 'IZip' / 'ZIP ' Compatibility of my port; Extraction: - Archives from Info-ZIP's first port (by Johnny Lee) are still compatible. - Extraction of ZipIt archives is supported. This support is not complete: Filenames are correct but Directory names are sometimes mangled to a DOS compatible form. Segmented archives are not supported. - PKZiP/mac archive files are extracted without resource-forks and without any Finder info. I have no information about that zip format. Compatibility of my port; Compression: - My port supports only the new Info-ZIP format (introduced with this port). Therefore archives created by MacZip 1.0 (March 1999) must be extracted with this version or later releases of Info-ZIP's UnZip to restore the complete set of Macintosh attributes. Note: This port is complete unrelated to the shareware ZipIt. Even more, handling of special Macintosh attributes is incompatible with ZipIt. This port (MacZip) may be used to extract archives created by ZipIt, but make sure that you get the result as you expected. Macintosh Files; File Forks: ---------------------------- All Macintosh files comprise two forks, known as the data fork and the resource fork. Unlike the bytes stored in the resource fork, the bytes in the data fork do not have to exhibit any particular internal structure. The application is responsible for interpreting the bytes in the data fork in whatever manner is appropriate. The bytes in the resource fork usually have a defined internal structure and contain data object like menus, dialog boxes, icons and pictures. Although all Macintosh files contain both a data fork and a resource fork, one or both of these forks may be empty. MacZip stores data-forks and resource-forks separately. The Zipfile format does not allow to store two archive entries using exactly the same name. My solution is to modify the Path name of the resource-fork. All resource-fork names are prepended with a leading special directory named "XtraStuf.mac". So, when extracting on a Mac, you should never see this directory "XtraStuf.mac" on your *disk*. On all foreign systems that support directories in filenames (e.g.: OS/2, Unix, DOS/Windows, VMS) you will get a directory "XtraStuf.mac" when extracting MacZip archives. You can delete the complete directory "XtraStuf.mac" since Mac resources do not make much sense outside the MacOS world. Text encoding; Charsets of the Filenames: ----------------------------------------- The following information is only important if you plan to transfer archives across different platforms/language systems: A typical Zip archive does not support different charsets. All filenames stored in the public area (= accessible by foreign systems other than MacOS) must be coded in the charset ISO-8859-1 (CP1252 in the Microsoft Windows world) or CP850 (DOSLatin1). The latter should only be used by Zip programs that mark the archive entries as "created under DOS". Apart from Macs, the commonly used platforms either support ISO-8859-1 directly, or are compatible with it. To achieve maximum compatibility, MacZip convert filenames from the Mac OS Roman character set to ISO-8859-1 and vice versa. But not every char of the charset MacRoman has their equivalent in ISO-8859-1. To make the mapping in most cases possible, I chose most similar chars or at least the MIDDLE DOT. Mac OS Roman character set is used for at least the following Mac OS localizations: U.S., British, Canadian French, French, Swiss French, German, Swiss German, Italian, Swiss Italian, Dutch, Swedish, Norwegian, Danish, Finnish, Spanish, Catalan, Portuguese, Brazilian, and the default International system. In all Mac OS encodings, character codes 0x00-0x7F are identical to ASCII, except that - in Mac OS Japanese, yen sign replaces reverse solidus - in Mac OS Arabic, Farsi, and Hebrew, some of the punctuation in this range is treated as having strong left-right directionality, although the corresponding Unicode characters have neutral directionality So, for best compatibility, confine filenames to the standard 7-bit ASCII character set. If you generate a filename list of your archive (unzip -l), you will see the converted filenames. Your can also extract the archive with the switch '-i' (= ignore mac filenames), and test your result. This MacZip port uses its own filename stored in the archive. At the moment, the filename will be not converted. However, I'm planning to add support for Unicode. Currently, the following Mac OS encodings are NOT supported: Japanese, ChineseTrad, Korean, Arabic, Hebrew, Greek, Cyrillic, Devanagari, Gurmukhi, Gujarati, Oriya, Bengali, Tamil, Telugu Kannada, Malayalam, Sinhalese, Burmese, Khmer, Thai, Laotian, Georgian, Armenian, ChineseSimp, Tibetan, Mongolian, Ethiopic, Vietnamese, ExtArabic and finally: Symbol - this is the encoding for the font named "Symbol". Dingbats - this is the encoding for the font named "Zapf Dingbats". If you extract an archive coded with one of these charsets you will probably get filenames with funny characters. These problems apply only to filenames and NOT to the file content. of course: The content of the files will NEVER be converted !! File-/Creator Type: ------------- This port uses the creator type 'IZip' and it is registered at Apple (since 08. March 1998). File types can not be registered any more. This port uses 'ZIP ' for Zip archive files. The creator 'IZip' type should be used for all future versions of MacZip. Hints for proper restoration of file-time stamps: ------------------------------------------------- UnZip requires the host computer to have proper time zone information in order to handle certain tasks correctly (see unzip.txt). To set the time zone on the Macintosh, go to the Map Control Panel and enter the correct number of hours (and, in a few locales, minutes) offset from Universal Time/Greenwich Mean Time. For example, the US Pacific time zone is -8 hours from UTC/GMT during standard (winter) time and -7 hours from UTC/GMT during Daylight Savings Time. The US Eastern time zone is -5 hours during the winter and -4 hours during the summer. Discussion of Daylight Savings Time ----------------------------------- The setting in the Date & Time control panel for Daylight Savings time is a universal setting. That is, it assumes everybody in the world is observing Daylight Savings time when its check box is selected. If other areas of the world are not observing Daylight Savings time when the check box is selected in the Date & Time control panel, then the Map control panel will be off by an hour for all areas that are not recognizing Daylight Savings time. Conversely, if you set the Map control panel to an area that does not observe Daylight Savings time and deselect/uncheck the check box for Daylight Savings time in the Date & Time control panel, then time in all areas celebrating Daylight Savings time will be off by an hour in the Map control panel. Example: In the case of Hawaiians, sometimes they are three hours behind Pacific Standard Time (PST) and sometimes two hours behind Pacific Daylight Time (PDT). The Map control panel can only calculate differences between time zones relative to Greenwich Mean Time (GMT). Hawaii will always show up as three hours past the Pacific time zone and five hours past the Central time zone. When Hawaiians are not observing Daylight Savings time, but the rest of the country is, there is no combination of settings in Map and Date & Time control panels which will enable you to display Hawaiian local time correctly AND concurrently display the correct time in other places that do observe Daylight Savings time. The knowledge about which countries observe Daylight Savings time and which do not is not built into the Map control panel, so it does not allow for such a complex calculation. This same situation also occurs in other parts of the world besides Hawaii. Phoenix, Arizona is an example of an area of the U.S. which also does not observe Daylight Savings time. Conclusion: MacZip only knows the GMT and DST offsets of the current time, not for the time in question. Projects & Packages: -------------------- A Note to version numbers: Version of MacZip is currently 1.06 and is based on the zip code version 2.3 and unzip code version 5.42. See About Box for current version and compiler build date. Because of the amount of sources I splitted this port into several projects. See http://www.sitec.net/maczip for updates. - core source parts: unzxxx.zip zipxxx.zip These archives contains the main parts of the port. You can build libraries and a standalone App with Metrowerks standard console SIOUX. They contain only sources, no executables. These archives are exact copies of the standard Info-ZIP source distributions; they were only repackaged under MacOS using MacZip, with one minor addition: For those files that are stored in BinHex'ed format in the Info-ZIP reference source archives, unpacked version that are ready for use have been added. - additional source part: MacZipxxx.zip: contains all the GUI stuff and the project files to build the main-app. Only sources of the GUI, no zip or unzip code. To build MacZip successfully you will need to also download the zip and unzip packages. - executables: MacZipxxxnc.hqx: contains only executables and 'README.TXT', This version is without en-/decryption support ! MacZipxxxc.hqx: contains only executables and 'README.TXT', This version supports en-/decryption ! - encryption sources: zcryptxx.zip: To build crypt versions of MacZip. download from ftp://ftp.icce.rug.nl/infozip/ (and subdirectories) - documentation: MacZipDocu.zip: contains some further docus about the algorithm, limits, Info-ZIP's appnote and a How-to-do Webpage. Credits: -------- Macstuff.c and recurse.c: All the functions are from More Files. More Files fixes many of the broken or underfunctional parts of the file system. Thanks to Jim Luther. (see morefiles.doc) --------------------------------------------------------------------------- Footnotes: 1. wild card: The '*' is a wild card and means 'all files' Just in case you don't know wild cards: '*' is a place holder for any character. e.g.: "this*" matches with "this_file" or "this_textfile" but it doesn't match with "only_this_file" or "first_this_textfile" "*this*" matches with "this_file" or "this_textfile" AND matches with "only_this_file" or "first_this_textfile" 2. Mac pathnames: The following characteristics of Macintosh pathnames should be noted: A full pathname never begins with a colon, but must contain at least one colon. A partial pathname always begins with a colon separator except in the case where the file partial pathname is a simple file or directory name. Single trailing separator colons in full or partial pathnames are ignored except in the case of full pathnames to volumes. In full pathnames to volumes, the trailing separator colon is required. Consecutive separator colons can be used to ascend a level from a directory to its parent directory. Two consecutive separator colons will ascend one level, three consecutive separator colons will ascend two levels, and so on. Ascending can only occur from a directory; not a file. --------------------------------------------------------------------------- Dirk Haase ========== zip30/macos/source/0040755000076400000060000000000011033727770012375 5ustar ediskzip30/macos/source/charmap.h0100644000076400000060000005125607076031052014160 0ustar edisk/* Copyright (c) 1990-2000 Info-ZIP. All rights reserved. See the accompanying file LICENSE, version 2000-Apr-09 or later (the contents of which are also included in zip.h) for terms of use. If, for some reason, all these files are missing, the Info-ZIP license also may be found at: ftp://ftp.info-zip.org/pub/infozip/license.html */ #ifndef __macos_charmap_h #define __macos_charmap_h /* Conversion table from MacOS Roman to "Western Europe & America" Windows codepage 1252 Notes on Mac OS Roman: ---------------------- Mac OS Roman character set is used for at least the following Mac OS localizations: U.S., British, Canadian French, French, Swiss French, German, Swiss German, Italian, Swiss Italian, Dutch, Swedish, Norwegian, Danish, Finnish, Spanish, Catalan, Portuguese, Brazilian, and the default International system. Not every char of the charset MacRoman has their equivalent in Windows CodePage1252. To make the mapping in most cases possible, I choosed most similar chars or at least the BULLET. Chars that do not have a direct match are marked with '***' The Windows codepage 1252 contains the ISO 8859-1 "Latin 1" codepage, with some additional printable characters in the range (0x80 - 0x9F), that is reserved to control codes in the ISO 8859-1 character table. In all Mac OS encodings, character codes 0x00-0x7F are identical to ASCII */ ZCONST unsigned char MacRoman_to_WinCP1252[128] = { /* Win CP1252 UniCode UniCode Names */ 0xC4 , /* 0x00C4 #LATIN CAPITAL LETTER A WITH DIAERESIS */ 0xC5 , /* 0x00C5 #LATIN CAPITAL LETTER A WITH RING ABOVE */ 0xC7 , /* 0x00C7 #LATIN CAPITAL LETTER C WITH CEDILLA */ 0xC9 , /* 0x00C9 #LATIN CAPITAL LETTER E WITH ACUTE */ 0xD1 , /* 0x00D1 #LATIN CAPITAL LETTER N WITH TILDE */ 0xD6 , /* 0x00D6 #LATIN CAPITAL LETTER O WITH DIAERESIS */ 0xDC , /* 0x00DC #LATIN CAPITAL LETTER U WITH DIAERESIS */ 0xE1 , /* 0x00E1 #LATIN SMALL LETTER A WITH ACUTE */ 0xE0 , /* 0x00E0 #LATIN SMALL LETTER A WITH GRAVE */ 0xE2 , /* 0x00E2 #LATIN SMALL LETTER A WITH CIRCUMFLEX */ 0xE4 , /* 0x00E4 #LATIN SMALL LETTER A WITH DIAERESIS */ 0xE3 , /* 0x00E3 #LATIN SMALL LETTER A WITH TILDE */ 0xE5 , /* 0x00E5 #LATIN SMALL LETTER A WITH RING ABOVE */ 0xE7 , /* 0x00E7 #LATIN SMALL LETTER C WITH CEDILLA */ 0xE9 , /* 0x00E9 #LATIN SMALL LETTER E WITH ACUTE */ 0xE8 , /* 0x00E8 #LATIN SMALL LETTER E WITH GRAVE */ 0xEA , /* 0x00EA #LATIN SMALL LETTER E WITH CIRCUMFLEX */ 0xEB , /* 0x00EB #LATIN SMALL LETTER E WITH DIAERESIS */ 0xED , /* 0x00ED #LATIN SMALL LETTER I WITH ACUTE */ 0xEC , /* 0x00EC #LATIN SMALL LETTER I WITH GRAVE */ 0xEE , /* 0x00EE #LATIN SMALL LETTER I WITH CIRCUMFLEX */ 0xEF , /* 0x00EF #LATIN SMALL LETTER I WITH DIAERESIS */ 0xF1 , /* 0x00F1 #LATIN SMALL LETTER N WITH TILDE */ 0xF3 , /* 0x00F3 #LATIN SMALL LETTER O WITH ACUTE */ 0xF2 , /* 0x00F2 #LATIN SMALL LETTER O WITH GRAVE */ 0xF4 , /* 0x00F4 #LATIN SMALL LETTER O WITH CIRCUMFLEX */ 0xF6 , /* 0x00F6 #LATIN SMALL LETTER O WITH DIAERESIS */ 0xF5 , /* 0x00F5 #LATIN SMALL LETTER O WITH TILDE */ 0xFA , /* 0x00FA #LATIN SMALL LETTER U WITH ACUTE */ 0xF9 , /* 0x00F9 #LATIN SMALL LETTER U WITH GRAVE */ 0xFB , /* 0x00FB #LATIN SMALL LETTER U WITH CIRCUMFLEX */ 0xFC , /* 0x00FC #LATIN SMALL LETTER U WITH DIAERESIS */ 0x86 , /* 0x2020 #DAGGER */ 0xB0 , /* 0x00B0 #DEGREE SIGN */ 0xA2 , /* 0x00A2 #CENT SIGN */ 0xA3 , /* 0x00A3 #POUND SIGN */ 0x95 , /* 0x2022 # *** BULLET */ 0x95 , /* 0x2022 #BULLET */ 0xB6 , /* 0x00B6 #PILCROW SIGN */ 0xDF , /* 0x00DF #LATIN SMALL LETTER SHARP S */ 0xAE , /* 0x00AE #REGISTERED SIGN */ 0xA9 , /* 0x00A9 #COPYRIGHT SIGN */ 0x99 , /* 0x2122 #TRADE MARK SIGN */ 0xB4 , /* 0x00B4 #ACUTE ACCENT */ 0xA8 , /* 0x00A8 #DIAERESIS */ 0x95 , /* 0x2022 # *** BULLET */ 0xC6 , /* 0x00C6 #LATIN CAPITAL LETTER AE */ 0xD8 , /* 0x00D8 #LATIN CAPITAL LETTER O WITH STROKE */ 0x95 , /* 0x2022 # *** BULLET */ 0xB1 , /* 0x00B1 #PLUS-MINUS SIGN */ 0x95 , /* 0x2022 # *** BULLET */ 0x95 , /* 0x2022 # *** BULLET */ 0xA5 , /* 0x00A5 #YEN SIGN */ 0xB5 , /* 0x00B5 #MICRO SIGN */ 0x95 , /* 0x2022 # *** BULLET */ 0x95 , /* 0x2022 # *** BULLET */ 0x95 , /* 0x2022 # *** BULLET */ 0x95 , /* 0x2022 # *** BULLET */ 0x95 , /* 0x2022 # *** BULLET */ 0xAA , /* 0x00AA #FEMININE ORDINAL INDICATOR */ 0xBA , /* 0x00BA #MASCULINE ORDINAL INDICATOR */ 0x95 , /* 0x2022 # *** BULLET */ 0xE6 , /* 0x00E6 #LATIN SMALL LETTER AE */ 0xF8 , /* 0x00F8 #LATIN SMALL LETTER O WITH STROKE */ 0xBF , /* 0x00BF #INVERTED QUESTION MARK */ 0xA1 , /* 0x00A1 #INVERTED EXCLAMATION MARK */ 0xAC , /* 0x00AC #NOT SIGN */ 0x95 , /* 0x2022 # *** BULLET */ 0x83 , /* 0x0192 #LATIN SMALL LETTER F WITH HOOK */ 0x95 , /* 0x2022 # *** BULLET */ 0x95 , /* 0x2022 # *** BULLET */ 0xAB , /* 0x00AB #LEFT-POINTING DOUBLE ANGLE QUOTATION MARK */ 0xBB , /* 0x00BB #RIGHT-POINTING DOUBLE ANGLE QUOTATION MARK */ 0x85 , /* 0x2026 #HORIZONTAL ELLIPSIS */ 0xA0 , /* 0x00A0 #NO-BREAK SPACE */ 0xC0 , /* 0x00C0 #LATIN CAPITAL LETTER A WITH GRAVE */ 0xC3 , /* 0x00C3 #LATIN CAPITAL LETTER A WITH TILDE */ 0xD5 , /* 0x00D5 #LATIN CAPITAL LETTER O WITH TILDE */ 0x95 , /* 0x2022 # *** BULLET */ 0x95 , /* 0x2022 # *** BULLET */ 0x96 , /* 0x2013 #EN DASH */ 0x97 , /* 0x2014 #EM DASH */ 0x93 , /* 0x201C #LEFT DOUBLE QUOTATION MARK */ 0x94 , /* 0x201D #RIGHT DOUBLE QUOTATION MARK */ 0x91 , /* 0x2018 #LEFT SINGLE QUOTATION MARK */ 0x92 , /* 0x2019 #RIGHT SINGLE QUOTATION MARK */ 0xF7 , /* 0x00F7 #DIVISION SIGN */ 0x95 , /* 0x2022 # *** BULLET */ 0xFF , /* 0x00FF #LATIN SMALL LETTER Y WITH DIAERESIS */ 0x9F , /* 0x0178 #LATIN CAPITAL LETTER Y WITH DIAERESIS */ 0x95 , /* 0x2022 # *** BULLET */ 0xA4 , /* 0x00A4 #CURRENCY SIGN */ 0x8B , /* 0x2039 #SINGLE LEFT-POINTING ANGLE QUOTATION MARK */ 0x9B , /* 0x203A #SINGLE RIGHT-POINTING ANGLE QUOTATION MARK */ 0x95 , /* 0x2022 # *** BULLET */ 0x95 , /* 0x2022 # *** BULLET */ 0x87 , /* 0x2021 #DOUBLE DAGGER */ 0xB7 , /* 0x00B7 #MIDDLE DOT */ 0x82 , /* 0x201A #SINGLE LOW-9 QUOTATION MARK */ 0x84 , /* 0x201E #DOUBLE LOW-9 QUOTATION MARK */ 0x89 , /* 0x2030 #PER MILLE SIGN */ 0xC2 , /* 0x00C2 #LATIN CAPITAL LETTER A WITH CIRCUMFLEX */ 0xCA , /* 0x00CA #LATIN CAPITAL LETTER E WITH CIRCUMFLEX */ 0xC1 , /* 0x00C1 #LATIN CAPITAL LETTER A WITH ACUTE */ 0xCB , /* 0x00CB #LATIN CAPITAL LETTER E WITH DIAERESIS */ 0xC8 , /* 0x00C8 #LATIN CAPITAL LETTER E WITH GRAVE */ 0xCD , /* 0x00CD #LATIN CAPITAL LETTER I WITH ACUTE */ 0xCE , /* 0x00CE #LATIN CAPITAL LETTER I WITH CIRCUMFLEX */ 0xCF , /* 0x00CF #LATIN CAPITAL LETTER I WITH DIAERESIS */ 0xCC , /* 0x00CC #LATIN CAPITAL LETTER I WITH GRAVE */ 0xD3 , /* 0x00D3 #LATIN CAPITAL LETTER O WITH ACUTE */ 0xD4 , /* 0x00D4 #LATIN CAPITAL LETTER O WITH CIRCUMFLEX */ 0x95 , /* 0x2022 # *** BULLET */ 0xD2 , /* 0x00D2 #LATIN CAPITAL LETTER O WITH GRAVE */ 0xDA , /* 0x00DA #LATIN CAPITAL LETTER U WITH ACUTE */ 0xDB , /* 0x00DB #LATIN CAPITAL LETTER U WITH CIRCUMFLEX */ 0xD9 , /* 0x00D9 #LATIN CAPITAL LETTER U WITH GRAVE */ 0x95 , /* 0x2022 # *** BULLET */ 0x88 , /* 0x02C6 #MODIFIER LETTER CIRCUMFLEX ACCENT */ 0x98 , /* 0x02DC #SMALL TILDE */ 0xAF , /* 0x00AF #MACRON */ 0x95 , /* 0x2022 # *** BULLET */ 0x95 , /* 0x2022 # *** BULLET */ 0x95 , /* 0x2022 # *** BULLET */ 0xB8 , /* 0x00B8 #CEDILLA */ 0x95 , /* 0x2022 # *** BULLET */ 0x95 , /* 0x2022 # *** BULLET */ 0x95 /* 0x2022 # *** BULLET */ }; ZCONST unsigned char WinCP1252_to_MacRoman[128] = { /* Mac Roman UniCode UniCode Names */ 0xA5 , /* 0x2022 # *** BULLET */ 0xA5 , /* 0x2022 # *** BULLET */ 0xE2 , /* 0x201A # SINGLE LOW-9 QUOTATION MARK */ 0xC4 , /* 0x0192 # LATIN SMALL LETTER F WITH HOOK */ 0xE3 , /* 0x201E # DOUBLE LOW-9 QUOTATION MARK */ 0xC9 , /* 0x2026 # HORIZONTAL ELLIPSIS */ 0xA0 , /* 0x2020 # DAGGER */ 0xE0 , /* 0x2021 # DOUBLE DAGGER */ 0xF6 , /* 0x02C6 # MODIFIER LETTER CIRCUMFLEX ACCENT */ 0xE4 , /* 0x2030 # PER MILLE SIGN */ 0xA5 , /* 0x2022 # *** BULLET */ 0xDC , /* 0x2039 # SINGLE LEFT-POINTING ANGLE QUOTATION MARK */ 0xA5 , /* 0x2022 # *** BULLET */ 0xA5 , /* 0x2022 # *** BULLET */ 0xA5 , /* 0x2022 # *** BULLET */ 0xA5 , /* 0x2022 # *** BULLET */ 0xA5 , /* 0x2022 # *** BULLET */ 0xD4 , /* 0x2018 # LEFT SINGLE QUOTATION MARK */ 0xD5 , /* 0x2019 # RIGHT SINGLE QUOTATION MARK */ 0xD2 , /* 0x201C # LEFT DOUBLE QUOTATION MARK */ 0xD3 , /* 0x201D # RIGHT DOUBLE QUOTATION MARK */ 0xA5 , /* 0x2022 # BULLET */ 0xD0 , /* 0x2013 # EN DASH */ 0xD1 , /* 0x2014 # EM DASH */ 0xF7 , /* 0x02DC # SMALL TILDE */ 0xAA , /* 0x2122 # TRADE MARK SIGN */ 0xA5 , /* 0x2022 # *** BULLET */ 0xDD , /* 0x203A # SINGLE RIGHT-POINTING ANGLE QUOTATION MARK */ 0xA5 , /* 0x2022 # *** BULLET */ 0xA5 , /* 0x2022 # *** BULLET */ 0xA5 , /* 0x2022 # *** BULLET */ 0xD9 , /* 0x0178 # LATIN CAPITAL LETTER Y WITH DIAERESIS */ 0xCA , /* 0x00A0 # NO-BREAK SPACE */ 0xC1 , /* 0x00A1 # INVERTED EXCLAMATION MARK */ 0xA2 , /* 0x00A2 # CENT SIGN */ 0xA3 , /* 0x00A3 # POUND SIGN */ 0xDB , /* 0x00A4 # CURRENCY SIGN */ 0xB4 , /* 0x00A5 # YEN SIGN */ 0xA5 , /* 0x2022 # *** BULLET */ 0xA5 , /* 0x2022 # *** BULLET */ 0xAC , /* 0x00A8 # DIAERESIS */ 0xA9 , /* 0x00A9 # COPYRIGHT SIGN */ 0xBB , /* 0x00AA # FEMININE ORDINAL INDICATOR */ 0xC7 , /* 0x00AB # LEFT-POINTING DOUBLE ANGLE QUOTATION MARK */ 0xC2 , /* 0x00AC # NOT SIGN */ 0xA5 , /* 0x2022 # *** BULLET */ 0xA8 , /* 0x00AE # REGISTERED SIGN */ 0xF8 , /* 0x00AF # MACRON */ 0xA1 , /* 0x00B0 # DEGREE SIGN */ 0xB1 , /* 0x00B1 # PLUS-MINUS SIGN */ 0xA5 , /* 0x2022 # *** BULLET */ 0xA5 , /* 0x2022 # *** BULLET */ 0xAB , /* 0x00B4 # ACUTE ACCENT */ 0xB5 , /* 0x00B5 # MICRO SIGN */ 0xA6 , /* 0x00B6 # PILCROW SIGN */ 0xE1 , /* 0x00B7 # MIDDLE DOT */ 0xFC , /* 0x00B8 # CEDILLA */ 0xA5 , /* 0x2022 # *** BULLET */ 0xBC , /* 0x00BA # MASCULINE ORDINAL INDICATOR */ 0xC8 , /* 0x00BB # RIGHT-POINTING DOUBLE ANGLE QUOTATION MARK */ 0xA5 , /* 0x2022 # *** BULLET */ 0xA5 , /* 0x2022 # *** BULLET */ 0xA5 , /* 0x2022 # *** BULLET */ 0xC0 , /* 0x00BF # INVERTED QUESTION MARK */ 0xCB , /* 0x00C0 # LATIN CAPITAL LETTER A WITH GRAVE */ 0xE7 , /* 0x00C1 # LATIN CAPITAL LETTER A WITH ACUTE */ 0xE5 , /* 0x00C2 # LATIN CAPITAL LETTER A WITH CIRCUMFLEX */ 0xCC , /* 0x00C3 # LATIN CAPITAL LETTER A WITH TILDE */ 0x80 , /* 0x00C4 # LATIN CAPITAL LETTER A WITH DIAERESIS */ 0x81 , /* 0x00C5 # LATIN CAPITAL LETTER A WITH RING ABOVE */ 0xAE , /* 0x00C6 # LATIN CAPITAL LETTER AE */ 0x82 , /* 0x00C7 # LATIN CAPITAL LETTER C WITH CEDILLA */ 0xE9 , /* 0x00C8 # LATIN CAPITAL LETTER E WITH GRAVE */ 0x83 , /* 0x00C9 # LATIN CAPITAL LETTER E WITH ACUTE */ 0xE6 , /* 0x00CA # LATIN CAPITAL LETTER E WITH CIRCUMFLEX */ 0xE8 , /* 0x00CB # LATIN CAPITAL LETTER E WITH DIAERESIS */ 0xED , /* 0x00CC # LATIN CAPITAL LETTER I WITH GRAVE */ 0xEA , /* 0x00CD # LATIN CAPITAL LETTER I WITH ACUTE */ 0xEB , /* 0x00CE # LATIN CAPITAL LETTER I WITH CIRCUMFLEX */ 0xEC , /* 0x00CF # LATIN CAPITAL LETTER I WITH DIAERESIS */ 0xA5 , /* 0x2022 # *** BULLET */ 0x84 , /* 0x00D1 # LATIN CAPITAL LETTER N WITH TILDE */ 0xF1 , /* 0x00D2 # LATIN CAPITAL LETTER O WITH GRAVE */ 0xEE , /* 0x00D3 # LATIN CAPITAL LETTER O WITH ACUTE */ 0xEF , /* 0x00D4 # LATIN CAPITAL LETTER O WITH CIRCUMFLEX */ 0xCD , /* 0x00D5 # LATIN CAPITAL LETTER O WITH TILDE */ 0x85 , /* 0x00D6 # LATIN CAPITAL LETTER O WITH DIAERESIS */ 0xA5 , /* 0x2022 # *** BULLET */ 0xAF , /* 0x00D8 # LATIN CAPITAL LETTER O WITH STROKE */ 0xF4 , /* 0x00D9 # LATIN CAPITAL LETTER U WITH GRAVE */ 0xF2 , /* 0x00DA # LATIN CAPITAL LETTER U WITH ACUTE */ 0xF3 , /* 0x00DB # LATIN CAPITAL LETTER U WITH CIRCUMFLEX */ 0x86 , /* 0x00DC # LATIN CAPITAL LETTER U WITH DIAERESIS */ 0xA5 , /* 0x2022 # *** BULLET */ 0xA5 , /* 0x2022 # *** BULLET */ 0xA7 , /* 0x00DF # LATIN SMALL LETTER SHARP S */ 0x88 , /* 0x00E0 # LATIN SMALL LETTER A WITH GRAVE */ 0x87 , /* 0x00E1 # LATIN SMALL LETTER A WITH ACUTE */ 0x89 , /* 0x00E2 # LATIN SMALL LETTER A WITH CIRCUMFLEX */ 0x8B , /* 0x00E3 # LATIN SMALL LETTER A WITH TILDE */ 0x8A , /* 0x00E4 # LATIN SMALL LETTER A WITH DIAERESIS */ 0x8C , /* 0x00E5 # LATIN SMALL LETTER A WITH RING ABOVE */ 0xBE , /* 0x00E6 # LATIN SMALL LETTER AE */ 0x8D , /* 0x00E7 # LATIN SMALL LETTER C WITH CEDILLA */ 0x8F , /* 0x00E8 # LATIN SMALL LETTER E WITH GRAVE */ 0x8E , /* 0x00E9 # LATIN SMALL LETTER E WITH ACUTE */ 0x90 , /* 0x00EA # LATIN SMALL LETTER E WITH CIRCUMFLEX */ 0x91 , /* 0x00EB # LATIN SMALL LETTER E WITH DIAERESIS */ 0x93 , /* 0x00EC # LATIN SMALL LETTER I WITH GRAVE */ 0x92 , /* 0x00ED # LATIN SMALL LETTER I WITH ACUTE */ 0x94 , /* 0x00EE # LATIN SMALL LETTER I WITH CIRCUMFLEX */ 0x95 , /* 0x00EF # LATIN SMALL LETTER I WITH DIAERESIS */ 0xA5 , /* 0x2022 # *** BULLET */ 0x96 , /* 0x00F1 # LATIN SMALL LETTER N WITH TILDE */ 0x98 , /* 0x00F2 # LATIN SMALL LETTER O WITH GRAVE */ 0x97 , /* 0x00F3 # LATIN SMALL LETTER O WITH ACUTE */ 0x99 , /* 0x00F4 # LATIN SMALL LETTER O WITH CIRCUMFLEX */ 0x9B , /* 0x00F5 # LATIN SMALL LETTER O WITH TILDE */ 0x9A , /* 0x00F6 # LATIN SMALL LETTER O WITH DIAERESIS */ 0xD6 , /* 0x00F7 # DIVISION SIGN */ 0xBF , /* 0x00F8 # LATIN SMALL LETTER O WITH STROKE */ 0x9D , /* 0x00F9 # LATIN SMALL LETTER U WITH GRAVE */ 0x9C , /* 0x00FA # LATIN SMALL LETTER U WITH ACUTE */ 0x9E , /* 0x00FB # LATIN SMALL LETTER U WITH CIRCUMFLEX */ 0x9F , /* 0x00FC # LATIN SMALL LETTER U WITH DIAERESIS */ 0xA5 , /* 0x2022 # *** BULLET */ 0xA5 , /* 0x2022 # *** BULLET */ 0xD8 /* 0x00FF # LATIN SMALL LETTER Y WITH DIAERESIS */ }; /* The following characters has no equivalent to each other: MacCodes 164 0xA4 0x00A7 # SECTION SIGN 253 0xFD 0x02DD # DOUBLE ACUTE ACCENT 189 0xBD 0x03A9 # GREEK CAPITAL LETTER OMEGA 185 0xB9 0x03C0 # GREEK SMALL LETTER PI 255 0xFF 0x02C7 # CARON 249 0xF9 0x02D8 # BREVE 250 0xFA 0x02D9 # DOT ABOVE 251 0xFB 0x02DA # RING ABOVE 254 0xFE 0x02DB # OGONEK 218 0xDA 0x2044 # FRACTION SLASH 182 0xB6 0x2202 # PARTIAL DIFFERENTIAL 198 0xC6 0x2206 # INCREMENT 184 0xB8 0x220F # N-ARY PRODUCT 183 0xB7 0x2211 # N-ARY SUMMATION 195 0xC3 0x221A # SQUARE ROOT 176 0xB0 0x221E # INFINITY 186 0xBA 0x222B # INTEGRAL 197 0xC5 0x2248 # ALMOST EQUAL TO 173 0xAD 0x2260 # NOT EQUAL TO 178 0xB2 0x2264 # LESS-THAN OR EQUAL TO 179 0xB3 0x2265 # GREATER-THAN OR EQUAL TO 215 0xD7 0x25CA # LOZENGE 240 0xF0 0xF8FF # Apple logo 222 0xDE 0xFB01 # LATIN SMALL LIGATURE FI 223 0xDF 0xFB02 # LATIN SMALL LIGATURE FL 245 0xF5 0x0131 # LATIN SMALL LETTER DOTLESS I 206 0xCE 0x0152 # LATIN CAPITAL LIGATURE OE 207 0xCF 0x0153 # LATIN SMALL LIGATURE OE WinCodes 129 0x81 #UNDEFINED 141 0x8D #UNDEFINED 143 0x8F #UNDEFINED 144 0x90 #UNDEFINED 157 0x9D #UNDEFINED 167 0xA7 0x00A7 #SECTION SIGN 173 0xAD 0x00AD #SOFT HYPHEN 178 0xB2 0x00B2 #SUPERSCRIPT TWO 179 0xB3 0x00B3 #SUPERSCRIPT THREE 185 0xB9 0x00B9 #SUPERSCRIPT ONE 188 0xBC 0x00BC #VULGAR FRACTION ONE QUARTER 189 0xBD 0x00BD #VULGAR FRACTION ONE HALF 190 0xBE 0x00BE #VULGAR FRACTION THREE QUARTERS 208 0xD0 0x00D0 #LATIN CAPITAL LETTER ETH 215 0xD7 0x00D7 #MULTIPLICATION SIGN 221 0xDD 0x00DD #LATIN CAPITAL LETTER Y WITH ACUTE 222 0xDE 0x00DE #LATIN CAPITAL LETTER THORN 240 0xF0 0x00F0 #LATIN SMALL LETTER ETH 253 0xFD 0x00FD #LATIN SMALL LETTER Y WITH ACUTE 254 0xFE 0x00FE #LATIN SMALL LETTER THORN 140 0x8C 0x0152 #LATIN CAPITAL LIGATURE OE 156 0x9C 0x0153 #LATIN SMALL LIGATURE OE 138 0x8A 0x0160 #LATIN CAPITAL LETTER S WITH CARON 154 0x9A 0x0161 #LATIN SMALL LETTER S WITH CARON 142 0x8E 0x017D #LATIN CAPITAL LETTER Z WITH CARON 158 0x9E 0x017E #LATIN SMALL LETTER Z WITH CARON 128 0x80 0x20AC #EURO SIGN 166 0xA6 0x00A6 #BROKEN BAR */ #endif /* !__macos_charmap_h */ zip30/macos/source/extrafld.c0100644000076400000060000007730710154332006014350 0ustar edisk/* Copyright (c) 1990-2002 Info-ZIP. All rights reserved. See the accompanying file LICENSE, version 2000-Apr-09 or later (the contents of which are also included in zip.h) for terms of use. If, for some reason, all these files are missing, the Info-ZIP license also may be found at: ftp://ftp.info-zip.org/pub/infozip/license.html */ /*--------------------------------------------------------------------------- extrafld.c contains functions to build extra-fields. ---------------------------------------------------------------------------*/ /*****************************************************************************/ /* Includes */ /*****************************************************************************/ #include #include "zip.h" #include "unixlike.h" #include "helpers.h" #include "pathname.h" /*****************************************************************************/ /* Macros, typedefs */ /*****************************************************************************/ /* ---------------------------------------------------------------------- */ /* Add a 'MAC3' extra field to the zlist data pointed to by z. */ /* This is the (new) Info-zip extra block for Macintosh */ #define EB_MAC3_HLEN 14 /* fixed length part of MAC3's header */ #define EB_L_MAC3_FINFO_LEN 52 /* fixed part of MAC3 compressible data */ #define EB_MAX_OF_VARDATA 1300 /* max possible datasize */ #define EB_L_MAC3_SIZE (EB_HEADSIZE + EB_MAC3_HLEN) #define EB_C_MAC3_SIZE (EB_HEADSIZE + EB_MAC3_HLEN) /* maximum memcompress overhead is the sum of the compression header length */ /* (6 = ush compression type, ulg CRC) and the worstcase deflate overhead */ /* when uncompressible data are kept in 2 "stored" blocks (5 per block = */ /* byte blocktype + 2 * ush blocklength) */ #define MEMCOMPRESS_OVERHEAD (EB_MEMCMPR_HSIZ + EB_DEFLAT_EXTRA) #define EB_M3_FL_COMPRESS 0x00 #define EB_M3_FL_DATFRK 0x01 /* data is data-fork */ #define EB_M3_FL_NOCHANGE 0x02 /* filename will be not changed */ #define EB_M3_FL_UNCMPR 0x04 /* data is 'natural' (not compressed) */ #define EB_M3_FL_TIME64 0x08 /* time is coded in 64 bit */ #define EB_M3_FL_NOUTC 0x10 /* only 'local' time-stamps are stored */ #define EB_L_UT_SIZE (EB_HEADSIZE + EB_UT_LEN(2)) #define EB_C_UT_SIZE (EB_HEADSIZE + EB_UT_LEN(1)) /* disable compressing of extra field #define MAC_EXTRAFLD_UNCMPR */ /* ---------------------------------------------------------------------- */ /* Add a 'JLEE' extra field to the zlist data pointed to by z. */ /* This is the (old) Info-zip resource-fork extra block for Macintosh (last Revision 1996-09-22) Layout made by Johnny Lee, Code made by me :-) */ #define EB_L_JLEE_LEN 40 /* fixed length of JLEE's header */ #define EB_C_JLEE_LEN 40 /* fixed length of JLEE's header */ #define EB_L_JLEE_SIZE (EB_HEADSIZE + EB_L_JLEE_LEN) #define EB_C_JLEE_SIZE (EB_HEADSIZE + EB_C_JLEE_LEN) /*****************************************************************************/ /* Global Vars */ /*****************************************************************************/ extern MacZipGlobals MacZip; extern unsigned long count_of_Zippedfiles; /*****************************************************************************/ /* Prototypes */ /*****************************************************************************/ static int add_UT_ef(struct zlist far *z, iztimes *z_utim); static int add_JLEE_ef(struct zlist far *z); /* old mac extra field */ static int add_MAC3_ef(struct zlist far *z); /* new mac extra field */ static void make_extrafield_JLEE(char *l_ef); static unsigned make_extrafield_MAC3(char *ef); static char *make_EF_Head_MAC3(char *ef, unsigned compsize, ulg attrsize, unsigned flag); static void print_extra_info(void); void UserStop(void); /*****************************************************************************/ /* Functions */ /*****************************************************************************/ /* * Set the extra-field's for each compressed file */ int set_extra_field(struct zlist far *z, iztimes *z_utim) /* store full data in local header but just modification time stamp info in central header */ { int retval; Assert_it(z, "set_extra_field","") Assert_it(z_utim, "set_extra_field","") z_utim = z_utim; /* Check to make sure z is valid. */ if( z == NULL ) { return ZE_LOGIC; } /* Resource forks are always binary */ if (MacZip.CurrentFork == ResourceFork) z->att = BINARY; if (noisy) { count_of_Zippedfiles++; InformProgress(MacZip.RawCountOfItems, count_of_Zippedfiles ); } /* PrintFileInfo(); */ switch (MacZip.MacZipMode) { case JohnnyLee_EF: { retval = add_JLEE_ef( z ); if (retval != ZE_OK) return retval; break; } case NewZipMode_EF: { /* */ #ifdef USE_EF_UT_TIME retval = add_UT_ef(z, z_utim); if (retval != ZE_OK) return retval; #endif retval = add_MAC3_ef( z ); if (retval != ZE_OK) return retval; break; } default: { printerr("Unknown Extrafieldmode", -1, -1, __LINE__, __FILE__, ""); return ZE_LOGIC; /* function should never reach this point */ } } /* MacStat information is now outdated and must be refreshed for the next file */ MacZip.isMacStatValid = false; return ZE_OK; } #ifdef USE_EF_UT_TIME /* * Build and add the Unix time extra-field. This extra field * will be included be default. Johnny Lee's implementation does * not use this kind of extra-field. * All datas are in Intel (=little-endian) format Extra field info: - 'UT' - UNIX time extra field This is done the same way ../unix/unix.c stores the 'UT'/'Ux' fields (full data in local header, only modification time in central header), with the 'M3' field added to the end and the size of the 'M3' field in the central header. */ static int add_UT_ef(struct zlist far *z, iztimes *z_utim) { char *l_ef = NULL; char *c_ef = NULL; Assert_it(z, "add_UT_ef","") #ifdef IZ_CHECK_TZ if (!zp_tz_is_valid) return ZE_OK; /* skip silently if no valid TZ info */ #endif /* We can't work if there's no entry to work on. */ if( z == NULL ) { return ZE_LOGIC; } /* Check to make sure we've got enough room in the extra fields. */ if( z->ext + EB_L_UT_SIZE > EF_SIZE_MAX || z->cext + EB_C_UT_SIZE > EF_SIZE_MAX ) { return ZE_MEM; } /* Allocate memory for the local and central extra fields. */ if( z->extra && z->ext != 0 ) { l_ef = (char *)realloc( z->extra, z->ext + EB_L_UT_SIZE ); } else { l_ef = (char *)malloc( EB_L_UT_SIZE ); z->ext = 0; } if( l_ef == NULL ) { return ZE_MEM; } z->extra = l_ef; l_ef += z->ext; if( z->cextra && z->cext != 0 ) { c_ef = (char *)realloc( z->cextra, z->cext + EB_C_UT_SIZE ); } else { c_ef = (char *)malloc( EB_C_UT_SIZE ); z->cext = 0; } if( c_ef == NULL ) { return ZE_MEM; } z->cextra = c_ef; c_ef += z->cext; /* Now add the local version of the field. */ *l_ef++ = 'U'; *l_ef++ = 'T'; *l_ef++ = (char)(EB_UT_LEN(2)); /* length of data in local EF */ *l_ef++ = (char)0; *l_ef++ = (char)(EB_UT_FL_MTIME | EB_UT_FL_CTIME); *l_ef++ = (char)(z_utim->mtime); *l_ef++ = (char)(z_utim->mtime >> 8); *l_ef++ = (char)(z_utim->mtime >> 16); *l_ef++ = (char)(z_utim->mtime >> 24); *l_ef++ = (char)(z_utim->ctime); *l_ef++ = (char)(z_utim->ctime >> 8); *l_ef++ = (char)(z_utim->ctime >> 16); *l_ef++ = (char)(z_utim->ctime >> 24); z->ext += EB_L_UT_SIZE; /* Now add the central version. */ memcpy(c_ef, l_ef-EB_L_UT_SIZE, EB_C_UT_SIZE); c_ef[EB_LEN] = (char)(EB_UT_LEN(1)); /* length of data in central EF */ z->cext += EB_C_UT_SIZE; return ZE_OK; } #endif /* USE_EF_UT_TIME */ /* * Build and add the old 'Johnny Lee' Mac extra field * All native datas are in Motorola (=big-endian) format */ static int add_JLEE_ef( struct zlist far *z ) { char *l_ef = NULL; char *c_ef = NULL; Assert_it(z, "add_JLEE_ef","") /* Check to make sure we've got enough room in the extra fields. */ if ( z->ext + EB_L_JLEE_SIZE > EF_SIZE_MAX || z->cext + EB_C_JLEE_SIZE > EF_SIZE_MAX ) { return ZE_MEM; } /* Allocate memory for the local extra fields. */ if ( z->extra && z->ext != 0 ) { l_ef = (char *)realloc( z->extra, z->ext + EB_L_JLEE_SIZE ); } else { l_ef = (char *)malloc( EB_L_JLEE_SIZE ); z->ext = 0; } if ( l_ef == NULL ) { return ZE_MEM; } z->extra = l_ef; l_ef += z->ext; /* Allocate memory for the central extra fields. */ if ( z->cextra && z->cext != 0 ) { c_ef = (char *)realloc( z->cextra, z->cext + EB_C_JLEE_SIZE ); } else { c_ef = (char *)malloc( EB_C_JLEE_SIZE ); z->cext = 0; } if ( c_ef == NULL ) { return ZE_MEM; } z->cextra = c_ef; c_ef += z->cext; if ( verbose ) { print_extra_info(); } /** ** ** Now add the local version of the field. **/ make_extrafield_JLEE(l_ef); z->ext += EB_L_JLEE_SIZE; /** ** ** Now add the central version of the field. ** It's identical to the local header. I wonder why ?? * the first two fields are in Intel little-endian format */ make_extrafield_JLEE(c_ef); z->cext += EB_C_JLEE_SIZE; return ZE_OK; } /* * This is an implementation of Johnny Lee's extra field. * I never saw Johnny Lee's code. My code is based on the extra-field * definition mac (see latest appnote 1997-03-11) * and on some experiments with Johnny Lee's Zip-app version 1.0, 1992 * * Unfortunately I cannot agree with his extra-field layout. * - it wasted space * - and holds not all mac-specific information * * I coded this extra-field only for testing purposes. * I don't want support this extra-field. Please use my implementation. * * This is old implementation of Johnny Lee's extra field. * All native datas are in Motorola (=big-endian) format */ static void make_extrafield_JLEE(char *ef) { Assert_it(ef, "make_extrafield_JLEE","") if (MacZip.isMacStatValid == false) { fprintf(stderr,"Internal Logic Error: [%d/%s] MacStat is out of sync !", __LINE__,__FILE__); exit(-1); } /* the first two fields are in Intel little-endian format */ *ef++ = 0xC8; /* tag for this extra block */ *ef++ = 0x07; *ef++ = (char)(EB_L_JLEE_LEN); /* total data size this block */ *ef++ = (char)((EB_L_JLEE_LEN) >> 8); /* the following fields are in motorola big-endian format */ *ef++ = 'J'; /* extra field signature: 4 Bytes */ *ef++ = 'L'; /* the old style extra field */ *ef++ = 'E'; *ef++ = 'E'; /* Start Macintosh Finder FInfo structure 16 Bytes overall */ /* Type: 4 Bytes */ *ef++ = (char)(MacZip.fpb.hFileInfo.ioFlFndrInfo.fdType >> 24); *ef++ = (char)(MacZip.fpb.hFileInfo.ioFlFndrInfo.fdType >> 16); *ef++ = (char)(MacZip.fpb.hFileInfo.ioFlFndrInfo.fdType >> 8); *ef++ = (char)(MacZip.fpb.hFileInfo.ioFlFndrInfo.fdType); /* Creator: 4 Bytes */ *ef++ = (char)(MacZip.fpb.hFileInfo.ioFlFndrInfo.fdCreator >> 24); *ef++ = (char)(MacZip.fpb.hFileInfo.ioFlFndrInfo.fdCreator >> 16); *ef++ = (char)(MacZip.fpb.hFileInfo.ioFlFndrInfo.fdCreator >> 8); *ef++ = (char)(MacZip.fpb.hFileInfo.ioFlFndrInfo.fdCreator); /* file Finder Flags: 2 Bytes */ *ef++ = (char)(MacZip.fpb.hFileInfo.ioFlFndrInfo.fdFlags >> 8); *ef++ = (char)(MacZip.fpb.hFileInfo.ioFlFndrInfo.fdFlags); /* Finders Icon position of a file*/ /* V/Y-Position: 2 Bytes */ *ef++ = (char)(MacZip.fpb.hFileInfo.ioFlFndrInfo.fdLocation.v >> 8); *ef++ = (char)(MacZip.fpb.hFileInfo.ioFlFndrInfo.fdLocation.v); /* H/X-Position: 2 Bytes */ *ef++ = (char)(MacZip.fpb.hFileInfo.ioFlFndrInfo.fdLocation.h >> 8); *ef++ = (char)(MacZip.fpb.hFileInfo.ioFlFndrInfo.fdLocation.h); /* fdFldr Folder containing file 2 Bytes */ *ef++ = (char)(MacZip.fpb.hFileInfo.ioFlFndrInfo.fdFldr >> 8); *ef++ = (char)(MacZip.fpb.hFileInfo.ioFlFndrInfo.fdFldr); /* End Macintosh Finder FInfo structure */ /* Creation-time 4 Bytes */ *ef++ = (char)(MacZip.fpb.hFileInfo.ioFlCrDat >> 24); *ef++ = (char)(MacZip.fpb.hFileInfo.ioFlCrDat >> 16); *ef++ = (char)(MacZip.fpb.hFileInfo.ioFlCrDat >> 8); *ef++ = (char)(MacZip.fpb.hFileInfo.ioFlCrDat); /* Modification-time 4 Bytes */ *ef++ = (char)(MacZip.fpb.hFileInfo.ioFlMdDat >> 24); *ef++ = (char)(MacZip.fpb.hFileInfo.ioFlMdDat >> 16); *ef++ = (char)(MacZip.fpb.hFileInfo.ioFlMdDat >> 8); *ef++ = (char)(MacZip.fpb.hFileInfo.ioFlMdDat); /* info Bits 4 Bytes */ *ef++ = 0x00; *ef++ = 0x00; *ef++ = 0x00; if (MacZip.DataForkOnly) { /* don't convert filename for unzipping */ /* 0x01 = data-fork; 0x00 = resource-fork */ *ef++ = (char) (MacZip.CurrentFork == DataFork) | 2; } else { *ef++ = (char) (MacZip.CurrentFork == DataFork); } /* file's location folder ID 4 Bytes */ *ef++ = (char)(MacZip.fpb.hFileInfo.ioFlParID >> 24); *ef++ = (char)(MacZip.fpb.hFileInfo.ioFlParID >> 16); *ef++ = (char)(MacZip.fpb.hFileInfo.ioFlParID >> 8); *ef++ = (char)(MacZip.fpb.hFileInfo.ioFlParID); /* ============ */ /* 40 Bytes */ } /* * Build and add the new mac extra field * All native data are stored in Intel (=little-endian) format */ static int add_MAC3_ef( struct zlist far *z ) { char *l_ef = NULL; char *c_ef = NULL; char *attrbuff = NULL; off_t attrsize = (EB_L_MAC3_FINFO_LEN + EB_MAX_OF_VARDATA); char *compbuff = NULL; unsigned compsize = 0; unsigned m3_compr; Boolean compress_data = true; Assert_it(z, "add_MAC3_ef","") UserStop(); /* do event handling and let the user stop */ if( verbose ) { print_extra_info(); } /* allocate temporary buffer to collect the Mac extra field info */ attrbuff = (char *)malloc( (size_t)attrsize ); if( attrbuff == NULL ) { return ZE_MEM; } /* fill the attribute buffer, to get its (uncompressed) size */ attrsize = make_extrafield_MAC3(attrbuff); if (compress_data && ((compbuff = (char *)malloc((size_t)attrsize + MEMCOMPRESS_OVERHEAD)) != NULL)) { /* Try compressing the data */ compsize = memcompress( compbuff, (size_t)attrsize + MEMCOMPRESS_OVERHEAD, attrbuff, (size_t)attrsize ); #ifdef MAC_EXTRAFLD_UNCMPR compsize = attrsize; #endif } else { compsize = attrsize; } if ((compsize) < attrsize) { /* compression gained some space ... */ free(attrbuff); /* no longer needed ... */ m3_compr = EB_M3_FL_COMPRESS; } else { /* compression does not help, store data in uncompressed mode */ if (compbuff != NULL) free(compbuff); compbuff = attrbuff; compsize = attrsize; m3_compr = EB_M3_FL_UNCMPR; } /* Check to make sure we've got enough room in the extra fields. */ if( z->ext + (EB_L_MAC3_SIZE + compsize) > EF_SIZE_MAX || z->cext + EB_C_MAC3_SIZE > EF_SIZE_MAX ) { if (compbuff != NULL) free(compbuff); return ZE_MEM; } /* Allocate memory for the local extra fields. */ if( z->extra && z->ext != 0 ) { l_ef = (char *)realloc( z->extra, z->ext + EB_L_MAC3_SIZE + compsize); } else { l_ef = (char *)malloc( EB_L_MAC3_SIZE + compsize); z->ext = 0; } if( l_ef == NULL ) { return ZE_MEM; } z->extra = l_ef; l_ef += z->ext; /* Allocate memory for the central extra fields. */ if( z->cextra && z->cext != 0 ) { c_ef = (char *)realloc( z->cextra, z->cext + EB_C_MAC3_SIZE); } else { c_ef = (char *)malloc( EB_C_MAC3_SIZE ); z->cext = 0; } if( c_ef == NULL ) { return ZE_MEM; } z->cextra = c_ef; c_ef += z->cext; /** ** Now add the local version of the field. **/ l_ef = make_EF_Head_MAC3(l_ef, compsize, (ulg)attrsize, m3_compr); memcpy(l_ef, compbuff, (size_t)compsize); l_ef += compsize; z->ext += EB_L_MAC3_SIZE + compsize; free(compbuff); /* And the central version. */ c_ef = make_EF_Head_MAC3(c_ef, 0, (ulg)attrsize, m3_compr); z->cext += EB_C_MAC3_SIZE; return ZE_OK; } /* * Build the new mac local extra field header. * It's identical with the central extra field. * All native data are in Intel (=little-endian) format */ static char *make_EF_Head_MAC3(char *ef, unsigned compsize, ulg attrsize, unsigned flag) { unsigned info_flag = flag; Assert_it(ef, "make_EF_Head_MAC3","") /* the first four fields are in Intel little-endian format */ *ef++ = 'M'; /* tag for this extra block 2 Bytes */ *ef++ = '3'; /* total data size this block 2 Bytes */ *ef++ = (char) (EB_MAC3_HLEN + compsize); *ef++ = (char)((EB_MAC3_HLEN + compsize) >> 8); *ef++ = (char)(attrsize); *ef++ = (char)(attrsize >> 8); *ef++ = (char)(attrsize >> 16); *ef++ = (char)(attrsize >> 24); /* info Bits (flags) 2 Bytes */ if (MacZip.DataForkOnly) info_flag |= (EB_M3_FL_DATFRK | EB_M3_FL_NOCHANGE); if (MacZip.CurrentFork == DataFork) info_flag |= EB_M3_FL_DATFRK; if (!MacZip.HaveGMToffset) info_flag |= EB_M3_FL_NOUTC; *ef++ = (char)info_flag; *ef++ = (char)0x00; /* reserved at the moment */ /* Note: Apple defined File-Type/-Creator as OSType ( =unsigned long, see Universal Headers 3.1). However, File-Type/-Creator are a unique four-character sequence. Therefore the byteorder of the File-Type/-Creator are NOT changed. The native format is used. */ /* Type: 4 Bytes */ *ef++ = (char)(MacZip.fpb.hFileInfo.ioFlFndrInfo.fdType >> 24); *ef++ = (char)(MacZip.fpb.hFileInfo.ioFlFndrInfo.fdType >> 16); *ef++ = (char)(MacZip.fpb.hFileInfo.ioFlFndrInfo.fdType >> 8); *ef++ = (char)(MacZip.fpb.hFileInfo.ioFlFndrInfo.fdType); /* Creator: 4 Bytes */ *ef++ = (char)(MacZip.fpb.hFileInfo.ioFlFndrInfo.fdCreator >> 24); *ef++ = (char)(MacZip.fpb.hFileInfo.ioFlFndrInfo.fdCreator >> 16); *ef++ = (char)(MacZip.fpb.hFileInfo.ioFlFndrInfo.fdCreator >> 8); *ef++ = (char)(MacZip.fpb.hFileInfo.ioFlFndrInfo.fdCreator); return ef; } /* * Build the new mac local extra field header. * All native data are in Intel (=little-endian) format */ unsigned make_extrafield_MAC3(char *ef) { char *ef_m3_begin = ef; char *temp_Pathname; char tmp_buffer[NAME_MAX]; unsigned char comment[257]; unsigned short FLength = 0; unsigned short CLength = 0; short tempFork; OSErr err; Assert_it(ef, "make_extrafield_MAC3","") if (MacZip.isMacStatValid == false) { fprintf(stderr, "Internal Logic Error: [%d/%s] MacStat is out of sync !", __LINE__, __FILE__); exit(-1); } /* Start Macintosh Finder FInfo structure except Type/Creator (see make_EF_Head_MAC3()) 8 Bytes overall */ /* file Finder Flags: 2 Bytes */ *ef++ = (char)(MacZip.fpb.hFileInfo.ioFlFndrInfo.fdFlags); *ef++ = (char)(MacZip.fpb.hFileInfo.ioFlFndrInfo.fdFlags >> 8); /* Finders Icon position of a file*/ /* V/Y-Position: 2 Bytes */ *ef++ = (char)(MacZip.fpb.hFileInfo.ioFlFndrInfo.fdLocation.v); *ef++ = (char)(MacZip.fpb.hFileInfo.ioFlFndrInfo.fdLocation.v >> 8); /* H/X-Position: 2 Bytes */ *ef++ = (char)(MacZip.fpb.hFileInfo.ioFlFndrInfo.fdLocation.h); *ef++ = (char)(MacZip.fpb.hFileInfo.ioFlFndrInfo.fdLocation.h >> 8); /* fdFldr Folder containing file 2 Bytes */ *ef++ = (char)(MacZip.fpb.hFileInfo.ioFlFndrInfo.fdFldr); *ef++ = (char)(MacZip.fpb.hFileInfo.ioFlFndrInfo.fdFldr >> 8); /* End Macintosh Finder FInfo structure */ /* 8 Bytes so far ... */ /* Start Macintosh Finder FXInfo structure 16 Bytes overall */ /* Icon ID: 2 Bytes */ *ef++ = (char)(MacZip.fpb.hFileInfo.ioFlXFndrInfo.fdIconID); *ef++ = (char)(MacZip.fpb.hFileInfo.ioFlXFndrInfo.fdIconID >> 8); /* unused: 6 Bytes */ *ef++ = (char)(MacZip.fpb.hFileInfo.ioFlXFndrInfo.fdUnused[0]); *ef++ = (char)(MacZip.fpb.hFileInfo.ioFlXFndrInfo.fdUnused[0] >> 8); *ef++ = (char)(MacZip.fpb.hFileInfo.ioFlXFndrInfo.fdUnused[1]); *ef++ = (char)(MacZip.fpb.hFileInfo.ioFlXFndrInfo.fdUnused[1] >> 8); *ef++ = (char)(MacZip.fpb.hFileInfo.ioFlXFndrInfo.fdUnused[2]); *ef++ = (char)(MacZip.fpb.hFileInfo.ioFlXFndrInfo.fdUnused[2] >> 8); /* Script flag: 1 Byte */ *ef++ = (char)(MacZip.fpb.hFileInfo.ioFlXFndrInfo.fdScript); /* More flag bits: 1 Byte */ *ef++ = (char)(MacZip.fpb.hFileInfo.ioFlXFndrInfo.fdXFlags); /* Comment ID 2 Bytes */ *ef++ = (char)(MacZip.fpb.hFileInfo.ioFlXFndrInfo.fdComment); *ef++ = (char)(MacZip.fpb.hFileInfo.ioFlXFndrInfo.fdComment >> 8); /* Home Dir ID: 4 Bytes */ *ef++ = (char)(MacZip.fpb.hFileInfo.ioFlXFndrInfo.fdPutAway); *ef++ = (char)(MacZip.fpb.hFileInfo.ioFlXFndrInfo.fdPutAway >> 8); *ef++ = (char)(MacZip.fpb.hFileInfo.ioFlXFndrInfo.fdPutAway >> 16); *ef++ = (char)(MacZip.fpb.hFileInfo.ioFlXFndrInfo.fdPutAway >> 24); /* End Macintosh Finder FXInfo structure */ /* 24 Bytes so far ... */ /* file version number 1 Byte */ *ef++ = (char)(MacZip.fpb.hFileInfo.ioFVersNum); /* directory access rights 1 Byte */ *ef++ = (char)(MacZip.fpb.hFileInfo.ioACUser); /* Creation-time 4 Bytes */ *ef++ = (char)(MacZip.fpb.hFileInfo.ioFlCrDat); *ef++ = (char)(MacZip.fpb.hFileInfo.ioFlCrDat >> 8); *ef++ = (char)(MacZip.fpb.hFileInfo.ioFlCrDat >> 16); *ef++ = (char)(MacZip.fpb.hFileInfo.ioFlCrDat >> 24); /* Modification-time 4 Bytes */ *ef++ = (char)(MacZip.fpb.hFileInfo.ioFlMdDat); *ef++ = (char)(MacZip.fpb.hFileInfo.ioFlMdDat >> 8); *ef++ = (char)(MacZip.fpb.hFileInfo.ioFlMdDat >> 16); *ef++ = (char)(MacZip.fpb.hFileInfo.ioFlMdDat >> 24); /* Backup-time 4 Bytes */ *ef++ = (char)(MacZip.fpb.hFileInfo.ioFlBkDat); *ef++ = (char)(MacZip.fpb.hFileInfo.ioFlBkDat >> 8); *ef++ = (char)(MacZip.fpb.hFileInfo.ioFlBkDat >> 16); *ef++ = (char)(MacZip.fpb.hFileInfo.ioFlBkDat >> 24); /* 38 Bytes so far ... */ #ifdef USE_EF_UT_TIME if (MacZip.HaveGMToffset) { /* GMT-Offset times 12 Bytes */ *ef++ = (char)(MacZip.Cr_UTCoffs); *ef++ = (char)(MacZip.Cr_UTCoffs >> 8); *ef++ = (char)(MacZip.Cr_UTCoffs >> 16); *ef++ = (char)(MacZip.Cr_UTCoffs >> 24); *ef++ = (char)(MacZip.Md_UTCoffs); *ef++ = (char)(MacZip.Md_UTCoffs >> 8); *ef++ = (char)(MacZip.Md_UTCoffs >> 16); *ef++ = (char)(MacZip.Md_UTCoffs >> 24); *ef++ = (char)(MacZip.Bk_UTCoffs); *ef++ = (char)(MacZip.Bk_UTCoffs >> 8); *ef++ = (char)(MacZip.Bk_UTCoffs >> 16); *ef++ = (char)(MacZip.Bk_UTCoffs >> 24); } /* 50 Bytes so far ... */ #endif /* Text Encoding Base (charset) 2 Bytes */ *ef++ = (char)(MacZip.CurrTextEncodingBase); *ef++ = (char)(MacZip.CurrTextEncodingBase >> 8); /* 52 Bytes so far ... */ /* MacZip.CurrentFork will be changed, so we have to save it */ tempFork = MacZip.CurrentFork; if (!MacZip.StoreFullPath) { temp_Pathname = StripPartialDir(tmp_buffer, MacZip.SearchDir, MacZip.FullPath); } else { temp_Pathname = MacZip.FullPath; } MacZip.CurrentFork = tempFork; FLength = strlen(temp_Pathname) + 1; memcpy( ef, temp_Pathname, (size_t)FLength ); ef += FLength; /* make room for the string - variable length */ err = FSpLocationFromFullPath(strlen(MacZip.FullPath), MacZip.FullPath, &MacZip.fileSpec); printerr("FSpLocationFromFullPath:", err, err, __LINE__, __FILE__, tmp_buffer); err = FSpDTGetComment(&MacZip.fileSpec, comment); printerr("FSpDTGetComment:", (err != -5012) && (err != 0), err, __LINE__, __FILE__, ""); PToCCpy(comment,tmp_buffer); CLength = strlen(tmp_buffer) + 1; memcpy( ef, tmp_buffer, (size_t)CLength ); ef += CLength; /* make room for the string - variable length */ if (verbose) printf("\n comment: [%s]", tmp_buffer); return (unsigned)(ef - ef_m3_begin); } /* * Print all native data of the new mac local extra field. * It's for debugging purposes and disabled by default. */ static void PrintFileInfo(void) { DateTimeRec MacTime; printf("\n\n---------------------------------------------"\ "----------------------------------"); printf("\n FullPath Name = [%s]", MacZip.FullPath); printf("\n File Attributes = %s 0x%x %d", sBit2Str(MacZip.fpb.hFileInfo.ioFlAttrib), MacZip.fpb.hFileInfo.ioFlAttrib, MacZip.fpb.hFileInfo.ioFlAttrib); printf("\n Enclosing Folder ID# = 0x%x %d", MacZip.fpb.hFileInfo.ioFlParID, MacZip.fpb.hFileInfo.ioFlParID); if (!MacZip.isDirectory) { printf("\n File Type = [%c%c%c%c] 0x%lx", MacZip.fpb.hFileInfo.ioFlFndrInfo.fdType >> 24, MacZip.fpb.hFileInfo.ioFlFndrInfo.fdType >> 16, MacZip.fpb.hFileInfo.ioFlFndrInfo.fdType >> 8, MacZip.fpb.hFileInfo.ioFlFndrInfo.fdType, MacZip.fpb.hFileInfo.ioFlFndrInfo.fdType); printf("\n File Creator = [%c%c%c%c] 0x%lx", MacZip.fpb.hFileInfo.ioFlFndrInfo.fdCreator >> 24, MacZip.fpb.hFileInfo.ioFlFndrInfo.fdCreator >> 16, MacZip.fpb.hFileInfo.ioFlFndrInfo.fdCreator >> 8, MacZip.fpb.hFileInfo.ioFlFndrInfo.fdCreator, MacZip.fpb.hFileInfo.ioFlFndrInfo.fdCreator); printf("\n Data Fork :" ); printf("\n Actual (Logical) Length = %d 0x%x ", MacZip.fpb.hFileInfo.ioFlLgLen, MacZip.fpb.hFileInfo.ioFlLgLen); printf("\n Allocated (Physical) Length = %d 0x%x", MacZip.fpb.hFileInfo.ioFlPyLen, MacZip.fpb.hFileInfo.ioFlPyLen); printf("\n Resource Fork :" ); printf("\n Actual (Logical) Length = %d 0x%x", MacZip.fpb.hFileInfo.ioFlRLgLen, MacZip.fpb.hFileInfo.ioFlRLgLen ); printf("\n Allocated (Physical) Length = %d 0x%x", MacZip.fpb.hFileInfo.ioFlRPyLen, MacZip.fpb.hFileInfo.ioFlRPyLen ); } printf("\n Dates : "); SecondsToDate (MacZip.CreatDate, &MacTime); printf("\n Created = %4d/%2d/%2d %2d:%2d:%2d ", MacTime.year, MacTime.month, MacTime.day, MacTime.hour, MacTime.minute, MacTime.second); SecondsToDate (MacZip.BackDate, &MacTime); printf("\n Backup = %4d/%2d/%2d %2d:%2d:%2d ", MacTime.year, MacTime.month, MacTime.day, MacTime.hour, MacTime.minute, MacTime.second); SecondsToDate (MacZip.ModDate, &MacTime); printf("\n Modified = %4d/%2d/%2d %2d:%2d:%2d ", MacTime.year, MacTime.month, MacTime.day, MacTime.hour, MacTime.minute, MacTime.second); if (!MacZip.isDirectory) { printf("\n Finder Flags : %s 0x%x %d", sBit2Str(MacZip.fpb.hFileInfo.ioFlFndrInfo.fdFlags), MacZip.fpb.hFileInfo.ioFlFndrInfo.fdFlags, MacZip.fpb.hFileInfo.ioFlFndrInfo.fdFlags); printf("\n Finder Icon Position = X: %d 0x%x ", MacZip.fpb.hFileInfo.ioFlFndrInfo.fdLocation.h, MacZip.fpb.hFileInfo.ioFlFndrInfo.fdLocation.h); printf("\n Y: %d 0x%x ", MacZip.fpb.hFileInfo.ioFlFndrInfo.fdLocation.v, MacZip.fpb.hFileInfo.ioFlFndrInfo.fdLocation.v); } else { printf("\n Finder Flags : %s 0x%x %d", sBit2Str(MacZip.fpb.dirInfo.ioDrUsrWds.frFlags), MacZip.fpb.dirInfo.ioDrUsrWds.frFlags, MacZip.fpb.dirInfo.ioDrUsrWds.frFlags); printf("\n Finder Icon Position = X: %d 0x%x ", MacZip.fpb.dirInfo.ioDrUsrWds.frLocation.h, MacZip.fpb.dirInfo.ioDrUsrWds.frLocation.h); printf("\n Y: %d 0x%x ", MacZip.fpb.dirInfo.ioDrUsrWds.frLocation.v, MacZip.fpb.dirInfo.ioDrUsrWds.frLocation.v); } printf("\n----------------------------------------------------"\ "---------------------------\n"); } /* * If the switch '-v' is used, print some more info. */ static void print_extra_info(void) { char Fork[20]; if (MacZip.CurrentFork == DataFork) sstrcpy(Fork,""); else sstrcpy(Fork,""); printf("\n%16s [%c%c%c%c] [%c%c%c%c]",Fork, MacZip.fpb.hFileInfo.ioFlFndrInfo.fdType >> 24, MacZip.fpb.hFileInfo.ioFlFndrInfo.fdType >> 16, MacZip.fpb.hFileInfo.ioFlFndrInfo.fdType >> 8, MacZip.fpb.hFileInfo.ioFlFndrInfo.fdType, MacZip.fpb.hFileInfo.ioFlFndrInfo.fdCreator >> 24, MacZip.fpb.hFileInfo.ioFlFndrInfo.fdCreator >> 16, MacZip.fpb.hFileInfo.ioFlFndrInfo.fdCreator >> 8, MacZip.fpb.hFileInfo.ioFlFndrInfo.fdCreator); } zip30/macos/source/getenv.c0100644000076400000060000002223310154332006014013 0ustar edisk/* Copyright (c) 1990-2000 Info-ZIP. All rights reserved. See the accompanying file LICENSE, version 2000-Apr-09 or later (the contents of which are also included in zip.h) for terms of use. If, for some reason, all these files are missing, the Info-ZIP license also may be found at: ftp://ftp.info-zip.org/pub/infozip/license.html */ /* This file implements the getenv() function. # Background: # Under Unix: Each Process (= running Program) has a set of # associated variables. The variables are called enviroment # variables and, together, constitute the process environment. # These variables include the search path, the terminal type, # and the user's login name. # Unfortunatelly the MacOS has no equivalent. So we need # a file to define the environment variables. # Name of this file is "MacZip.Env". It can be placed # in the current folder of MacZip or in the # preference folder of the system disk. # If MacZip founds the "MacZip.Env" file in the current # the folder of MacZip the "MacZip.Env" file in the # preference folder will be ignored. # An environment variable has a name and a value: # Name=Value # Note: Spaces are significant: # ZIPOPT=-r and # ZIPOPT = -r are different !!! */ /*****************************************************************************/ /* Includes */ /*****************************************************************************/ #include #include #include #include #include #include #include #include "pathname.h" #include "helpers.h" /*****************************************************************************/ /* Module level Vars */ /*****************************************************************************/ static char ListAllKeyValues = 0; static unsigned LineNumber = 0; static char CompletePath[NAME_MAX]; Boolean IgnoreEnvironment = false; /* used by dialog.c and initfunc.c of the Mainapp */ /*****************************************************************************/ /* Macros, typedefs */ /*****************************************************************************/ typedef struct _EnviromentPair { char *key; char *value; } EnviromentPair; #define MAX_COMMAND 1024 /*****************************************************************************/ /* Prototypes */ /*****************************************************************************/ int get_char(FILE *file); void unget_char(int ch,FILE *file); int get_string(char *string,int size, FILE *file, char *terms); void skip_comments(FILE *file); char *load_entry(FILE *file); char *getenv(const char *name); EnviromentPair *ParseLine(char *line); OSErr FSpFindFolder_Name(short vRefNum, OSType folderType, Boolean createFolder,FSSpec *spec, unsigned char *name); FILE * FSp_fopen(ConstFSSpecPtr spec, const char * open_mode); void ShowAllKeyValues(void); void Set_LineNum(unsigned ln); /*****************************************************************************/ /* Functions */ /*****************************************************************************/ /* get_string(str, max, file, termstr) : like fgets() but * (1) has terminator string which should include \n * (2) will always leave room for the null * (3) uses get_char() so LineNumber will be accurate * (4) returns EOF or terminating character, whichever */ int get_string(char *string, int size, FILE *file, char *terms) { int ch; while (EOF != (ch = get_char(file)) && !strchr(terms, ch)) { if (size > 1) { *string++ = (char) ch; size--; } } if (size > 0) { *string = '\0'; } return ch; } void Set_LineNum(unsigned ln) { LineNumber = ln; } /* get_char(file) : like getc() but increment LineNumber on newlines */ int get_char(FILE *file) { int ch; ch = getc(file); if (ch == '\n') { Set_LineNum(LineNumber + 1); } return ch; } /* skip_comments(file) : read past comment (if any) */ void skip_comments(FILE *file) { int ch; while (EOF != (ch = get_char(file))) { /* ch is now the first character of a line. */ while (ch == ' ' || ch == '\t') { ch = get_char(file); } if (ch == EOF) { break; } /* ch is now the first non-blank character of a line. */ if (ch != '\n' && ch != '#') { break; } /* ch must be a newline or comment as first non-blank * character on a line. */ while (ch != '\n' && ch != EOF) { ch = get_char(file); } /* ch is now the newline of a line which we're going to * ignore. */ } if (ch != EOF) { unget_char(ch, file); } } /* unget_char(ch, file) : like ungetc but do LineNumber processing */ void unget_char(int ch, FILE *file) { ungetc(ch, file); if (ch == '\n') { Set_LineNum(LineNumber - 1); } } /* this function reads one file entry -- the next -- from a file. * it skips any leading blank lines, ignores comments, and returns * NULL if for any reason the entry can't be read and parsed. */ char *load_entry(FILE *file) { int ch; static char cmd[MAX_COMMAND]; skip_comments(file); ch = get_string(cmd, MAX_COMMAND, file, "\n"); if (ch == EOF) { return NULL; } return cmd; } EnviromentPair *ParseLine(char *line) { char *tmpPtr; static EnviromentPair *Env; unsigned short length = strlen(line); Env->key = ""; Env->value = ""; for (tmpPtr = line; *tmpPtr; tmpPtr++) { if (*tmpPtr == '=') { *tmpPtr = 0; Env->key = line; if (strlen(Env->key) < length) { Env->value = ++tmpPtr; } return Env; } } return Env; } char *getenv(const char *name) { FILE *fp; char *LineStr = NULL; EnviromentPair *Env1; FSSpec spec; OSErr err; if (IgnoreEnvironment) return NULL; /* user wants to ignore the environment vars */ if (name == NULL) return NULL; GetCompletePath(CompletePath,"MacZip.Env",&spec,&err); /* try open the file in the current folder */ fp = FSp_fopen(&spec,"r"); if (fp == NULL) { /* Okey, lets try open the file in the preference folder */ FSpFindFolder_Name( kOnSystemDisk, kPreferencesFolderType, kDontCreateFolder, &spec, "\pMacZip.Env"); fp = FSp_fopen(&spec,"r"); if (fp == NULL) { return NULL; /* there is no enviroment-file */ } } LineStr = load_entry(fp); while (LineStr != NULL) { /* parse the file line by line */ Env1 = ParseLine(LineStr); if (strlen(Env1->value) > 0) { /* we found a key/value pair */ if (ListAllKeyValues) printf("\n Line:%3d [%s] = [%s]",LineNumber,Env1->key,Env1->value); if (stricmp(name,Env1->key) == 0) { /* we found the value of a given key */ return Env1->value; } } LineStr = load_entry(fp); /* read next line */ } fclose(fp); return NULL; } OSErr FSpFindFolder_Name( short vRefNum, /* Volume reference number. */ OSType folderType, /* Folder type taken by FindFolder. */ Boolean createFolder, /* Should we create it if non-existant. */ FSSpec *spec, /* Pointer to resulting directory. */ unsigned char *name) /* Name of the file in the folder */ { short foundVRefNum; long foundDirID; OSErr err; err = FindFolder(vRefNum, folderType, createFolder, &foundVRefNum, &foundDirID); if (err != noErr) { return err; } err = FSMakeFSSpec(foundVRefNum, foundDirID, name, spec); return err; } void ShowAllKeyValues(void) { OSErr err; FSSpec spec; Boolean tmpIgnoreEnvironment = IgnoreEnvironment; ListAllKeyValues = 1; IgnoreEnvironment = false; GetCompletePath(CompletePath,"MacZip.Env",&spec,&err); if (err != 0) { /* Okey, lets try open the file in the preference folder */ FSpFindFolder_Name( kOnSystemDisk, kPreferencesFolderType, kDontCreateFolder, &spec, "\pMacZip.Env"); GetFullPathFromSpec(CompletePath,&spec, &err); if (err != 0) { return; /* there is no enviroment-file */ } } printf("\nLocation of the current \"MacZip.Env\" file:\n [%s]",CompletePath); printf("\n\nList of all environment variables\n"); getenv(" "); printf("\n\nEnd\n\n"); /* restore used variables */ ListAllKeyValues = 0; LineNumber = 0; IgnoreEnvironment = tmpIgnoreEnvironment; } zip30/macos/source/helpers.c0100644000076400000060000002264710154332006014176 0ustar edisk/* Copyright (c) 1990-2001 Info-ZIP. All rights reserved. See the accompanying file LICENSE, version 2000-Apr-09 or later (the contents of which are also included in zip.h) for terms of use. If, for some reason, all these files are missing, the Info-ZIP license also may be found at: ftp://ftp.info-zip.org/pub/infozip/license.html */ /*--------------------------------------------------------------------------- helpers.c Some useful functions Used by unzip and zip. ---------------------------------------------------------------------------*/ /*****************************************************************************/ /* Includes */ /*****************************************************************************/ #include "zip.h" #include #include #include #include "macstuff.h" #include "helpers.h" #include "pathname.h" /*****************************************************************************/ /* Global Vars */ /*****************************************************************************/ extern int noisy; extern char MacPathEnd; extern char *zipfile; /* filename of the Zipfile */ extern char *tempzip; /* Temporary zip file name */ extern ZCONST unsigned char MacRoman_to_WinCP1252[128]; static char argStr[1024]; static char *argv[MAX_ARGS + 1]; /*****************************************************************************/ /* Functions */ /*****************************************************************************/ /* ** Copy a C string to a Pascal string ** */ unsigned char *CToPCpy(unsigned char *pstr, char *cstr) { register char *dptr; register unsigned len; len=0; dptr=(char *)pstr+1; while (len<255 && (*dptr++ = *cstr++)!='\0') ++len; *pstr= (unsigned char)len; return pstr; } /* ** Copy a Pascal string to a C string ** */ char *PToCCpy(unsigned char *pstr, char *cstr) { strncpy(cstr, (char *) &pstr[1], *pstr); cstr[pstr[0]] = '\0'; /* set endmarker for c-string */ return cstr; } /* ** strcpy() and strcat() work-alikes which allow overlapping buffers. */ char *sstrcpy(char *to,const char *from) { memmove(to, from, 1+strlen(from)); return to; } char *sstrcat(char *to,const char *from) { sstrcpy(to + strlen(to), from); return to; } /* ** Alloc memory and init it ** */ char *StrCalloc(unsigned short size) { char *strPtr = NULL; if ((strPtr = calloc(size, sizeof(char))) == NULL) printerr("StrCalloc failed:", -1, size, __LINE__, __FILE__, ""); Assert_it(strPtr,"strPtr == NULL","") return strPtr; } /* ** Release only non NULL pointers ** */ char *StrFree(char *strPtr) { if (strPtr != NULL) { free(strPtr); } return NULL; } /* ** Return a value in a binary string ** */ char *sBit2Str(unsigned short value) { static char str[sizeof(value)*8]; int biz = 16; int strwid = 16; int i, j; char *tempPtr = str; j = strwid - (biz + (biz >> 2)- (biz % 4 ? 0 : 1)); for (i = 0; i < j; i++) { *tempPtr++ = ' '; } while (--biz >= 0) { *tempPtr++ = ((value >> biz) & 1) + '0'; if (!(biz % 4) && biz) { *tempPtr++ = ' '; } } *tempPtr = '\0'; return str; } /* ** Parse commandline style arguments ** */ int ParseArguments(char *s, char ***arg) { int n = 1, Quote = 0; char *p = s, *p1, c; argv[0] = GetAppName(); *arg = argv; p1 = (char *) argStr; while ((c = *p++) != 0) { if (c==' ') continue; argv[n++] = p1; if (n > MAX_ARGS) return (n-1); do { if (c=='\\' && *p++) c = *p++; else if ((c=='"') || (c == '\'')) { if (!Quote) { Quote = c; continue; } if (c == Quote) { Quote = 0; continue; } } *p1++ = c; } while (*p && ((c = *p++) != ' ' || Quote)); *p1++ = '\0'; } return n; } /* ** Print commandline style arguments ** */ void PrintArguments(int argc, char **argv) { printf("\n Arguments:"); printf("\n --------------------------"); while(--argc >= 0) printf("\n argc: %d argv: [%s]", argc, &*argv[argc]); printf("\n --------------------------\n\n"); return; } /* ** return some error-msg on file-system ** */ int PrintUserHFSerr(int cond, int err, char *msg2) { char *msg; if (cond != 0) { switch (err) { case -35: msg = "No such Volume"; break; case -56: msg = "No such Drive"; break; case -37: msg = "Bad Volume Name"; break; case -49: msg = "File is already open for writing"; break; case -43: msg = "Directory/File not found"; break; case -120: msg = "Directory/File not found or incomplete pathname"; break; default: return err; } fprintf(stderr, "\n\n Error: %s ->%s", msg, msg2); exit(err); } return 0; } /* ** Check mounted volumes and return number of volumes ** with the same name. */ short CheckMountedVolumes(char *FullPath) { FSSpec volumes[50]; /* 50 Volumes should be enough */ char VolumeName[257], volume[257]; short actVolCount, volIndex = 1, VolCount = 0; OSErr err; int i; GetVolumeFromPath(FullPath, VolumeName); err = OnLine(volumes, 50, &actVolCount, &volIndex); printerr("OnLine:", (err != -35) && (err != 0), err, __LINE__, __FILE__, ""); for (i=0; i < actVolCount; i++) { PToCCpy(volumes[i].name,volume); if (stricmp(volume, VolumeName) == 0) VolCount++; } printerr("OnLine: ", (VolCount == 0), VolCount, __LINE__, __FILE__, FullPath); return VolCount; } /* ** compares strings, ignoring differences in case ** */ int stricmp(const char *p1, const char *p2) { int diff; while (*p1 && *p2) { if (*p1 != *p2) { if (isalpha(*p1) && isalpha(*p2)) { diff = toupper(*p1) - toupper(*p2); if (diff) return diff; } else break; } p1++; p2++; } return *p1 - *p2; } /* ** Convert the MacOS-Strings (Filenames/Findercomments) to a most compatible. ** These strings will be stored in the public area of the zip-archive. ** Every foreign platform (outside macos) will access these strings ** for extraction. */ void MakeCompatibleString(char *MacOS_Str, const char SpcChar1, const char SpcChar2, const char SpcChar3, const char SpcChar4, short CurrTextEncodingBase) { char *tmpPtr; register uch curch; Assert_it(MacOS_Str,"MakeCompatibleString MacOS_Str == NULL","") for (tmpPtr = MacOS_Str; (curch = *tmpPtr) != '\0'; tmpPtr++) { if (curch == SpcChar1) *tmpPtr = SpcChar2; else if (curch == SpcChar3) *tmpPtr = SpcChar4; else /* default */ /* now convert from MacRoman to ISO-8859-1 */ /* but convert only if MacRoman is activ */ if ((CurrTextEncodingBase == kTextEncodingMacRoman) && (curch > 127)) { *tmpPtr = (char)MacRoman_to_WinCP1252[curch - 128]; } } /* end for */ } Boolean CheckForSwitch(char *Switch, int argc, char **argv) { char *p; /* steps through option arguments */ int i; /* arg counter, root directory flag */ for (i = 1; i < argc; i++) { if (argv[i][0] == '-') { if (argv[i][1]) { for (p = argv[i]+1; *p; p++) { if (*p == Switch[0]) { return true; } if ((Switch[1] != NULL) && ((*p == Switch[0]) && (*p == Switch[1]))) { return true; } } } } } return false; } #if (defined(USE_SIOUX) || defined(MACUNZIP_STANDALONE)) /* ** checks the condition and returns an error-msg ** this function is for internal use only */ OSErr printerr(const char *msg, int cond, int err, int line, char *file, const char *msg2) { if (cond != 0) { fprintf(stderr, "\nint err: %d: %s %d [%d/%s] {%s}\n", clock(), msg, err, line, file, msg2); } return cond; } /* fake-functions: Not Implemented for metrowerks SIOUX */ void leftStatusString(char *status) { status = status; } void rightStatusString(char *status) { status = status; } void DoWarnUserDupVol( char *FullPath ) { char VolName[257]; GetVolumeFromPath(FullPath, VolName); printf("\n There are more than one volume that has the same name !!\n"); printf("\n Volume: %s\n",VolName); printf("\n This port has one weak point:"); printf("\n It is based on pathnames. As you may be already know:"); printf("\n Pathnames are not unique on a Mac !"); printf("\n MacZip has problems to find the correct location of"); printf("\n the archive or the files.\n"); printf("\n My (Big) recommendation: Name all your volumes with an"); printf("\n unique name and MacZip will run without any problem."); } #endif zip30/macos/source/helpers.h0100644000076400000060000000327707251360600014206 0ustar edisk/* Copyright (c) 1990-2001 Info-ZIP. All rights reserved. See the accompanying file LICENSE, version 2000-Apr-09 or later (the contents of which are also included in zip.h) for terms of use. If, for some reason, all these files are missing, the Info-ZIP license also may be found at: ftp://ftp.info-zip.org/pub/infozip/license.html */ #ifndef HELPERS_H #define HELPERS_H 1 /* Convert a C string to a Pascal string */ unsigned char *CToPCpy(unsigned char *pstr, char *cstr); /* Convert a Pascal string to a C string */ char *PToCCpy(unsigned char *pstr, char *cstr); char *sstrcpy(char *to,const char *from); char *sstrcat(char *to,const char *from); char *StrCalloc(unsigned short size); char *StrFree(char *strPtr); char *sBit2Str(unsigned short value); void print_extra_info(void); int ParseArguments(char *s, char ***arg); void PrintArguments(int argc, char **argv); Boolean IsZipFile(char *name); OSErr printerr(const char *msg, int cond, int err, int line, char *file, const char *msg2); int PrintUserHFSerr(int cond, int err, char *msg2); short CheckMountedVolumes(char *FullPath); void DoWarnUserDupVol(char *path); void PrintFileInfo(void); int stricmp(const char *p1, const char *p2); void leftStatusString(char *status); void rightStatusString(char *status); Boolean isZipFile(FSSpec *fileToOpen); unsigned long MacFileDate_to_UTime(unsigned long mactime); Boolean CheckForSwitch(char *Switch, int argc, char **argv); void MakeCompatibleString(char *MacOS_Str, const char SpcChar1, const char SpcChar2, const char SpcChar3, const char SpcChar4, short CurrTextEncodingBase); #define MAX_ARGS 25 #endif /* HELPERS_H */ zip30/macos/source/macglob.h0100644000076400000060000000434107011111152014127 0ustar edisk/* Copyright (c) 1990-1999 Info-ZIP. All rights reserved. See the accompanying file LICENSE, version 1999-Oct-05 or later (the contents of which are also included in zip.h) for terms of use. If, for some reason, both of these files are missing, the Info-ZIP license also may be found at: ftp://ftp.cdrom.com/pub/infozip/license.html */ #ifndef _MACGLOBAL_ #define _MACGLOBAL_ #include /* all my Global vars are defined here. */ #define ResourceFork -1 #define DataFork 1 #define NoFork 0 /* all my Global vars are defined here. */ typedef struct { short CurrentFork; short MacZipMode; Boolean isMacStatValid; Boolean HaveGMToffset; short CurrTextEncodingBase; /* info about the current file */ Boolean isDirectory; char FullPath[NAME_MAX]; char FileName[NAME_MAX]; FSSpec fileSpec; long dirID; CInfoPBRec fpb; /* time infos about the current file */ time_t CreatDate; time_t ModDate; time_t BackDate; long Cr_UTCoffs; /* offset "local time - UTC" for CreatDate */ long Md_UTCoffs; /* offset "local time - UTC" for ModDate */ long Bk_UTCoffs; /* offset "local time - UTC" for BackDate */ /* some statistics over all*/ unsigned long FoundFiles; unsigned long FoundDirectories; unsigned long RawCountOfItems; unsigned long BytesOfData; unsigned long attrsize; /* some switches and user parameters */ Boolean DataForkOnly; Boolean StoreFullPath; Boolean StoreFoldersAlso; /* internal switch is true if '-r' is set */ unsigned short SearchLevels; char Pattern[NAME_MAX]; Boolean IncludeInvisible; Boolean StatingProgress; char SearchDir[NAME_MAX]; char CurrentPath[NAME_MAX]; /* current zip / tempzip file info */ char ZipFullPath[NAME_MAX]; FSSpec ZipFileSpec; unsigned long ZipFileType; char TempZipFullPath[NAME_MAX]; FSSpec TempZipFileSpec; } MacZipGlobals; void UserStop(void); #endif zip30/macos/source/macopen.c0100644000076400000060000002312610154332006014147 0ustar edisk/* Copyright (c) 1990-1999 Info-ZIP. All rights reserved. See the accompanying file LICENSE, version 1999-Oct-05 or later (the contents of which are also included in zip.h) for terms of use. If, for some reason, both of these files are missing, the Info-ZIP license also may be found at: ftp://ftp.cdrom.com/pub/infozip/license.html */ /*** macopen.c; stuff only required for the Mac port ***/ #include "zip.h" #include #include #include #include #include "helpers.h" #include "pathname.h" #include "macopen.h" #include "macstuff.h" #ifdef MACZIP #include "macglob.h" extern char *zipfile; /* filename of the Zipfile */ extern char *tempzip; /* Temporary zip file name */ extern MacZipGlobals MacZip; /* don't include "osdep.h" otherwise we will trap into endless loop */ #undef open #undef fopen FILE *MacFopen(const char *path, const char *mode) { static char TruncPath[NAME_MAX]; OSErr err = 0; AssertStr(path,path) /* open zipfile or tempzip */ if (strcmp(zipfile,path) == 0) { GetCompletePath(MacZip.ZipFullPath,path,&MacZip.ZipFileSpec,&err); err = PrintUserHFSerr((err != -43) && (err != 0), err, path); printerr("GetCompletePath:",err,err,__LINE__,__FILE__,path); if (CheckMountedVolumes(MacZip.ZipFullPath) > 1) DoWarnUserDupVol(MacZip.ZipFullPath); /* tempfile should appear in the same directory of the zipfile -> save path of zipfile */ TruncFilename(TruncPath, MacZip.ZipFullPath); return fopen(MacZip.ZipFullPath, mode); } if (strcmp(tempzip,path) == 0) { /* add path of zipfile */ sstrcat(TruncPath,tempzip); GetCompletePath(MacZip.TempZipFullPath,TruncPath,&MacZip.TempZipFileSpec,&err); err = PrintUserHFSerr((err != -43) && (err != 0), err, path); printerr("GetCompletePath:",err,err,__LINE__,__FILE__,path); return fopen(MacZip.TempZipFullPath, mode); } printerr("MacFopen:",err,err,__LINE__,__FILE__,path); return NULL; } int MacOpen(const char *path,int oflag, ...) { char RealFname[NAME_MAX]; AssertStr(path,path) RfDfFilen2Real(RealFname,path, MacZip.MacZipMode, MacZip.DataForkOnly, &MacZip.CurrentFork); /* convert to real fname and init global var MacZip.CurrentFork !! */ switch (MacZip.CurrentFork) { case DataFork: { return my_open(RealFname, oflag); break; } case ResourceFork: { return my_open( RealFname, oflag | O_RSRC); break; } default: /* for now (Zip ver 2.3b) MacOpen should never reach this point */ { /* however, this may change in the future ... */ printerr("open: no resource / datafork ",-1,-1,__LINE__,__FILE__,path); return -1; } } } #ifdef muell /* file to delete */ int destroy(char *path) { static char lastpath[NAME_MAX]; char currpath[NAME_MAX]; static Boolean FirstCall = true; long rc; AssertStr(path,path) RfDfFilen2Real(currpath, path, MacZip.MacZipMode, MacZip.DataForkOnly, &MacZip.CurrentFork); if (FirstCall == true) { FirstCall = false; rc = remove(currpath); } else if (strcmp(currpath,lastpath) == 0) return 0; /* ignore, file is already deleted */ else rc = remove(currpath); /* we are removeing all the files only by their pathname this is dangerous on a mac but there is no other way without a complete rewrite of the port */ strcpy(lastpath,currpath); return rc; } #endif /* this function replaces the function "replace()" defined in fileio.c */ int replace(char *new_f, char *temp_f) /* destination and source file names */ { OSErr err = 0; char newfname[NAME_MAX]; AssertStr(new_f,new_f) AssertStr(temp_f,temp_f) UserStop(); GetFilename(newfname, new_f); /* check zipfile name and tempfile name */ /* we are using this function only for replacing the tempfile with the zipfile */ if ((strcmp(zipfile,new_f) == 0) || (strcmp(tempzip,temp_f) == 0)) { remove(MacZip.ZipFullPath); /* rename the temp file to the zip file */ err = rename(MacZip.TempZipFullPath,MacZip.ZipFullPath); printerr("rename:",err,err,__LINE__,__FILE__,MacZip.TempZipFullPath); if (err != 0) return ZE_CREAT; else return ZE_OK; } else return ZE_CREAT; } /* file to delete */ /* we are removeing all the files only by their pathname this is dangerous on a mac but there is no other way without a complete rewrite of the port */ int destroy(char *path) { static char lastpath[NAME_MAX]; static FSSpec trashfolder; static Boolean FirstCall = true; static char Num = 0; static Boolean Immediate_File_Deletion = false; char currpath[NAME_MAX], *envptr; FSSpec fileToDelete; OSErr err; /* init this function */ if ((path == NULL) || (strlen(path) == 0)) { FirstCall = true; Num = 0; return -1; } UserStop(); RfDfFilen2Real(currpath, path, MacZip.MacZipMode, MacZip.DataForkOnly, &MacZip.CurrentFork); GetCompletePath(currpath,currpath,&fileToDelete, &err); if (FirstCall == true) { FirstCall = false; sstrcpy(lastpath,currpath); err = FSpFindFolder(fileToDelete.vRefNum, kTrashFolderType, kDontCreateFolder,&trashfolder); printerr("FSpFindFolder:",err,err,__LINE__,__FILE__,path); envptr = getenv("Immediate_File_Deletion"); if (!(envptr == (char *)NULL || *envptr == '\0')) { if (stricmp(envptr,"yes") == 0) Immediate_File_Deletion = true; else Immediate_File_Deletion = false; } if (Immediate_File_Deletion) { err = FSpDelete(&fileToDelete); return err; } err = CatMove (fileToDelete.vRefNum, fileToDelete.parID, fileToDelete.name, trashfolder.parID, trashfolder.name); return err; } if (strcmp(currpath,lastpath) == 0) { return 0; /* ignore, file is already deleted */ } else { if (Immediate_File_Deletion) { err = FSpDelete(&fileToDelete); sstrcpy(lastpath,path); return err; } err = CatMove (fileToDelete.vRefNum, fileToDelete.parID, fileToDelete.name, trashfolder.parID, trashfolder.name); /* -48 = file is already existing so we have to rename it before moving the file */ if (err == -48) { Num++; if (fileToDelete.name[0] >= 28) /* cut filename if to long */ fileToDelete.name[0] = 28; P2CStr(fileToDelete.name); sprintf(currpath,"%s~%d",(char *)fileToDelete.name,Num); C2PStr(currpath); C2PStr((char *)fileToDelete.name); err = HRename (fileToDelete.vRefNum, fileToDelete.parID, fileToDelete.name, (unsigned char *) currpath); err = CatMove (fileToDelete.vRefNum, fileToDelete.parID, (unsigned char *) currpath, trashfolder.parID, trashfolder.name); } } sstrcpy(lastpath,currpath); return err; } #endif /* #ifdef MACZIP */ /* * int open(const char *path, int oflag) * * Opens a file stream. */ int my_open(char *path, int oflag) { FSSpec spec; char permission; HParamBlockRec hpb; OSErr err, errno; Boolean targetIsFolder, wasAliased; AssertStr(path,path) /* Setup permission */ if ((oflag & 0x03) == O_RDWR) permission = fsRdWrPerm; else permission = (oflag & O_RDONLY) ? fsRdPerm : 0 + (oflag & O_WRONLY) ? fsWrPerm : 0; FSpLocationFromFullPath(strlen(path),path, &spec); if ((oflag & (O_ALIAS | O_NRESOLVE)) == 0) ResolveAliasFile(&spec, true, &targetIsFolder, &wasAliased); hpb.fileParam.ioNamePtr = spec.name; hpb.fileParam.ioVRefNum = spec.vRefNum; hpb.fileParam.ioDirID = spec.parID; hpb.ioParam.ioPermssn = permission; if (oflag & O_RSRC) /* open the resource fork of the file */ err = PBHOpenRFSync(&hpb); else /* open the data fork of the file */ err = PBHOpenDFSync(&hpb); if ((err == fnfErr) && (oflag & O_CREAT)) { hpb.fileParam.ioFlVersNum = 0; err = PBHCreateSync(&hpb); if (err == noErr) { /* Set the finder info */ unsigned long secs; unsigned long isbinary = oflag & O_BINARY; hpb.fileParam.ioFlFndrInfo.fdType = '\?\?\?\?'; hpb.fileParam.ioFlFndrInfo.fdCreator = '\?\?\?\?'; hpb.fileParam.ioFlFndrInfo.fdFlags = 0; if (oflag & O_ALIAS) /* set the alias bit */ hpb.fileParam.ioFlFndrInfo.fdFlags = kIsAlias; else /* clear all flags */ hpb.fileParam.ioFlFndrInfo.fdFlags = 0; GetDateTime(&secs); hpb.fileParam.ioFlCrDat = hpb.fileParam.ioFlMdDat = secs; PBHSetFInfoSync(&hpb); } if (err && (err != dupFNErr)) { errno = err; return -1; } if (oflag & O_RSRC) /* open the resource fork of the file */ err = PBHOpenRFSync(&hpb); else /* open the data fork of the file */ err = PBHOpenDFSync(&hpb); } if (err && (err != dupFNErr) && (err != opWrErr)) { errno = err; return -1; } if (oflag & O_TRUNC) { IOParam pb; pb.ioRefNum = hpb.ioParam.ioRefNum; pb.ioMisc = 0L; err = PBSetEOFSync((ParmBlkPtr)&pb); if (err != noErr) { errno = err; return -1; } } if (oflag & O_APPEND) lseek(hpb.ioParam.ioRefNum,0,SEEK_END); return (hpb.ioParam.ioRefNum); } zip30/macos/source/macopen.h0100644000076400000060000000112707011111164014147 0ustar edisk/* Copyright (c) 1990-1999 Info-ZIP. All rights reserved. See the accompanying file LICENSE, version 1999-Oct-05 or later (the contents of which are also included in zip.h) for terms of use. If, for some reason, both of these files are missing, the Info-ZIP license also may be found at: ftp://ftp.cdrom.com/pub/infozip/license.html */ #ifndef __MACOPEN_H__ #define __MACOPEN_H__ #include #include FILE *MacFopen(const char *path, const char *mode); int MacOpen(const char *path, int oflag, ...); int my_open(char *path, int oflag); #endif /* __MACOPEN_H__ */ zip30/macos/source/macos.c0100644000076400000060000006242610154332006013635 0ustar edisk/* Copyright (c) 1990-1999 Info-ZIP. All rights reserved. See the accompanying file LICENSE, version 1999-Oct-05 or later (the contents of which are also included in zip.h) for terms of use. If, for some reason, both of these files are missing, the Info-ZIP license also may be found at: ftp://ftp.cdrom.com/pub/infozip/license.html */ /*--------------------------------------------------------------------------- macos.c Macintosh-specific routines for use with Info-ZIP's Zip 2.3 and later. ---------------------------------------------------------------------------*/ /*****************************************************************************/ /* Includes */ /*****************************************************************************/ #include "zip.h" #include "revision.h" #include "crypt.h" #include #include #include #include #include #include #include /* #include "charmap.h" */ #include "helpers.h" #include "macstuff.h" #include "pathname.h" #include "recurse.h" /*****************************************************************************/ /* Macros, typedefs */ /*****************************************************************************/ #define PATH_END MacPathEnd /*****************************************************************************/ /* Global Vars */ /*****************************************************************************/ int error_level; /* used only in ziperr() */ /* Note: sizeof() returns the size of this allusion 13 is current length of "XtraStuf.mac:" */ extern const char ResourceMark[13]; /* var is initialized in file pathname.c */ extern jmp_buf EnvForExit; MacZipGlobals MacZip; unsigned long count_of_Zippedfiles = 0; /*****************************************************************************/ /* Module level Vars */ /*****************************************************************************/ static const char MacPathEnd = ':'; /* the Macintosh dir separator */ /* Inform Progress vars */ long estTicksToFinish; long createTime; long updateTicks; static char *Time_Est_strings[] = { "Zipping Files; Items done:", "More than 24 hours", "More than %s hours", "About %s hours, %s minutes", "About an hour", "Less than an hour", "About %s minutes, %s seconds", "About a minute", "Less than a minute", "About %s seconds", "About a second", "About 1 minute, %s seconds"}; /*****************************************************************************/ /* Prototypes */ /*****************************************************************************/ int DoCurrentDir(void); void DoAboutBox(void); void DoQuit(void); void DoEventLoop(void); void ZipInitAllVars(void); void UserStop(void); Boolean IsZipFile(char *name); static long EstimateCompletionTime(const long progressMax, const long progressSoFar, unsigned char percent); static void UpdateTimeToComplete(void); #ifdef USE_SIOUX #include void DoWarnUserDupVol( char *FullPath ); /*****************************************************************************/ /* Functions */ /*****************************************************************************/ /* ** Standalone Unzip with Metrowerks SIOUX starts here ** */ int main(int argc, char **argv) { int return_code; SIOUXSettings.asktosaveonclose = FALSE; SIOUXSettings.showstatusline = TRUE; SIOUXSettings.columns = 100; SIOUXSettings.rows = 40; /* 30 = MacZip Johnny Lee's; 40 = new (my) MacZip */ MacZip.MacZipMode = NewZipMode_EF; argc = ccommand(&argv); if (verbose) PrintArguments(argc, argv); ZipInitAllVars(); return_code = zipmain(argc, argv); if (verbose) printf("\n\n Finish"); return return_code; } /* ** SIOUX needs no extra event handling ** */ void UserStop(void) { }; /* ** Password enter function '*' printed for each char ** */ int macgetch(void) { WindowPtr whichWindow; EventRecord theEvent; char c; /* one-byte buffer for read() to use */ do { SystemTask(); if (!GetNextEvent(everyEvent, &theEvent)) theEvent.what = nullEvent; else { switch (theEvent.what) { case keyDown: c = theEvent.message & charCodeMask; break; case mouseDown: if (FindWindow(theEvent.where, &whichWindow) == inSysWindow) SystemClick(&theEvent, whichWindow); break; case updateEvt: break; } } } while (theEvent.what != keyDown); printf("*"); fflush(stdout); return (int)c; } #endif /******************************/ /* Function version_local() */ /******************************/ /* ** Print Compilers version and compile time/date ** */ void version_local() { /* prints e.g: Compiled with Metrowerks CodeWarrior version 2000 for PowerPC Processor compile time: Feb 4 1998 17:49:49. */ static ZCONST char CompiledWith[] = "\n\nCompiled with %s %x for %s \n %s %s %s.\n\n"; printf(CompiledWith, #ifdef __MWERKS__ " Metrowerks CodeWarrior version", __MWERKS__, #endif #ifdef __MC68K__ " MC68K Processor", #else " PowerPC Processor", #endif #ifdef __DATE__ "compile time: ", __DATE__, __TIME__ #else "", "", "" #endif ); } /* end function version_local() */ /* ** Deletes a dir if the switch '-m' is used ** */ int deletedir(char *path) { static char Num = 0; static FSSpec trashfolder; static Boolean FirstCall = true; static Boolean Immediate_File_Deletion = false; OSErr err; FSSpec dirToDelete; char currpath[NAME_MAX], *envptr; CInfoPBRec fpb; /* init this function */ if ((path == NULL) || (strlen(path) == 0)) { Num = 0; FirstCall = true; return -1; } UserStop(); GetCompletePath(currpath,path,&dirToDelete, &err); if (FirstCall == true) { FirstCall = false; envptr = getenv("Immediate_File_Deletion"); if (!(envptr == (char *)NULL || *envptr == '\0')) { if (stricmp(envptr,"yes") == 0) Immediate_File_Deletion = true; else Immediate_File_Deletion = false; } err = FSpFindFolder(dirToDelete.vRefNum, kTrashFolderType, kDontCreateFolder,&trashfolder); printerr("FSpFindFolder:",err,err,__LINE__,__FILE__,path); } fpb.dirInfo.ioNamePtr = dirToDelete.name; fpb.dirInfo.ioVRefNum = dirToDelete.vRefNum; fpb.dirInfo.ioDrDirID = dirToDelete.parID; fpb.dirInfo.ioFDirIndex = 0; err = PBGetCatInfoSync(&fpb); printerr("PBGetCatInfo deletedir ", err, err, __LINE__, __FILE__, ""); if (fpb.dirInfo.ioDrNmFls > 0) { return 0; /* do not move / delete folders which are not empty */ } if (Immediate_File_Deletion) { err = FSpDelete(&dirToDelete); return err; } err = CatMove (dirToDelete.vRefNum, dirToDelete.parID, dirToDelete.name, trashfolder.parID, trashfolder.name); /* -48 = file is already existing so we have to rename it before moving the file */ if (err == -48) { Num++; if (dirToDelete.name[0] >= 28) /* cut foldername if to long */ dirToDelete.name[0] = 28; P2CStr(dirToDelete.name); sprintf(currpath,"%s~%d",(char *)dirToDelete.name,Num); C2PStr(currpath); C2PStr((char *)dirToDelete.name); err = HRename (dirToDelete.vRefNum, dirToDelete.parID, dirToDelete.name, (unsigned char *) currpath); err = CatMove (dirToDelete.vRefNum, dirToDelete.parID, (unsigned char *) currpath, trashfolder.parID, trashfolder.name); } return err; } /* ** Set the file-type so the archive will get the correct icon, type ** and creator code. */ void setfiletype(char *new_f, unsigned long Creator, unsigned long Type) { OSErr err; if (strcmp(zipfile, new_f) == 0) err = FSpChangeCreatorType(&MacZip.ZipFileSpec, Creator, Type); printerr("FSpChangeCreatorType:", err, err, __LINE__, __FILE__, new_f); return; } /* ** Convert the external (native) filename into Zip's internal Unix compatible ** name space. */ char *ex2in(char *externalFilen, int isdir, int *pdosflag) /* char *externalFilen external file name */ /* int isdir input: externalFilen is a directory */ /* int *pdosflag output: force MSDOS file attributes? */ /* Convert the external file name to a zip file name, returning the malloc'ed string or NULL if not enough memory. */ { char *internalFilen; /* internal file name (malloc'ed) */ char *t; /* shortened name */ char *Pathname; char buffer[NAME_MAX]; int dosflag; AssertStr(externalFilen, externalFilen) AssertBool(isdir,"") dosflag = dosify; /* default for non-DOS and non-OS/2 */ /* Find starting point in name before doing malloc */ for (t = externalFilen; *t == PATH_END; t++) ; if (!MacZip.StoreFullPath) { Pathname = StripPartialDir(buffer, MacZip.SearchDir,t); } else { Pathname = t; } /* Make changes, if any, to the copied name (leave original intact) */ if (!pathput) { t = last(Pathname, PATH_END); } else t = Pathname; /* Malloc space for internal name and copy it */ if ((internalFilen = malloc(strlen(t) + 10 + strlen(ResourceMark) )) == NULL) return NULL; sstrcpy(internalFilen, t); /* we have to eliminate illegal chars: * The name space for Mac filenames and Zip filenames (unix style names) * do both include all printable extended-ASCII characters. The only * difference we have to take care of is the single special character * used as path delimiter: * ':' on MacOS and '/' on Unix and '\' on Dos. * So, to convert between Mac filenames and Unix filenames without any * loss of information, we simply interchange ':' and '/'. Additionally, * we try to convert the coding of the extended-ASCII characters into * InfoZip's standard ISO 8859-1 codepage table. */ MakeCompatibleString(internalFilen, ':', '/', '/', ':', MacZip.CurrTextEncodingBase); /* Returned malloc'ed name */ if (pdosflag) *pdosflag = dosflag; if (isdir) { return internalFilen; /* avoid warning on unused variable */ } if (dosify) { msname(internalFilen); printf("\n ex2in: %s",internalFilen); } return internalFilen; } /* ** Collect all filenames. Go through all directories ** */ int wild(char *Pathpat) /* path/pattern to match */ /* If not in exclude mode, expand the pattern based on the contents of the file system. Return an error code in the ZE_ class. */ { FSSpec Spec; char fullpath[NAME_MAX]; OSErr err; AssertStr(Pathpat, Pathpat); if (noisy) printf("%s \n\n",GetZipVersionsInfo()); if (extra_fields == 0) { MacZip.DataForkOnly = true; } /* for switch '-R' -> '.' means current dir */ if (strcmp(Pathpat,".") == 0) sstrcpy(Pathpat,"*"); sstrcpy(MacZip.Pattern,Pathpat); if (recurse) { MacZip.StoreFoldersAlso = true; MacZip.SearchLevels = 0; /* if 0 we aren't checking levels */ } else { MacZip.StoreFoldersAlso = false; MacZip.SearchLevels = 1; } /* make complete path */ GetCompletePath(fullpath, MacZip.Pattern, &Spec,&err); err = PrintUserHFSerr((err != -43) && (err != 0), err, MacZip.Pattern); printerr("GetCompletePath:", err, err, __LINE__, __FILE__, fullpath); /* extract the filepattern */ GetFilename(MacZip.Pattern, fullpath); /* extract Path and get FSSpec of search-path */ /* get FSSpec of search-path ; we need a dir to start searching for filenames */ TruncFilename(MacZip.SearchDir, fullpath); GetCompletePath(MacZip.SearchDir, MacZip.SearchDir, &Spec,&err); if (noisy) { if (MacZip.SearchLevels == 0) { printf("\nSearch Pattern: [%s] Levels: all", MacZip.Pattern); } else { printf("\nSearch Pattern: [%s] Levels: %d", MacZip.Pattern, MacZip.SearchLevels); } printf("\nSearch Path: [%s]", MacZip.SearchDir); printf("\nZip-File: [%s] \n",MacZip.ZipFullPath); } /* we are working only with pathnames; * this can cause big problems on a mac ... */ if (CheckMountedVolumes(MacZip.SearchDir) > 1) DoWarnUserDupVol(MacZip.SearchDir); /* start getting all filenames */ err = FSpRecurseDirectory(&Spec, MacZip.SearchLevels); printerr("FSpRecurseDirectory:", err, err, __LINE__, __FILE__, ""); return ZE_OK; } /* ** Convert the internal filename into a external (native). ** The user will see this modified filename. ** For more performance: ** I do not completly switch back to the native macos filename. ** The user will still see directory separator '/' and the converted ** charset. */ char *in2ex(char *n) /* internal file name */ /* Convert the zip file name to an external file name, returning the malloc'ed string or NULL if not enough memory. */ { char *x; /* external file name */ AssertStr(n,n) if ((x = malloc(strlen(n) + 1)) == NULL) return NULL; RfDfFilen2Real(x, n, MacZip.MacZipMode, MacZip.DataForkOnly, &MacZip.CurrentFork); return x; } /* ** Process on filenames. This function will be called to collect ** the filenames. */ int procname(char *filename, /* name to process */ int caseflag) /* true to force case-sensitive match (always false on a Mac) */ /* Process a name . Return an error code in the ZE_ class. */ { int rc; /* matched flag */ AssertBool(caseflag,"caseflag") AssertStr(filename,filename) /* add or remove name of file */ rc = newname(filename, MacZip.isDirectory, caseflag); return rc; } ulg filetime( char *f, /* name of file to get info on */ ulg *a, /* return value: file attributes */ long *n, /* return value: file size */ iztimes *t) /* return value: access, modific. and creation times */ /* If file *f does not exist, return 0. Else, return the file's last modified date and time as an MSDOS date and time. The date and time is returned in a long with the date most significant to allow unsigned integer comparison of absolute times. Also, if a is not a NULL pointer, store the file attributes there, with the high two bytes being the Unix attributes, and the low byte being a mapping of that to DOS attributes. If n is not NULL, store the file size there. If t is not NULL, the file's access, modification and creation times are stored there as UNIX time_t values. If f is "-", use standard input as the file. If f is a device, return a file size of -1 */ { struct stat s; /* results of stat() */ AssertStr(f,f) if (strlen(f) == 0) return 0; if (SSTAT(f, &s) != 0) /* Accept about any file kind including directories * (stored with trailing : with -r option) */ return 0; if (a != NULL) { *a = ((ulg)s.st_mode << 16) | !(s.st_mode & S_IWRITE); if (MacZip.isDirectory) { *a |= MSDOS_DIR_ATTR; } } if (n != NULL) *n = (s.st_mode & UNX_IFMT) == UNX_IFREG ? s.st_size : -1L; if (t != NULL) { t->atime = s.st_atime; t->mtime = s.st_mtime; t->ctime = s.st_ctime; /* on Mac, st_ctime contains creation time! */ } return unix2dostime(&s.st_mtime); } void stamp(char *f, ulg d) /* char *f; name of file to change */ /* ulg d; dos-style time to change it to */ /* Set last updated and accessed time of file f to the DOS time d. */ { time_t u[2]; /* argument for utime() */ f = f; /* Convert DOS time to time_t format in u */ u[0] = u[1] = dos2unixtime(d); /* utime(f, u); */ } /* ** return only the longest part of the path: ** second parameter: Volume:test folder:second folder: ** third parameter: Volume:test folder:second folder:third folder:file ** result will be: third folder:file ** first parameter: contains string buffer that will be used to prepend ** the "resource mark" part in front of the result when ** a resource fork is processed in "M3" mode. ** */ char *StripPartialDir(char *CompletePath, const char *PartialPath, const char *FullPath) { const char *tmpPtr1 = PartialPath; const char *tmpPtr2 = FullPath; int result; Assert_it(CompletePath,"StripPartialDir","") AssertStrNoOverlap(FullPath,PartialPath,PartialPath) if (MacZip.DataForkOnly) { tmpPtr2 += strlen(tmpPtr1); return (char *)tmpPtr2; } switch (MacZip.MacZipMode) { case JohnnyLee_EF: { tmpPtr2 += strlen(tmpPtr1); return (char *)tmpPtr2; break; } case NewZipMode_EF: { /* determine Fork type */ result = strncmp(FullPath, ResourceMark, sizeof(ResourceMark)-2); if (result != 0) { /* data fork */ MacZip.CurrentFork = DataFork; tmpPtr2 += strlen(tmpPtr1); return (char *)tmpPtr2; } else { /* resource fork */ MacZip.CurrentFork = ResourceFork; sstrcpy(CompletePath, ResourceMark); tmpPtr2 += strlen(tmpPtr1); tmpPtr2 += sizeof(ResourceMark); sstrcat(CompletePath, tmpPtr2); return (char *)CompletePath; } break; } } return NULL; /* function should never reach this point */ } /* ** Init all global variables ** Must be called for each zip-run */ void ZipInitAllVars(void) { getcwd(MacZip.CurrentPath, sizeof(MacZip.CurrentPath)); /* MacZip.MacZipMode = JohnnyLee_EF; */ MacZip.MacZipMode = NewZipMode_EF; MacZip.DataForkOnly = false; MacZip.CurrentFork = NoFork; MacZip.StoreFoldersAlso = false; MacZip.FoundFiles = 0; MacZip.FoundDirectories = 0; MacZip.RawCountOfItems = 0; MacZip.BytesOfData = 0; MacZip.StoreFullPath = false; MacZip.StatingProgress = false; MacZip.IncludeInvisible = false; MacZip.isMacStatValid = false; MacZip.CurrTextEncodingBase = FontScript(); MacZip.HaveGMToffset = false; createTime = TickCount(); estTicksToFinish = -1; updateTicks = 0; /* init some functions */ IsZipFile(NULL); destroy(NULL); deletedir(NULL); ShowCounter(true); extra_fields = 1; error_level = 0; count_of_Zippedfiles = 0; } /* ** Get the findercomment and store it as file-comment in the Zip-file ** */ char *GetComment(char *filename) { OSErr err; static char buffer[NAME_MAX]; char buffer2[NAME_MAX]; char *tmpPtr; if (filename == NULL) return NULL; /* now we can convert Unix-Path in HFS-Path */ for (tmpPtr = filename; *tmpPtr; tmpPtr++) if (*tmpPtr == '/') *tmpPtr = ':'; if (MacZip.StoreFullPath) { /* filename is already a fullpath */ sstrcpy(buffer,filename); } else { /* make a fullpath */ sstrcpy(buffer,MacZip.SearchDir); sstrcat(buffer,filename); } /* make fullpath and get FSSpec */ /* Unfortunately: I get only the converted filename here */ /* so filenames with extended characters can not be found */ GetCompletePath(buffer2,buffer, &MacZip.fileSpec, &err); printerr("GetCompletePath:",(err != -43) && (err != -120) && (err != 0) , err,__LINE__,__FILE__,buffer); err = FSpDTGetComment(&MacZip.fileSpec, (unsigned char *) buffer); printerr("FSpDTGetComment:", (err != -5012) && (err != 0), err, __LINE__, __FILE__, filename); P2CStr((unsigned char *) buffer); if (err == -5012) return NULL; /* no finder-comments found */ if (noisy) printf("\n%32s -> %s",filename, buffer); /* Beside the script change we need only to change 0x0d in 0x0a so the last two arguments are not needed and does nothing. */ MakeCompatibleString(buffer, 0x0d, 0x0a, ' ', ' ', MacZip.CurrTextEncodingBase); return buffer; } /* ** Print a progress indicator for stating the files ** */ void PrintStatProgress(char *msg) { if (!noisy) return; /* do no output if noisy is false */ MacZip.StatingProgress = true; if (strcmp(msg,"done") == 0) { MacZip.StatingProgress = false; printf("\n ... done \n\n"); } else printf("\n %s",msg); } void InformProgress(const long progressMax, const long progressSoFar ) { int curr_percent; char no_time[5] = "..."; curr_percent = percent(progressMax, progressSoFar); if (curr_percent < 95) { estTicksToFinish = EstimateCompletionTime(progressMax, progressSoFar, curr_percent); } else { rightStatusString(no_time); leftStatusString(no_time); } updateTicks = TickCount() + 60; return; } void ShowCounter(Boolean reset) { static char statusline[100]; static unsigned long filecount = 0; if (reset) { filecount = 0; return; } if (noisy) { sprintf(statusline, "%6d", filecount++); rightStatusString(statusline); } } static long EstimateCompletionTime(const long progressMax, const long progressSoFar, unsigned char curr_percent) { long max = progressMax, value = progressSoFar; static char buf[100]; unsigned long ticksTakenSoFar = TickCount() - createTime; float currentRate = (float) ticksTakenSoFar / (float) value; long newEst = (long)( currentRate * (float)( max - value )); sprintf(buf, "%d [%d%%]",progressSoFar, curr_percent); rightStatusString(buf); estTicksToFinish = newEst; UpdateTimeToComplete(); return estTicksToFinish; } static void UpdateTimeToComplete(void) { short days, hours, minutes, seconds; char estStr[255]; Str15 xx, yy; short idx = 0; if ( estTicksToFinish == -1 ) return; days = estTicksToFinish / 5184000L; hours = ( estTicksToFinish - ( days * 5184000L )) / 216000L; minutes = ( estTicksToFinish - ( days * 5184000L ) - ( hours * 216000L )) / 3600L; seconds = ( estTicksToFinish - ( days * 5184000L ) - ( hours * 216000L ) - ( minutes * 3600L )) / 60L; xx[0] = 0; yy[0] = 0; if ( days ) { /* "more than 24 hours" */ idx = 1; goto setEstTimeStr; } if ( hours >= 8 ) { /* "more than x hours" */ NumToString( hours, xx ); idx = 2; goto setEstTimeStr; } if ( estTicksToFinish > 252000L ) /* > 1hr, 10 minutes */ { /* "about x hours, y minutes" */ NumToString( hours, xx ); NumToString( minutes, yy ); idx = 3; goto setEstTimeStr; } if ( estTicksToFinish > 198000L ) /* > 55 minutes */ { /* "about an hour" */ idx = 4; goto setEstTimeStr; } if ( estTicksToFinish > 144000L ) /* > 40 minutes */ { /* "less than an hour" */ idx = 5; goto setEstTimeStr; } if ( estTicksToFinish > 4200L ) /* > 1 minute, 10 sec */ { /* "about x minutes, y seconds */ NumToString( minutes, xx ); NumToString( seconds, yy ); if ( minutes == 1 ) idx = 11; else idx = 6; goto setEstTimeStr; } if ( estTicksToFinish > 3000L ) /* > 50 seconds */ { /* "about a minute" */ idx = 7; goto setEstTimeStr; } if ( estTicksToFinish > 1500L ) /* > 25 seconds */ { /* "less than a minute" */ idx = 8; goto setEstTimeStr; } if ( estTicksToFinish > 120L ) /* > 2 seconds */ { NumToString( seconds, xx ); idx = 9; goto setEstTimeStr; } idx = 10; setEstTimeStr: sprintf(estStr,Time_Est_strings[idx],P2CStr(xx),P2CStr(yy)); leftStatusString((char *)estStr); } /* ** Just return the zip version ** */ char *GetZipVersionsInfo(void) { static char ZipVersion[100]; sprintf(ZipVersion, "Zip Module\n%d.%d%d%s of %s", Z_MAJORVER, Z_MINORVER, Z_PATCHLEVEL, Z_BETALEVEL, REVDATE); return ZipVersion; } #ifndef USE_SIOUX /* ** Just return the copyright message ** */ char *GetZipCopyright(void) { static char CopyR[300]; sstrcpy(CopyR, copyright[0]); sstrcat(CopyR, copyright[1]); sstrcat(CopyR, "\r\rPlease send bug reports to the authors at\r"\ "Zip-Bugs@lists.wku.edu"); return CopyR; } /* ** Just return the compilers date/time ** */ char *GetZipVersionLocal(void) { static char ZipVersionLocal[50]; sprintf(ZipVersionLocal, "[%s %s]", __DATE__, __TIME__); return ZipVersionLocal; } #endif /* #ifndef USE_SIOUX */ zip30/macos/source/macstuff.c0100644000076400000060000014754410154332006014350 0ustar edisk/* These Functions were originally part of More Files version 1.4.8 More Files fixes many of the broken or underfunctional parts of the file system. More Files A collection of File Manager and related routines by Jim Luther (Apple Macintosh Developer Technical Support Emeritus) with significant code contributions by Nitin Ganatra (Apple Macintosh Developer Technical Support Emeritus) Copyright 1992-1998 Apple Computer, Inc. Portions copyright 1995 Jim Luther All rights reserved. The Package "More Files" is distributed under the following license terms: "You may incorporate this sample code into your applications without restriction, though the sample code has been provided "AS IS" and the responsibility for its operation is 100% yours. However, what you are not permitted to do is to redistribute the source as "DSC Sample Code" after having made changes. If you're going to redistribute the source, we require that you make it clear in the source that the code was descended from Apple Sample Code, but that you've made changes." The following changes are made by Info-ZIP: - The only changes are made by pasting the functions (mostly found in MoreFilesExtras.c / MoreFiles.c) directly into macstuff.c / macstuff.h and slightly reformatting the text (replacement of TABs by spaces, removal/replacement of non-ASCII characters). The code itself is NOT changed. This file has been modified by Info-ZIP for use in MacZip. This file is NOT part of the original package More Files. More Files can be found on the MetroWerks CD and Developer CD from Apple. You can also download the latest version from: http://members.aol.com/JumpLong/#MoreFiles Jim Luther's Home-page: http://members.aol.com/JumpLong/ */ #include #include "macstuff.h" extern int errno; static OSErr GetCommentFromDesktopFile(short vRefNum, long dirID, ConstStr255Param name, Str255 comment); static OSErr GetCommentID(short vRefNum, long dirID, ConstStr255Param name, short *commentID); static OSErr GetDesktopFileName(short vRefNum, Str255 desktopName); enum { kBNDLResType = 'BNDL', kFREFResType = 'FREF', kIconFamResType = 'ICN#', kFCMTResType = 'FCMT', kAPPLResType = 'APPL' }; /*****************************************************************************/ /* ** File Manager FSp calls */ /*****************************************************************************/ pascal OSErr FSMakeFSSpecCompat(short vRefNum, long dirID, ConstStr255Param fileName, FSSpec *spec) { OSErr result; #if !__MACOSSEVENORLATER if ( !FSHasFSSpecCalls() && !QTHasFSSpecCalls() ) { Boolean isDirectory; result = GetObjectLocation(vRefNum, dirID, fileName, &(spec->vRefNum), &(spec->parID), spec->name, &isDirectory); } else #endif /* !__MACOSSEVENORLATER */ { /* Let the file system create the FSSpec if it can since it does the job */ /* much more efficiently than I can. */ result = FSMakeFSSpec(vRefNum, dirID, fileName, spec); /* Fix a bug in Macintosh PC Exchange's MakeFSSpec code where 0 is */ /* returned in the parID field when making an FSSpec to the volume's */ /* root directory by passing a full pathname in MakeFSSpec's */ /* fileName parameter. Fixed in Mac OS 8.1 */ if ( (result == noErr) && (spec->parID == 0) ) spec->parID = fsRtParID; } return ( result ); } /*****************************************************************************/ /* FSHasFSSpecCalls returns true if the file system provides FSSpec calls. */ #if !__MACOSSEVENORLATER static Boolean FSHasFSSpecCalls(void) { long response; #if !GENERATENODATA static Boolean tested = false; static Boolean result = false; #else Boolean result = false; #endif #if !GENERATENODATA if ( !tested ) { tested = true; #endif if ( Gestalt(gestaltFSAttr, &response) == noErr ) { result = ((response & (1L << gestaltHasFSSpecCalls)) != 0); } #if !GENERATENODATA } #endif return ( result ); } #endif /* !__MACOSSEVENORLATER */ /*****************************************************************************/ /* QTHasFSSpecCalls returns true if QuickTime provides FSSpec calls */ /* except for FSpExchangeFiles. */ #if !__MACOSSEVENORLATER static Boolean QTHasFSSpecCalls(void) { long response; #if !GENERATENODATA static Boolean tested = false; static Boolean result = false; #else Boolean result = false; #endif #if !GENERATENODATA if ( !tested ) { tested = true; #endif result = (Gestalt(gestaltQuickTimeVersion, &response) == noErr); #if !GENERATENODATA } #endif return ( result ); } #endif /* !__MACOSSEVENORLATER */ /* *---------------------------------------------------------------------- * * FSpGetDefaultDir -- * * This function gets the current default directory. * * Results: * The provided FSSpec is changed to point to the "default" * directory. The function returns what ever errors * FSMakeFSSpecCompat may encounter. * * Side effects: * None. * *---------------------------------------------------------------------- */ int FSpGetDefaultDir(FSSpecPtr dirSpec) /* On return the default directory. */ { OSErr err; short vRefNum = 0; long int dirID = 0; err = HGetVol(NULL, &vRefNum, &dirID); if (err == noErr) { err = FSMakeFSSpecCompat(vRefNum, dirID, (ConstStr255Param) NULL, dirSpec); } return err; } /* *---------------------------------------------------------------------- * * FSpSetDefaultDir -- * * This function sets the default directory to the directory * pointed to by the provided FSSpec. * * Results: * The function returns what ever errors HSetVol may encounter. * * Side effects: * None. * *---------------------------------------------------------------------- */ int FSpSetDefaultDir(FSSpecPtr dirSpec) /* The new default directory. */ { OSErr err; /* * The following special case is needed to work around a bug * in the Macintosh OS. (Acutally PC Exchange.) */ if (dirSpec->parID == fsRtParID) { err = HSetVol(NULL, dirSpec->vRefNum, fsRtDirID); } else { err = HSetVol(dirSpec->name, dirSpec->vRefNum, dirSpec->parID); } return err; } /* *---------------------------------------------------------------------- * * FSpFindFolder -- * * This function is a version of the FindFolder function that * returns the result as a FSSpec rather than a vRefNum and dirID. * * Results: * Results will be simaler to that of the FindFolder function. * * Side effects: * None. * *---------------------------------------------------------------------- */ OSErr FSpFindFolder( short vRefNum, /* Volume reference number. */ OSType folderType, /* Folder type taken by FindFolder. */ Boolean createFolder, /* Should we create it if non-existant. */ FSSpec *spec) /* Pointer to resulting directory. */ { short foundVRefNum; long foundDirID; OSErr err; err = FindFolder(vRefNum, folderType, createFolder, &foundVRefNum, &foundDirID); if (err != noErr) { return err; } err = FSMakeFSSpecCompat(foundVRefNum, foundDirID, "\p", spec); return err; } /* *---------------------------------------------------------------------- * * FSpPathFromLocation -- * * This function obtains a full path name for a given macintosh * FSSpec. Unlike the More Files function FSpGetFullPath, this * function will return a C string in the Handle. It also will * create paths for FSSpec that do not yet exist. * * Results: * OSErr code. * * Side effects: * None. * *---------------------------------------------------------------------- */ OSErr FSpPathFromLocation( FSSpec *spec, /* The location we want a path for. */ int *length, /* Length of the resulting path. */ Handle *fullPath) /* Handle to path. */ { OSErr err; FSSpec tempSpec; CInfoPBRec pb; *fullPath = NULL; /* * Make a copy of the input FSSpec that can be modified. */ BlockMoveData(spec, &tempSpec, sizeof(FSSpec)); if (tempSpec.parID == fsRtParID) { /* * The object is a volume. Add a colon to make it a full * pathname. Allocate a handle for it and we are done. */ tempSpec.name[0] += 2; tempSpec.name[tempSpec.name[0] - 1] = ':'; tempSpec.name[tempSpec.name[0]] = '\0'; err = PtrToHand(&tempSpec.name[1], fullPath, tempSpec.name[0]); } else { /* * The object isn't a volume. Is the object a file or a directory? */ pb.dirInfo.ioNamePtr = tempSpec.name; pb.dirInfo.ioVRefNum = tempSpec.vRefNum; pb.dirInfo.ioDrDirID = tempSpec.parID; pb.dirInfo.ioFDirIndex = 0; err = PBGetCatInfoSync(&pb); if ((err == noErr) || (err == fnfErr)) { /* * If the file doesn't currently exist we start over. If the * directory exists everything will work just fine. Otherwise we * will just fail later. If the object is a directory, append a * colon so full pathname ends with colon. */ if (err == fnfErr) { BlockMoveData(spec, &tempSpec, sizeof(FSSpec)); } else if ( (pb.hFileInfo.ioFlAttrib & ioDirMask) != 0 ) { tempSpec.name[0] += 1; tempSpec.name[tempSpec.name[0]] = ':'; } /* * Create a new Handle for the object - make it a C string. */ tempSpec.name[0] += 1; tempSpec.name[tempSpec.name[0]] = '\0'; err = PtrToHand(&tempSpec.name[1], fullPath, tempSpec.name[0]); if (err == noErr) { /* * Get the ancestor directory names - loop until we have an * error or find the root directory. */ pb.dirInfo.ioNamePtr = tempSpec.name; pb.dirInfo.ioVRefNum = tempSpec.vRefNum; pb.dirInfo.ioDrParID = tempSpec.parID; do { pb.dirInfo.ioFDirIndex = -1; pb.dirInfo.ioDrDirID = pb.dirInfo.ioDrParID; err = PBGetCatInfoSync(&pb); if (err == noErr) { /* * Append colon to directory name and add * directory name to beginning of fullPath. */ ++tempSpec.name[0]; tempSpec.name[tempSpec.name[0]] = ':'; (void) Munger(*fullPath, 0, NULL, 0, &tempSpec.name[1], tempSpec.name[0]); err = MemError(); } } while ( (err == noErr) && (pb.dirInfo.ioDrDirID != fsRtDirID) ); } } } /* * On error Dispose the handle, set it to NULL & return the err. * Otherwise, set the length & return. */ if (err == noErr) { *length = GetHandleSize(*fullPath) - 1; } else { if ( *fullPath != NULL ) { DisposeHandle(*fullPath); } *fullPath = NULL; *length = 0; } return err; } /*****************************************************************************/ pascal OSErr FSpGetDirectoryID(const FSSpec *spec, long *theDirID, Boolean *isDirectory) { return ( GetDirectoryID(spec->vRefNum, spec->parID, spec->name, theDirID, isDirectory) ); } /*****************************************************************************/ pascal OSErr GetDirectoryID(short vRefNum, long dirID, ConstStr255Param name, long *theDirID, Boolean *isDirectory) { CInfoPBRec pb; OSErr error; error = GetCatInfoNoName(vRefNum, dirID, name, &pb); if ( error == noErr ) { *isDirectory = (pb.hFileInfo.ioFlAttrib & ioDirMask) != 0; if ( *isDirectory ) { *theDirID = pb.dirInfo.ioDrDirID; } else { *theDirID = pb.hFileInfo.ioFlParID; } } return ( error ); } /*****************************************************************************/ pascal OSErr GetCatInfoNoName(short vRefNum, long dirID, ConstStr255Param name, CInfoPBPtr pb) { Str31 tempName; OSErr error; /* Protection against File Sharing problem */ if ( (name == NULL) || (name[0] == 0) ) { tempName[0] = 0; pb->dirInfo.ioNamePtr = tempName; pb->dirInfo.ioFDirIndex = -1; /* use ioDirID */ } else { pb->dirInfo.ioNamePtr = (StringPtr)name; pb->dirInfo.ioFDirIndex = 0; /* use ioNamePtr and ioDirID */ } pb->dirInfo.ioVRefNum = vRefNum; pb->dirInfo.ioDrDirID = dirID; error = PBGetCatInfoSync(pb); pb->dirInfo.ioNamePtr = NULL; return ( error ); } /*****************************************************************************/ pascal OSErr GetObjectLocation(short vRefNum, long dirID, ConstStr255Param pathname, short *realVRefNum, long *realParID, Str255 realName, Boolean *isDirectory) { OSErr error; CInfoPBRec pb; Str255 tempPathname; /* clear results */ *realVRefNum = 0; *realParID = 0; realName[0] = 0; /* ** Get the real vRefNum */ error = DetermineVRefNum(pathname, vRefNum, realVRefNum); if ( error == noErr ) { /* ** Determine if the object already exists and if so, ** get the real parent directory ID if it's a file */ /* Protection against File Sharing problem */ if ( (pathname == NULL) || (pathname[0] == 0) ) { tempPathname[0] = 0; pb.hFileInfo.ioNamePtr = tempPathname; pb.hFileInfo.ioFDirIndex = -1; /* use ioDirID */ } else { pb.hFileInfo.ioNamePtr = (StringPtr)pathname; pb.hFileInfo.ioFDirIndex = 0; /* use ioNamePtr and ioDirID */ } pb.hFileInfo.ioVRefNum = vRefNum; pb.hFileInfo.ioDirID = dirID; error = PBGetCatInfoSync(&pb); if ( error == noErr ) { /* ** The file system object is present and we have the file's ** real parID */ /* Is it a directory or a file? */ *isDirectory = (pb.hFileInfo.ioFlAttrib & ioDirMask) != 0; if ( *isDirectory ) { /* ** It's a directory, get its name and parent dirID, and then ** we're done */ pb.dirInfo.ioNamePtr = realName; pb.dirInfo.ioVRefNum = *realVRefNum; /* pb.dirInfo.ioDrDirID already contains the dirID of the directory object */ pb.dirInfo.ioFDirIndex = -1; /* get information about ioDirID */ error = PBGetCatInfoSync(&pb); /* get the parent ID here, because the file system can return the */ /* wrong parent ID from the last call. */ *realParID = pb.dirInfo.ioDrParID; } else { /* ** It's a file - use the parent directory ID from the last call ** to GetCatInfoparse, get the file name, and then we're done */ *realParID = pb.hFileInfo.ioFlParID; error = GetFilenameFromPathname(pathname, realName); } } else if ( error == fnfErr ) { /* ** The file system object is not present - see if its parent is present */ /* ** Parse to get the object name from end of pathname */ error = GetFilenameFromPathname(pathname, realName); /* if we can't get the object name from the end, we can't continue */ if ( error == noErr ) { /* ** What we want now is the pathname minus the object name ** for example: ** if pathname is 'vol:dir:file' tempPathname becomes 'vol:dir:' ** if pathname is 'vol:dir:file:' tempPathname becomes 'vol:dir:' ** if pathname is ':dir:file' tempPathname becomes ':dir:' ** if pathname is ':dir:file:' tempPathname becomes ':dir:' ** if pathname is ':file' tempPathname becomes ':' ** if pathname is 'file or file:' tempPathname becomes '' */ /* get a copy of the pathname */ BlockMoveData(pathname, tempPathname, pathname[0] + 1); /* remove the object name */ tempPathname[0] -= realName[0]; /* and the trailing colon (if any) */ if ( pathname[pathname[0]] == ':' ) { --tempPathname[0]; } /* OK, now get the parent's directory ID */ /* Protection against File Sharing problem */ pb.hFileInfo.ioNamePtr = (StringPtr)tempPathname; if ( tempPathname[0] != 0 ) { pb.hFileInfo.ioFDirIndex = 0; /* use ioNamePtr and ioDirID */ } else { pb.hFileInfo.ioFDirIndex = -1; /* use ioDirID */ } pb.hFileInfo.ioVRefNum = vRefNum; pb.hFileInfo.ioDirID = dirID; error = PBGetCatInfoSync(&pb); *realParID = pb.dirInfo.ioDrDirID; *isDirectory = false; /* we don't know what the object is really going to be */ } if ( error != noErr ) { error = dirNFErr; /* couldn't find parent directory */ } else { error = fnfErr; /* we found the parent, but not the file */ } } } return ( error ); } /*****************************************************************************/ pascal OSErr DetermineVRefNum(ConstStr255Param pathname, short vRefNum, short *realVRefNum) { HParamBlockRec pb; OSErr error; error = GetVolumeInfoNoName(pathname,vRefNum, &pb); if ( error == noErr ) { *realVRefNum = pb.volumeParam.ioVRefNum; } return ( error ); } /*****************************************************************************/ pascal OSErr GetFilenameFromPathname(ConstStr255Param pathname, Str255 filename) { short index; short nameEnd; OSErr error; /* default to no filename */ filename[0] = 0; /* check for no pathname */ if ( pathname != NULL ) { /* get string length */ index = pathname[0]; /* check for empty string */ if ( index != 0 ) { /* skip over last trailing colon (if any) */ if ( pathname[index] == ':' ) { --index; } /* save the end of the string */ nameEnd = index; /* if pathname ends with multiple colons, then this pathname refers */ /* to a directory, not a file */ if ( pathname[index] != ':' ) { /* parse backwards until we find a colon or hit the beginning of the pathname */ while ( (index != 0) && (pathname[index] != ':') ) { --index; } /* if we parsed to the beginning of the pathname and the pathname ended */ /* with a colon, then pathname is a full pathname to a volume, not a file */ if ( (index != 0) || (pathname[pathname[0]] != ':') ) { /* get the filename and return noErr */ filename[0] = (char)(nameEnd - index); BlockMoveData(&pathname[index+1], &filename[1], nameEnd - index); error = noErr; } else { /* pathname to a volume, not a file */ error = notAFileErr; } } else { /* directory, not a file */ error = notAFileErr; } } else { /* empty string isn't a file */ error = notAFileErr; } } else { /* NULL pathname isn't a file */ error = notAFileErr; } return ( error ); } /*****************************************************************************/ /* ** GetVolumeInfoNoName uses pathname and vRefNum to call PBHGetVInfoSync ** in cases where the returned volume name is not needed by the caller. ** The pathname and vRefNum parameters are not touched, and the pb ** parameter is initialized by PBHGetVInfoSync except that ioNamePtr in ** the parameter block is always returned as NULL (since it might point ** to the local tempPathname). ** ** I noticed using this code in several places, so here it is once. ** This reduces the code size of MoreFiles. */ pascal OSErr GetVolumeInfoNoName(ConstStr255Param pathname, short vRefNum, HParmBlkPtr pb) { Str255 tempPathname; OSErr error; /* Make sure pb parameter is not NULL */ if ( pb != NULL ) { pb->volumeParam.ioVRefNum = vRefNum; if ( pathname == NULL ) { pb->volumeParam.ioNamePtr = NULL; pb->volumeParam.ioVolIndex = 0; /* use ioVRefNum only */ } else { /* make a copy of the string and */ BlockMoveData(pathname, tempPathname, pathname[0] + 1); /* use the copy so original isn't trashed */ pb->volumeParam.ioNamePtr = (StringPtr)tempPathname; /* use ioNamePtr/ioVRefNum combination */ pb->volumeParam.ioVolIndex = -1; } error = PBHGetVInfoSync(pb); pb->volumeParam.ioNamePtr = NULL; /* ioNamePtr may point to local tempPathname, so don't return it */ } else { error = paramErr; } return ( error ); } /*****************************************************************************/ pascal OSErr FSpGetFullPath(const FSSpec *spec, short *fullPathLength, Handle *fullPath) { OSErr result; OSErr realResult; FSSpec tempSpec; CInfoPBRec pb; *fullPathLength = 0; *fullPath = NULL; /* Default to noErr */ realResult = noErr; /* Make a copy of the input FSSpec that can be modified */ BlockMoveData(spec, &tempSpec, sizeof(FSSpec)); if ( tempSpec.parID == fsRtParID ) { /* The object is a volume */ /* Add a colon to make it a full pathname */ ++tempSpec.name[0]; tempSpec.name[tempSpec.name[0]] = ':'; /* We're done */ result = PtrToHand(&tempSpec.name[1], fullPath, tempSpec.name[0]); } else { /* The object isn't a volume */ /* Is the object a file or a directory? */ pb.dirInfo.ioNamePtr = tempSpec.name; pb.dirInfo.ioVRefNum = tempSpec.vRefNum; pb.dirInfo.ioDrDirID = tempSpec.parID; pb.dirInfo.ioFDirIndex = 0; result = PBGetCatInfoSync(&pb); /* Allow file/directory name at end of path to not exist. */ realResult = result; if ( (result == noErr) || (result == fnfErr) ) { /* if the object is a directory, append a colon so full pathname ends with colon */ if ( (result == noErr) && (pb.hFileInfo.ioFlAttrib & ioDirMask) != 0 ) { ++tempSpec.name[0]; tempSpec.name[tempSpec.name[0]] = ':'; } /* Put the object name in first */ result = PtrToHand(&tempSpec.name[1], fullPath, tempSpec.name[0]); if ( result == noErr ) { /* Get the ancestor directory names */ pb.dirInfo.ioNamePtr = tempSpec.name; pb.dirInfo.ioVRefNum = tempSpec.vRefNum; pb.dirInfo.ioDrParID = tempSpec.parID; do /* loop until we have an error or find the root directory */ { pb.dirInfo.ioFDirIndex = -1; pb.dirInfo.ioDrDirID = pb.dirInfo.ioDrParID; result = PBGetCatInfoSync(&pb); if ( result == noErr ) { /* Append colon to directory name */ ++tempSpec.name[0]; tempSpec.name[tempSpec.name[0]] = ':'; /* Add directory name to beginning of fullPath */ (void) Munger(*fullPath, 0, NULL, 0, &tempSpec.name[1], tempSpec.name[0]); result = MemError(); } } while ( (result == noErr) && (pb.dirInfo.ioDrDirID != fsRtDirID) ); } } } if ( result == noErr ) { /* Return the length */ *fullPathLength = InlineGetHandleSize(*fullPath); result = realResult; /* return realResult in case it was fnfErr */ } else { /* Dispose of the handle and return NULL and zero length */ if ( *fullPath != NULL ) { DisposeHandle(*fullPath); } *fullPath = NULL; *fullPathLength = 0; } return ( result ); } /*****************************************************************************/ pascal OSErr FSpLocationFromFullPath(short fullPathLength, const void *fullPath, FSSpec *spec) { AliasHandle alias; OSErr result; Boolean wasChanged; Str32 nullString; /* Create a minimal alias from the full pathname */ nullString[0] = 0; /* null string to indicate no zone or server name */ result = NewAliasMinimalFromFullPath(fullPathLength, fullPath, nullString, nullString, &alias); if ( result == noErr ) { /* Let the Alias Manager resolve the alias. */ result = ResolveAlias(NULL, alias, spec, &wasChanged); DisposeHandle((Handle)alias); /* Free up memory used */ } return ( result ); } /*****************************************************************************/ pascal OSErr GetFullPath(short vRefNum, long dirID, ConstStr255Param name, short *fullPathLength, Handle *fullPath) { OSErr result; FSSpec spec; *fullPathLength = 0; *fullPath = NULL; result = FSMakeFSSpecCompat(vRefNum, dirID, name, &spec); if ( (result == noErr) || (result == fnfErr) ) { result = FSpGetFullPath(&spec, fullPathLength, fullPath); } return ( result ); } /*****************************************************************************/ pascal OSErr ChangeCreatorType(short vRefNum, long dirID, ConstStr255Param name, OSType creator, OSType fileType) { CInfoPBRec pb; OSErr error; short realVRefNum; long parID; pb.hFileInfo.ioNamePtr = (StringPtr)name; pb.hFileInfo.ioVRefNum = vRefNum; pb.hFileInfo.ioDirID = dirID; pb.hFileInfo.ioFDirIndex = 0; /* use ioNamePtr and ioDirID */ error = PBGetCatInfoSync(&pb); if ( error == noErr ) { if ( (pb.hFileInfo.ioFlAttrib & ioDirMask) == 0 ) /* if file */ { /* save parent dirID for BumpDate call */ parID = pb.hFileInfo.ioFlParID; /* If creator not 0x00000000, change creator */ if ( creator != (OSType)0x00000000 ) { pb.hFileInfo.ioFlFndrInfo.fdCreator = creator; } /* If fileType not 0x00000000, change fileType */ if ( fileType != (OSType)0x00000000 ) { pb.hFileInfo.ioFlFndrInfo.fdType = fileType; } pb.hFileInfo.ioDirID = dirID; error = PBSetCatInfoSync(&pb); /* now, save the new information back to disk */ if ( (error == noErr) && (parID != fsRtParID) ) /* can't bump fsRtParID */ { /* get the real vRefNum in case a full pathname was passed */ error = DetermineVRefNum(name, vRefNum, &realVRefNum); if ( error == noErr ) { error = BumpDate(realVRefNum, parID, NULL); /* and bump the parent directory's mod date to wake up the Finder */ /* to the change we just made */ } } } else { /* it was a directory, not a file */ error = notAFileErr; } } return ( error ); } /*****************************************************************************/ pascal OSErr FSpChangeCreatorType(const FSSpec *spec, OSType creator, OSType fileType) { return ( ChangeCreatorType(spec->vRefNum, spec->parID, spec->name, creator, fileType) ); } /*****************************************************************************/ pascal OSErr BumpDate(short vRefNum, long dirID, ConstStr255Param name) /* Given a file or directory, change its modification date to the current date/time. */ { CInfoPBRec pb; Str31 tempName; OSErr error; unsigned long secs; /* Protection against File Sharing problem */ if ( (name == NULL) || (name[0] == 0) ) { tempName[0] = 0; pb.hFileInfo.ioNamePtr = tempName; pb.hFileInfo.ioFDirIndex = -1; /* use ioDirID */ } else { pb.hFileInfo.ioNamePtr = (StringPtr)name; pb.hFileInfo.ioFDirIndex = 0; /* use ioNamePtr and ioDirID */ } pb.hFileInfo.ioVRefNum = vRefNum; pb.hFileInfo.ioDirID = dirID; error = PBGetCatInfoSync(&pb); if ( error == noErr ) { GetDateTime(&secs); /* set mod date to current date, or one second into the future if mod date = current date */ pb.hFileInfo.ioFlMdDat = (secs == pb.hFileInfo.ioFlMdDat) ? (++secs) : (secs); if ( pb.dirInfo.ioNamePtr == tempName ) { pb.hFileInfo.ioDirID = pb.hFileInfo.ioFlParID; } else { pb.hFileInfo.ioDirID = dirID; } error = PBSetCatInfoSync(&pb); } return ( error ); } /*****************************************************************************/ pascal OSErr FSpBumpDate(const FSSpec *spec) { return ( BumpDate(spec->vRefNum, spec->parID, spec->name) ); } /*****************************************************************************/ pascal OSErr OnLine(FSSpecPtr volumes, short reqVolCount, short *actVolCount, short *volIndex) { HParamBlockRec pb; OSErr error = noErr; FSSpec *endVolArray; if ( *volIndex > 0 ) { *actVolCount = 0; for ( endVolArray = volumes + reqVolCount; (volumes < endVolArray) && (error == noErr); ++volumes ) { pb.volumeParam.ioNamePtr = (StringPtr) & volumes->name; pb.volumeParam.ioVolIndex = *volIndex; error = PBHGetVInfoSync(&pb); if ( error == noErr ) { volumes->parID = fsRtParID; /* the root directory's parent is 1 */ volumes->vRefNum = pb.volumeParam.ioVRefNum; ++*volIndex; ++*actVolCount; } } } else { error = paramErr; } return ( error ); } /*****************************************************************************/ pascal OSErr DTGetComment(short vRefNum, long dirID, ConstStr255Param name, Str255 comment) { DTPBRec pb; OSErr error; short dtRefNum; Boolean newDTDatabase; if (comment != NULL) { comment[0] = 0; /* return nothing by default */ /* attempt to open the desktop database */ error = DTOpen(name, vRefNum, &dtRefNum, &newDTDatabase); if ( error == noErr ) { /* There was a desktop database and it's now open */ if ( !newDTDatabase ) { pb.ioDTRefNum = dtRefNum; pb.ioNamePtr = (StringPtr)name; pb.ioDirID = dirID; pb.ioDTBuffer = (Ptr)&comment[1]; /* ** IMPORTANT NOTE #1: Inside Macintosh says that comments ** are up to 200 characters. While that may be correct for ** the HFS file system's Desktop Manager, other file ** systems (such as Apple Photo Access) return up to ** 255 characters. Make sure the comment buffer is a Str255 ** or you'll regret it. ** ** IMPORTANT NOTE #2: Although Inside Macintosh doesn't ** mention it, ioDTReqCount is a input field to ** PBDTGetCommentSync. Some file systems (like HFS) ignore ** ioDTReqCount and always return the full comment -- ** others (like AppleShare) respect ioDTReqCount and only ** return up to ioDTReqCount characters of the comment. */ pb.ioDTReqCount = sizeof(Str255) - 1; error = PBDTGetCommentSync(&pb); if (error == noErr) { comment[0] = (unsigned char)pb.ioDTActCount; } } } else { /* There is no desktop database - try the Desktop file */ error = GetCommentFromDesktopFile(vRefNum, dirID, name, comment); if ( error != noErr ) { error = afpItemNotFound; /* return an expected error */ } } } else { error = paramErr; } return (error); } /*****************************************************************************/ pascal OSErr FSpDTGetComment(const FSSpec *spec, Str255 comment) { return (DTGetComment(spec->vRefNum, spec->parID, spec->name, comment)); } /*****************************************************************************/ pascal OSErr DTSetComment(short vRefNum, long dirID, ConstStr255Param name, ConstStr255Param comment) { DTPBRec pb; OSErr error; short dtRefNum; Boolean newDTDatabase; error = DTOpen(name, vRefNum, &dtRefNum, &newDTDatabase); if ( error == noErr ) { pb.ioDTRefNum = dtRefNum; pb.ioNamePtr = (StringPtr)name; pb.ioDirID = dirID; pb.ioDTBuffer = (Ptr)&comment[1]; /* Truncate the comment to 200 characters just in case */ /* some file system doesn't range check */ if ( comment[0] <= 200 ) { pb.ioDTReqCount = comment[0]; } else { pb.ioDTReqCount = 200; } error = PBDTSetCommentSync(&pb); } return (error); } /*****************************************************************************/ pascal OSErr FSpDTSetComment(const FSSpec *spec, ConstStr255Param comment) { return (DTSetComment(spec->vRefNum, spec->parID, spec->name, comment)); } /*****************************************************************************/ pascal OSErr DTOpen(ConstStr255Param volName, short vRefNum, short *dtRefNum, Boolean *newDTDatabase) { OSErr error; GetVolParmsInfoBuffer volParmsInfo; long infoSize; DTPBRec pb; /* Check for volume Desktop Manager support before calling */ infoSize = sizeof(GetVolParmsInfoBuffer); error = HGetVolParms(volName, vRefNum, &volParmsInfo, &infoSize); if ( error == noErr ) { if ( hasDesktopMgr(volParmsInfo) ) { pb.ioNamePtr = (StringPtr)volName; pb.ioVRefNum = vRefNum; error = PBDTOpenInform(&pb); /* PBDTOpenInform informs us if the desktop was just created */ /* by leaving the low bit of ioTagInfo clear (0) */ *newDTDatabase = ((pb.ioTagInfo & 1L) == 0); if ( error == paramErr ) { error = PBDTGetPath(&pb); /* PBDTGetPath doesn't tell us if the database is new */ /* so assume it is not new */ *newDTDatabase = false; } *dtRefNum = pb.ioDTRefNum; } else { error = paramErr; } } return ( error ); } /*****************************************************************************/ /* ** GetCommentFromDesktopFile ** ** Get a file or directory's Finder comment field (if any) from the ** Desktop file's 'FCMT' resources. */ static OSErr GetCommentFromDesktopFile(short vRefNum, long dirID, ConstStr255Param name, Str255 comment) { OSErr error; short commentID; short realVRefNum; Str255 desktopName; short savedResFile; short dfRefNum; StringHandle commentHandle; /* Get the comment ID number */ error = GetCommentID(vRefNum, dirID, name, &commentID); if ( error == noErr ) { if ( commentID != 0 ) /* commentID == 0 means there's no comment */ { error = DetermineVRefNum(name, vRefNum, &realVRefNum); if ( error == noErr ) { error = GetDesktopFileName(realVRefNum, desktopName); if ( error == noErr ) { savedResFile = CurResFile(); /* ** Open the 'Desktop' file in the root directory. (because ** opening the resource file could preload unwanted resources, ** bracket the call with SetResLoad(s)) */ SetResLoad(false); dfRefNum = HOpenResFile(realVRefNum, fsRtDirID, desktopName, fsRdPerm); SetResLoad(true); if ( dfRefNum != -1) { /* Get the comment resource */ commentHandle = (StringHandle)Get1Resource(kFCMTResType, commentID); if ( commentHandle != NULL ) { if ( InlineGetHandleSize((Handle)commentHandle) > 0 ) { BlockMoveData(*commentHandle, comment, *commentHandle[0] + 1); } else { /* no comment available */ error = afpItemNotFound; } } else { /* no comment available */ error = afpItemNotFound; } /* restore the resource chain and close the Desktop file */ UseResFile(savedResFile); CloseResFile(dfRefNum); } else { error = afpItemNotFound; } } else { error = afpItemNotFound; } } } else { error = afpItemNotFound; /* no comment available */ } } return ( error ); } /*****************************************************************************/ pascal OSErr HGetVolParms(ConstStr255Param volName, short vRefNum, GetVolParmsInfoBuffer *volParmsInfo, long *infoSize) { HParamBlockRec pb; OSErr error; pb.ioParam.ioNamePtr = (StringPtr)volName; pb.ioParam.ioVRefNum = vRefNum; pb.ioParam.ioBuffer = (Ptr)volParmsInfo; pb.ioParam.ioReqCount = *infoSize; error = PBHGetVolParmsSync(&pb); if ( error == noErr ) { *infoSize = pb.ioParam.ioActCount; } return ( error ); } /*****************************************************************************/ /* ** GetCommentID ** ** Get the comment ID number for the Desktop file's 'FCMT' resource ID from ** the file or folders fdComment (frComment) field. */ static OSErr GetCommentID(short vRefNum, long dirID, ConstStr255Param name, short *commentID) { CInfoPBRec pb; OSErr error; error = GetCatInfoNoName(vRefNum, dirID, name, &pb); *commentID = pb.hFileInfo.ioFlXFndrInfo.fdComment; return ( error ); } /*****************************************************************************/ /* ** GetDesktopFileName ** ** Get the name of the Desktop file. */ static OSErr GetDesktopFileName(short vRefNum, Str255 desktopName) { OSErr error; HParamBlockRec pb; short index; Boolean found; pb.fileParam.ioNamePtr = desktopName; pb.fileParam.ioVRefNum = vRefNum; pb.fileParam.ioFVersNum = 0; index = 1; found = false; do { pb.fileParam.ioDirID = fsRtDirID; pb.fileParam.ioFDirIndex = index; error = PBHGetFInfoSync(&pb); if ( error == noErr ) { if ( (pb.fileParam.ioFlFndrInfo.fdType == 'FNDR') && (pb.fileParam.ioFlFndrInfo.fdCreator == 'ERIK') ) { found = true; } } ++index; } while ( (error == noErr) && !found ); return ( error ); } /*****************************************************************************/ pascal OSErr XGetVInfo(short volReference, StringPtr volName, short *vRefNum, UnsignedWide *freeBytes, UnsignedWide *totalBytes) { OSErr result; long response; XVolumeParam pb; /* See if large volume support is available */ if ( ( Gestalt(gestaltFSAttr, &response) == noErr ) && ((response & (1L << gestaltFSSupports2TBVols)) != 0) ) { /* Large volume support is available */ pb.ioVRefNum = volReference; pb.ioNamePtr = volName; pb.ioXVersion = 0; /* this XVolumeParam version (0) */ pb.ioVolIndex = 0; /* use ioVRefNum only, return volume name */ result = PBXGetVolInfoSync(&pb); if ( result == noErr ) { /* The volume name was returned in volName (if not NULL) and */ /* we have the volume's vRefNum and allocation block size */ *vRefNum = pb.ioVRefNum; /* return the freeBytes and totalBytes */ *totalBytes = pb.ioVTotalBytes; *freeBytes = pb.ioVFreeBytes; } } else { /* No large volume support */ /* Use HGetVInfo to get the results */ result = HGetVInfo(volReference, volName, vRefNum, &freeBytes->lo, &totalBytes->lo); if ( result == noErr ) { /* zero the high longs of totalBytes and freeBytes */ totalBytes->hi = 0; freeBytes->hi = 0; } } return ( result ); } /*****************************************************************************/ pascal OSErr HGetVInfo(short volReference, StringPtr volName, short *vRefNum, unsigned long *freeBytes, unsigned long *totalBytes) { HParamBlockRec pb; unsigned long allocationBlockSize; unsigned short numAllocationBlocks; unsigned short numFreeBlocks; VCB *theVCB; Boolean vcbFound; OSErr result; /* Use the File Manager to get the real vRefNum */ pb.volumeParam.ioVRefNum = volReference; pb.volumeParam.ioNamePtr = volName; pb.volumeParam.ioVolIndex = 0; /* use ioVRefNum only, return volume name */ result = PBHGetVInfoSync(&pb); if ( result == noErr ) { /* The volume name was returned in volName (if not NULL) and */ /* we have the volume's vRefNum and allocation block size */ *vRefNum = pb.volumeParam.ioVRefNum; allocationBlockSize = (unsigned long)pb.volumeParam.ioVAlBlkSiz; /* System 7.5 (and beyond) pins the number of allocation blocks and */ /* the number of free allocation blocks returned by PBHGetVInfo to */ /* a value so that when multiplied by the allocation block size, */ /* the volume will look like it has $7fffffff bytes or less. This */ /* was done so older applications that use signed math or that use */ /* the GetVInfo function (which uses signed math) will continue to work. */ /* However, the unpinned numbers (which we want) are always available */ /* in the volume's VCB so we'll get those values from the VCB if possible. */ /* Find the volume's VCB */ vcbFound = false; theVCB = (VCB *)(GetVCBQHdr()->qHead); while ( (theVCB != NULL) && !vcbFound ) { /* Check VCB signature before using VCB. Don't have to check for */ /* MFS (0xd2d7) because they can't get big enough to be pinned */ if ( theVCB->vcbSigWord == 0x4244 ) { if ( theVCB->vcbVRefNum == *vRefNum ) { vcbFound = true; } } if ( !vcbFound ) { theVCB = (VCB *)(theVCB->qLink); } } if ( theVCB != NULL ) { /* Found a VCB we can use. Get the un-pinned number of allocation blocks */ /* and the number of free blocks from the VCB. */ numAllocationBlocks = (unsigned short)theVCB->vcbNmAlBlks; numFreeBlocks = (unsigned short)theVCB->vcbFreeBks; } else { /* Didn't find a VCB we can use. Return the number of allocation blocks */ /* and the number of free blocks returned by PBHGetVInfoSync. */ numAllocationBlocks = (unsigned short)pb.volumeParam.ioVNmAlBlks; numFreeBlocks = (unsigned short)pb.volumeParam.ioVFrBlk; } /* Now, calculate freeBytes and totalBytes using unsigned values */ *freeBytes = numFreeBlocks * allocationBlockSize; *totalBytes = numAllocationBlocks * allocationBlockSize; } return ( result ); } /* ** PBXGetVolInfoSync is the glue code needed to make PBXGetVolInfoSync ** File Manager requests from CFM-based programs. At some point, Apple ** will get around to adding this to the standard libraries you link with ** and you'll get a duplicate symbol link error. At that time, just delete ** this code (or comment it out). ** ** Non-CFM 68K programs don't needs this glue (and won't get it) because ** they instead use the inline assembly glue found in the Files.h interface ** file. */ #if __WANTPASCALELIMINATION #undef pascal #endif #if GENERATINGCFM pascal OSErr PBXGetVolInfoSync(XVolumeParamPtr paramBlock) { enum { kXGetVolInfoSelector = 0x0012, /* Selector for XGetVolInfo */ uppFSDispatchProcInfo = kRegisterBased | REGISTER_RESULT_LOCATION(kRegisterD0) | RESULT_SIZE(SIZE_CODE(sizeof(OSErr))) | REGISTER_ROUTINE_PARAMETER(1, kRegisterD1, SIZE_CODE(sizeof(long))) /* trap word */ | REGISTER_ROUTINE_PARAMETER(2, kRegisterD0, SIZE_CODE(sizeof(long))) /* selector */ | REGISTER_ROUTINE_PARAMETER(3, kRegisterA0, SIZE_CODE(sizeof(XVolumeParamPtr))) }; return ( CallOSTrapUniversalProc(NGetTrapAddress(_FSDispatch, OSTrap), uppFSDispatchProcInfo, _FSDispatch, kXGetVolInfoSelector, paramBlock) ); } #endif #if __WANTPASCALELIMINATION #define pascal #endif /*****************************************************************************/ pascal OSErr GetDirName(short vRefNum, long dirID, Str31 name) { CInfoPBRec pb; OSErr error; if ( name != NULL ) { pb.dirInfo.ioNamePtr = name; pb.dirInfo.ioVRefNum = vRefNum; pb.dirInfo.ioDrDirID = dirID; pb.dirInfo.ioFDirIndex = -1; /* get information about ioDirID */ error = PBGetCatInfoSync(&pb); } else { error = paramErr; } return ( error ); } /*****************************************************************************/ pascal OSErr GetVolFileSystemID(ConstStr255Param pathname, short vRefNum, short *fileSystemID) { HParamBlockRec pb; OSErr error; error = GetVolumeInfoNoName(pathname,vRefNum, &pb); if ( error == noErr ) { *fileSystemID = pb.volumeParam.ioVFSID; } return ( error ); } /*****************************************************************************/ pascal OSErr GetDInfo(short vRefNum, long dirID, ConstStr255Param name, DInfo *fndrInfo) { CInfoPBRec pb; OSErr error; error = GetCatInfoNoName(vRefNum, dirID, name, &pb); if ( error == noErr ) { if ( (pb.dirInfo.ioFlAttrib & ioDirMask) != 0 ) { /* it's a directory, return the DInfo */ *fndrInfo = pb.dirInfo.ioDrUsrWds; } else { /* oops, a file was passed */ error = dirNFErr; } } return ( error ); } /*****************************************************************************/ pascal OSErr FSpGetDInfo(const FSSpec *spec, DInfo *fndrInfo) { return ( GetDInfo(spec->vRefNum, spec->parID, spec->name, fndrInfo) ); } zip30/macos/source/macstuff.h0100644000076400000060000000106207251361020014337 0ustar edisk/* Copyright (c) 1990-2001 Info-ZIP. All rights reserved. See the accompanying file LICENSE, version 2000-Apr-09 or later (the contents of which are also included in zip.h) for terms of use. If, for some reason, all these files are missing, the Info-ZIP license also may be found at: ftp://ftp.info-zip.org/pub/infozip/license.html */ #ifndef _MACSTUFF_H #define _MACSTUFF_H 1 #include "MoreFilesExtras.h" #include "MoreDesktopMgr.h" #include "MoreFiles.h" #include "FSpCompat.h" #include "FullPath.h" #endif /* _MACSTUFF_H */ zip30/macos/source/mactime.c0100644000076400000060000002534010154332006014144 0ustar edisk/* Copyright (c) 1990-2000 Info-ZIP. All rights reserved. See the accompanying file LICENSE, version 2000-Apr-09 or later (the contents of which are also included in zip.h) for terms of use. If, for some reason, all these files are missing, the Info-ZIP license also may be found at: ftp://ftp.info-zip.org/pub/infozip/license.html */ /* ----------------------------------------------------------------------------- The original functions (Metrowerks Codewarrior pro 3.0) gmtime, localtime, mktime and time do not work correctly. The supplied link library mactime.c contains replacement functions for them. * Caveat: On a Mac, we only know the GMT and DST offsets for * the current time, not for the time in question. * Mac has no support for DST handling. * DST changeover is all manually set by the user. ------------------------------------------------------------------------------*/ /*****************************************************************************/ /* Includes */ /*****************************************************************************/ #include #include #include #include #include #include "mactime.h" /* The MacOS function GetDateTime returns the number of seconds elapsed since midnight, January 1, 1904. */ const unsigned long MacOS_2_Unix = 2082844800L; /*****************************************************************************/ /* Macros, typedefs */ /*****************************************************************************/ #ifndef TEST_TIME_LIB #define my_gmtime gmtime #define my_localtime localtime #define my_mktime mktime #define my_time time #endif /*****************************************************************************/ /* Prototypes */ /*****************************************************************************/ /* internal prototypes */ static void clear_tm(struct tm * tm); static long GMTDelta(void); static Boolean DaylightSaving(void); static time_t GetTimeMac(void); static time_t Mactime(time_t *timer); static void normalize(int *i,int *j,int norm); static struct tm *time2tm(const time_t *timer); static time_t tm2time(struct tm *tp); /* Because serial port and SLIP conflict with ReadXPram calls, we cache the call here so we don't hang on calling ReadLocation() */ static void myReadLocation(MachineLocation * loc); /* prototypes for STD lib replacement functions */ struct tm *my_gmtime(const time_t *t); struct tm *my_localtime(const time_t *t); time_t my_mktime(struct tm *tp); time_t my_time(time_t *t); /*****************************************************************************/ /* Functions */ /*****************************************************************************/ /* * Mac file times are based on 1904 Jan 1 00:00 local time, * not 1970 Jan 1 00:00 UTC. * So we have to convert the time stamps into UNIX UTC * compatible values. */ time_t MacFtime2UnixFtime(unsigned long macftime) { long UTCoffset; GetGMToffsetMac(macftime, &UTCoffset); MACOS_TO_UNIX(macftime); macftime -= UTCoffset; return macftime; } /* * Mac file times are based on 1904 Jan 1 00:00 local time, * not 1970 Jan 1 00:00 UTC. * So we have to convert the time stamps into MacOS local * compatible values. */ unsigned long UnixFtime2MacFtime(time_t unxftime) { long UTCoffset; unsigned long macftime = unxftime; UNIX_TO_MACOS(macftime); GetGMToffsetMac(macftime, &UTCoffset); macftime += UTCoffset; return macftime; } /* * This function convert a file-localtime to an another * file-localtime. */ time_t AdjustForTZmoveMac(unsigned long macloctim, long s_gmtoffs) { time_t MacGMTTime; long UTCoffset; /* convert macloctim into corresponding UTC value */ MacGMTTime = macloctim - s_gmtoffs; GetGMToffsetMac(macloctim, &UTCoffset); return (MacGMTTime + UTCoffset); } /* AdjustForTZmove() */ /* * This function calculates the difference between the supplied Mac * ftime value (local time) and the corresponding UTC time in seconds. */ Boolean GetGMToffsetMac(unsigned long mactime, long *UTCoffset) { mactime = mactime; /* * Caveat: On a Mac, we only know the GMT and DST offsets for * the current time, not for the time in question. * Mac has no support for DST handling. * DST changeover is all manually set by the user. May be later I can include a support of GMT offset calculation for the time in question here. */ *UTCoffset = GMTDelta(); return true; } /***************************************************************************** * Standard Library Replacement Functions * gmtime(), mktime(), localtime(), time() * * The unix epoch is used here. * These functions gmtime(), mktime(), localtime() and time() * expects and returns unix times. * * At midnight Jan. 1, 1970 GMT, the local time was * midnight Jan. 1, 1970 + GMTDelta(). * * *****************************************************************************/ struct tm *my_gmtime(const time_t *timer) { return time2tm(timer); } struct tm *my_localtime(const time_t *timer) { time_t maclocal; maclocal = *timer; maclocal += GMTDelta(); return time2tm(&maclocal); } time_t my_mktime(struct tm *tp) { time_t maclocal; maclocal = tm2time(tp); maclocal -= GMTDelta(); return maclocal; } time_t my_time(time_t *time) { time_t tmp_time; GetDateTime(&tmp_time); MACOS_TO_UNIX(tmp_time); if (time) { *time = tmp_time; } return tmp_time; } /*****************************************************************************/ /* static module level functions /*****************************************************************************/ /* * The geographic location and time zone information of a Mac * are stored in extended parameter RAM. The ReadLocation * produdure uses the geographic location record, MachineLocation, * to read the geographic location and time zone information in * extended parameter RAM. * * Because serial port and SLIP conflict with ReadXPram calls, * we cache the call here. * * Caveat: this caching will give the wrong result if a session * extend across the DST changeover time, but * this function resets itself every 2 hours. */ static void myReadLocation(MachineLocation * loc) { static MachineLocation storedLoc; /* InsideMac, OSUtilities, page 4-20 */ static time_t first_call = 0, last_call = 86400; if ((last_call - first_call) > 7200) { GetDateTime(&first_call); ReadLocation(&storedLoc); } GetDateTime(&last_call); *loc = storedLoc; } static Boolean DaylightSaving(void) { MachineLocation loc; unsigned char dlsDelta; myReadLocation(&loc); dlsDelta = loc.u.dlsDelta; return (dlsDelta != 0); } /* current local time = GMTDelta() + GMT GMT = local time - GMTDelta() */ static long GMTDelta(void) { MachineLocation loc; long gmtDelta; myReadLocation(&loc); /* * On a Mac, the GMT value is in seconds east of GMT. For example, * San Francisco is at -28,800 seconds (8 hours * 3600 seconds per hour) * east of GMT. The gmtDelta field is a 3-byte value contained in a * long word, so you must take care to get it properly. */ gmtDelta = loc.u.gmtDelta & 0x00FFFFFF; if ((gmtDelta & 0x00800000) != 0) { gmtDelta |= 0xFF000000; } return gmtDelta; } /* This routine simulates stdclib time(), time in seconds since 1.1.1970 The time is in GMT */ static time_t GetTimeMac(void) { unsigned long maclocal; /* * Get the current time expressed as the number of seconds * elapsed since the Mac epoch, midnight, Jan. 1, 1904 (local time). * On a Mac, current time accuracy is up to a second. */ GetDateTime(&maclocal); /* Get Mac local time */ maclocal -= GMTDelta(); /* Get Mac GMT */ MACOS_TO_UNIX(maclocal); return maclocal; /* return unix GMT */ } /* * clear_tm - sets a broken-down time to the equivalent of 1970/1/1 00:00:00 */ static void clear_tm(struct tm * tm) { tm->tm_sec = 0; tm->tm_min = 0; tm->tm_hour = 0; tm->tm_mday = 1; tm->tm_mon = 0; tm->tm_year = 0; tm->tm_wday = 1; tm->tm_yday = 0; tm->tm_isdst = -1; } static void normalize(int *i,int *j,int norm) { while(*i < 0) { *i += norm; (*j)--; } while(*i >= norm) { *i -= norm; (*j)++; } } /* Returns the GMT times */ static time_t Mactime(time_t *timer) { time_t t = GetTimeMac(); if (timer != NULL) *timer = t; return t; } static struct tm *time2tm(const time_t *timer) { DateTimeRec dtr; MachineLocation loc; time_t macLocal = *timer; static struct tm statictime; static const short monthday[12] = {0, 31, 59, 90, 120, 151, 181, 212, 243, 273, 304, 334}; UNIX_TO_MACOS(macLocal); SecondsToDate(macLocal, &dtr); statictime.tm_sec = dtr.second; /* second, from 0 to 59 */ statictime.tm_min = dtr.minute; /* minute, from 0 to 59 */ statictime.tm_hour = dtr.hour; /* hour, from 0 to 23 */ statictime.tm_mday = dtr.day; /* day of the month, from 1 to 31 */ statictime.tm_mon = dtr.month - 1; /* month, 1= January and 12 = December */ statictime.tm_year = dtr.year - 1900; /* year, ranging from 1904 to 2040 */ statictime.tm_wday = dtr.dayOfWeek - 1; /* day of the week, 1 = Sun, 7 = Sat */ statictime.tm_yday = monthday[statictime.tm_mon] + statictime.tm_mday - 1; if (2 < statictime.tm_mon && !(statictime.tm_year & 3)) { ++statictime.tm_yday; } myReadLocation(&loc); statictime.tm_isdst = DaylightSaving(); return(&statictime); } static time_t tm2time(struct tm *tp) { time_t intMacTime; DateTimeRec dtr; normalize(&tp->tm_sec, &tp->tm_min, 60); normalize(&tp->tm_min, &tp->tm_hour,60); normalize(&tp->tm_hour,&tp->tm_mday,24); normalize(&tp->tm_mon, &tp->tm_year,12); dtr.year = tp->tm_year + 1900; /* years since 1900 */ dtr.month = tp->tm_mon + 1; /* month, 0 = January and 11 = December */ dtr.day = tp->tm_mday; /* day of the month, from 1 to 31 */ dtr.hour = tp->tm_hour; /* hour, from 0 to 23 */ dtr.minute = tp->tm_min; /* minute, from 0 to 59 */ dtr.second = tp->tm_sec; /* second, from 0 to 59 */ DateToSeconds(&dtr, &intMacTime); MACOS_TO_UNIX(intMacTime); return intMacTime; } zip30/macos/source/mactime.h0100644000076400000060000000432507076031116014160 0ustar edisk/* Copyright (c) 1990-2000 Info-ZIP. All rights reserved. See the accompanying file LICENSE, version 2000-Apr-09 or later (the contents of which are also included in zip.h) for terms of use. If, for some reason, all these files are missing, the Info-ZIP license also may be found at: ftp://ftp.info-zip.org/pub/infozip/license.html */ #ifndef _MACTIME_H_ #define _MACTIME_H_ /* ----------------------------------------------------------------------------- The original functions (Metrowerks Codewarrior pro 3.0) gmtime, localtime, mktime and time do not work correctly. The supplied link library mactime.c contains replacement functions for them. * Caveat: On a Mac, we only know the GMT and DST offsets for * the current time, not for the time in question. * Mac has no support for DST handling. * DST changeover is all manually set by the user. ------------------------------------------------------------------------------*/ #include #include /*****************************************************************************/ /* Macros, typedefs */ /*****************************************************************************/ /* * ARGH. Mac times are based on 1904 Jan 1 00:00, not 1970 Jan 1 00:00. * So we have to diddle time_t's appropriately: add or subtract 66 years' * worth of seconds == number of days times 86400 == (66*365 regular days + * 17 leap days ) * 86400 == (24090 + 17) * 86400 == 2082844800L seconds. * We hope time_t is an unsigned long (ulg) on the Macintosh... */ /* This Offset is only used by MacFileDate_to_UTime() */ #define MACOS_TO_UNIX(x) (x) -= (unsigned long)MacOS_2_Unix #define UNIX_TO_MACOS(x) (x) += (unsigned long)MacOS_2_Unix /* The MacOS function GetDateTime returns the number of seconds elapsed since midnight, January 1, 1904. */ extern const unsigned long MacOS_2_Unix; /* prototypes for public utility functions */ time_t MacFtime2UnixFtime(unsigned long macftime); unsigned long UnixFtime2MacFtime(time_t unxftime); time_t AdjustForTZmoveMac(unsigned long macloctim, long s_gmtoffs); Boolean GetGMToffsetMac(unsigned long macftime, long *UTCoffset); #endif zip30/macos/source/pathname.c0100644000076400000060000004434707607765374014365 0ustar edisk/* Copyright (c) 1990-2003 Info-ZIP. All rights reserved. See the accompanying file LICENSE, version 2000-Apr-09 or later (the contents of which are also included in zip.h) for terms of use. If, for some reason, all these files are missing, the Info-ZIP license also may be found at: ftp://ftp.info-zip.org/pub/infozip/license.html */ /*--------------------------------------------------------------------------- pathname.c Function dealing with the pathname. Mostly C-string work. ---------------------------------------------------------------------------*/ /*****************************************************************************/ /* Includes */ /*****************************************************************************/ #include #include #include #include #include "pathname.h" #include "helpers.h" #include "macstuff.h" /*****************************************************************************/ /* Global Vars */ /*****************************************************************************/ const char ResourceMark[] = "XtraStuf.mac:"; /* see also macos.c */ #include "zip.h" /*****************************************************************************/ /* Functions */ /*****************************************************************************/ /* *---------------------------------------------------------------------- * * FSpFindFolder -- * * This function is a version of the FindFolder function that * returns the result as a FSSpec rather than a vRefNum and dirID. * * Results: * Results will be simaler to that of the FindFolder function. * * Side effects: * None. * *---------------------------------------------------------------------- */ OSErr FSpFindFolder( short vRefNum, /* Volume reference number. */ OSType folderType, /* Folder type taken by FindFolder. */ Boolean createFolder, /* Should we create it if non-existant. */ FSSpec *spec) /* Pointer to resulting directory. */ { short foundVRefNum; long foundDirID; OSErr err; err = FindFolder(vRefNum, folderType, createFolder, &foundVRefNum, &foundDirID); if (err != noErr) { return err; } err = FSMakeFSSpecCompat(foundVRefNum, foundDirID, "\p", spec); return err; } /* ** return volumename from pathname ** */ unsigned short GetVolumeFromPath(const char *FullPath, char *VolumeName) { const char *VolEnd, *tmpPtr1; char *tmpPtr2 = VolumeName; AssertStr(FullPath,"GetVolumeFromPath") for (VolEnd = FullPath; *VolEnd != '\0' && *VolEnd != ':'; VolEnd++) ; if (*VolEnd == '\0') return 0; for (tmpPtr1 = FullPath; tmpPtr1 != VolEnd;) { *tmpPtr2++ = *tmpPtr1++; } *tmpPtr2 = '\0'; return (unsigned short) strlen(VolumeName); } /***********************************/ /* Function FindNewExtractFolder() */ /***********************************/ char *FindNewExtractFolder(char *ExtractPath, Boolean uniqueFolder) { char buffer[NAME_MAX], *tmpPtr, *namePtr; char *last_dotpos = ExtractPath; short count = 0, folderCount = 0; OSErr err; FSSpec Spec; long theDirID; Boolean isDirectory; unsigned short namelen, pathlen = strlen(ExtractPath); unsigned long ext_length = 0; unsigned long num_to_cut = 0; long firstpart_length = pathlen; AssertStr(ExtractPath,"FindNewExtractFolder ExtractPath == NULL") for (tmpPtr = ExtractPath; *tmpPtr; tmpPtr++) if (*tmpPtr == ':') { folderCount++; namePtr = tmpPtr; } if (folderCount > 1) { namelen = strlen(namePtr); } else { namelen = strlen(ExtractPath); } if (uniqueFolder) { for (count = 0; count < 99; count++) { memset(buffer,0,sizeof(buffer)); if (namelen >= 28) ExtractPath[pathlen-2] = 0x0; else ExtractPath[pathlen-1] = 0x0; sprintf(buffer,"%s%d",ExtractPath,count); GetCompletePath(ExtractPath, buffer, &Spec,&err); err = FSpGetDirectoryID(&Spec, &theDirID, &isDirectory); if (err == -43) break; } } else { /* Look for the last extension pos */ for (tmpPtr = ExtractPath; *tmpPtr; tmpPtr++) if (*tmpPtr == '.') last_dotpos = tmpPtr; ext_length = strlen(last_dotpos); if (ext_length < 6) { /* up to 5 chars are treated as a */ /* normal extension like ".html" or ".class" */ int nameLength = last_dotpos - ExtractPath; if (nameLength > 1) { ExtractPath[nameLength] = 0x0; } else { ExtractPath[pathlen-1] = 0x0; } } else { ExtractPath[pathlen-1] = 0x0; } GetCompletePath(ExtractPath, ExtractPath, &Spec,&err); } /* Foldernames must always end with a colon */ sstrcat(ExtractPath,":"); return ExtractPath; } /* ** creates an archive file name ** */ void createArchiveName(char *thePath) { char *tmpPtr, *namePtr; short folderCount = 0; unsigned short namelen, pathlen = strlen(thePath); if (thePath[pathlen-1] == ':') thePath[pathlen-1] = 0x0; for (tmpPtr = thePath; *tmpPtr; tmpPtr++) if (*tmpPtr == ':') { folderCount++; namePtr = tmpPtr; } namelen = strlen(namePtr); /* we have to eliminate illegal chars: * The name space for Mac filenames and Zip filenames (unix style names) * do both include all printable extended-ASCII characters. The only * difference we have to take care of is the single special character * used as path delimiter: * ':' on MacOS and '/' on Unix and '\\' on Dos. * So, to convert between Mac filenames and Unix filenames without any * loss of information, we simply interchange ':' and '/'. Additionally, * we try to convert the coding of the extended-ASCII characters into * InfoZip's standard ISO 8859-1 codepage table. */ MakeCompatibleString(namePtr, '/', '_', '.', '-', -1); /* Avoid filenames like: "Archive..zip" */ if (thePath[pathlen-1] == '.') { thePath[pathlen-1] = 0; } if (folderCount >= 1) { /* path contains at least one folder */ if (namelen >= 28) { pathlen = pathlen-4; } thePath[pathlen] = '.'; thePath[pathlen+1] = 'z'; thePath[pathlen+2] = 'i'; thePath[pathlen+3] = 'p'; thePath[pathlen+4] = 0x0; return; } else { /* path contains no folder */ FindDesktopFolder(thePath); createArchiveName(thePath); } } /* ** finds the desktop-folder on a volume with ** largest amount of free-space. */ void FindDesktopFolder(char *Path) { char buffer[255]; FSSpec volumes[50]; /* 50 Volumes should be enough */ short actVolCount, volIndex = 1, VolCount = 0; OSErr err; short i, foundVRefNum; FSSpec spec; UInt64 freeBytes; UInt64 totalBytes; UInt64 MaxFreeBytes; err = OnLine(volumes, 50, &actVolCount, &volIndex); printerr("OnLine:", (err != -35) && (err != 0), err, __LINE__, __FILE__, ""); MaxFreeBytes = 0; for (i=0; i < actVolCount; i++) { XGetVInfo(volumes[i].vRefNum, volumes[i].name, &volumes[i].vRefNum, &freeBytes, &totalBytes); if (MaxFreeBytes < freeBytes) { MaxFreeBytes = freeBytes; foundVRefNum = volumes[i].vRefNum; } if ((freeBytes == 0) && (MaxFreeBytes < freeBytes)) { MaxFreeBytes = freeBytes; foundVRefNum = volumes[i].vRefNum; } } FSpFindFolder(foundVRefNum, kDesktopFolderType, kDontCreateFolder,&spec); GetFullPathFromSpec(buffer, &spec , &err); sstrcat(buffer,Path); sstrcpy(Path,buffer); } /* ** return the path without the filename ** */ char *TruncFilename(char *DirPath, const char *FilePath) { char *tmpPtr; char *dirPtr = NULL; AssertStr(DirPath,"TruncFilename") Assert_it(Spec,"TruncFilename","") sstrcpy(DirPath, FilePath); for (tmpPtr = DirPath; *tmpPtr; tmpPtr++) if (*tmpPtr == ':') dirPtr = tmpPtr; if (dirPtr) *++dirPtr = '\0'; else printerr("TruncFilename: FilePath has no Folders", -1, -1, __LINE__, __FILE__, FilePath); return DirPath; } /* ** return only filename ** */ char *GetFilename(char *FileName, const char *FilePath) { const char *tmpPtr; const char *dirPtr = NULL; Assert_it(FileName,"GetFilename","") Assert_it(FilePath,"GetFilename","") for (tmpPtr = FilePath; *tmpPtr; tmpPtr++) { if (*tmpPtr == ':') { dirPtr = tmpPtr; } } if (dirPtr) { ++dirPtr; /* jump over the ':' */ } else { return strcpy(FileName, FilePath); /* FilePath has no Folders */ } return strcpy(FileName, dirPtr); } /* ** return fullpathname from folder/dir-id ** */ char *GetFullPathFromID(char *CompletePath, short vRefNum, long dirID, ConstStr255Param name, OSErr *err) { FSSpec spec; *err = FSMakeFSSpecCompat(vRefNum, dirID, name, &spec); printerr("FSMakeFSSpecCompat:", (*err != -43) && (*err != 0), *err, __LINE__, __FILE__, ""); if ( (*err == noErr) || (*err == fnfErr) ) { return GetFullPathFromSpec(CompletePath, &spec, err); } return NULL; } /* ** convert real-filename to archive-filename ** */ char *Real2RfDfFilen(char *RfDfFilen, const char *RealPath, short CurrentFork, short MacZipMode, Boolean DataForkOnly) { AssertStr(RealPath,"Real2RfDfFilen") AssertStr(RfDfFilen,"Real2RfDfFilen") if (DataForkOnly) /* make no changes */ { return sstrcpy(RfDfFilen, RealPath); } switch (MacZipMode) { case JohnnyLee_EF: { sstrcpy(RfDfFilen, RealPath); if (CurrentFork == DataFork) /* data-fork */ return sstrcat(RfDfFilen, "d"); if (CurrentFork == ResourceFork) /* resource-fork */ return sstrcat(RfDfFilen, "r"); break; } case NewZipMode_EF: { switch (CurrentFork) { case DataFork: { sstrcpy(RfDfFilen, RealPath); return RfDfFilen; /* data-fork */ break; } case ResourceFork: { sstrcpy(RfDfFilen, ResourceMark); sstrcat(RfDfFilen, RealPath); /* resource-fork */ return RfDfFilen; break; } default: { printerr("Real2RfDfFilen:", -1, -1, __LINE__, __FILE__, RealPath); return NULL; /* function should never reach this point */ } } break; } default: { printerr("Real2RfDfFilen:", -1, -1, __LINE__, __FILE__, RealPath); return NULL; /* function should never reach this point */ } } printerr("Real2RfDfFilen:", -1, -1, __LINE__, __FILE__, RealPath); return NULL; /* function should never come reach this point */ } /* ** convert archive-filename into a real filename ** */ char *RfDfFilen2Real(char *RealFn, const char *RfDfFilen, short MacZipMode, Boolean DataForkOnly, short *CurrentFork) { short length; int result; AssertStr(RfDfFilen,"RfDfFilen2Real") if (DataForkOnly || (MacZipMode == UnKnown_EF) || (MacZipMode < JohnnyLee_EF)) { *CurrentFork = DataFork; return sstrcpy(RealFn,RfDfFilen); } result = strncmp(RfDfFilen, ResourceMark, sizeof(ResourceMark)-2); if (result == 0) { MacZipMode = NewZipMode_EF; } switch (MacZipMode) { case JohnnyLee_EF: { sstrcpy(RealFn, RfDfFilen); length = strlen(RealFn); /* determine Fork type */ if (RealFn[length-1] == 'd') *CurrentFork = DataFork; else *CurrentFork = ResourceFork; RealFn[length-1] = '\0'; /* simply cut one char */ return RealFn; break; } case NewZipMode_EF: { /* determine Fork type */ result = strncmp(RfDfFilen, ResourceMark, sizeof(ResourceMark)-2); if (result != 0) { *CurrentFork = DataFork; sstrcpy(RealFn, RfDfFilen); return RealFn; /* data-fork */ } else { *CurrentFork = ResourceFork; if (strlen(RfDfFilen) > (sizeof(ResourceMark) - 1)) { sstrcpy(RealFn, &RfDfFilen[sizeof(ResourceMark)-1]); } else RealFn[0] = '\0'; return RealFn; /* resource-fork */ } break; } default: { *CurrentFork = NoFork; printerr("RfDfFilen2Real():", -1, MacZipMode, __LINE__, __FILE__, RfDfFilen); return NULL; /* function should never reach this point */ } } printerr("RfDfFilen2Real():", -1, MacZipMode, __LINE__, __FILE__, RfDfFilen); return NULL; /* function should never reach this point */ } /* ** return the applications name (argv[0]) ** */ char *GetAppName(void) { ProcessSerialNumber psn; static Str255 AppName; ProcessInfoRec pinfo; OSErr err; GetCurrentProcess(&psn); pinfo.processName = AppName; pinfo.processInfoLength = sizeof(pinfo); pinfo.processAppSpec = NULL; err = GetProcessInformation(&psn,&pinfo); AppName[AppName[0]+1] = 0x00; return (char *)&AppName[1]; } /* ** return fullpathname from FSSpec ** */ char *GetFullPathFromSpec(char *FullPath, FSSpec *Spec, OSErr *err) { Handle hFullPath; short len; Assert_it(Spec,"GetFullPathFromSpec","") *err = FSpGetFullPath(Spec, &len, &hFullPath); printerr("FSpGetFullPath:", (*err != -43) && (*err != 0), *err, __LINE__, __FILE__, ""); memmove(FullPath, (Handle) *hFullPath, len); FullPath[len] = '\0'; /* make c-string */ DisposeHandle((Handle)hFullPath); /* we don't need it any more */ printerr("Warning path length exceeds limit: ", len >= NAME_MAX, len, __LINE__, __FILE__, " chars "); return FullPath; } /* * This function expands a given partial path to a complete path. * Path expansions are relative to the running app. * This function follows the notation: * 1. relative path: * a: ":subfolder:filename" -> ":current folder:subfolder:filename" * b: "::folder2:filename" -> folder2 is beside the current * folder on the same level * c: "filename" -> in current folder * * An absolute path will be returned. The following characteristics of Macintosh pathnames should be noted: A full pathname never begins with a colon, but must contain at least one colon. A partial pathname always begins with a colon separator except in the case where the file partial pathname is a simple file or directory name. Single trailing separator colons in full or partial pathnames are ignored except in the case of full pathnames to volumes. In full pathnames to volumes, the trailing separator colon is required. Consecutive separator colons can be used to ascend a level from a directory to its parent directory. Two consecutive separator colons will ascend one level, three consecutive separator colons will ascend two levels, and so on. Ascending can only occur from a directory; not a file. */ char *GetCompletePath(char *CompletePath, const char *name, FSSpec *Spec, OSErr *err) { Boolean hasDirName = false; char currentdir[NAME_MAX]; char *tmpPtr; unsigned short pathlen; AssertStr(name,"GetCompletePath") Assert_it(Spec,"GetCompletePath","") Assert_it((CompletePath != name),"GetCompletePath","") for (tmpPtr = name; *tmpPtr; tmpPtr++) if (*tmpPtr == ':') hasDirName = true; if (name[0] != ':') /* case c: path including volume name or only filename */ { if (hasDirName) { /* okey, starts with volume name, so it must be a complete path */ sstrcpy(CompletePath, name); } else { /* only filename: add cwd and return */ getcwd(currentdir, NAME_MAX); sstrcat(currentdir, name); sstrcpy(CompletePath, currentdir); } } else if (name[1] == ':') /* it's case b: "::folder2:filename" */ { printerr("GetCompletePath ", -1, *err, __LINE__, __FILE__, "not implemented"); /* it's not yet implemented; do we really need this case ?*/ return NULL; } else /* it's case a: ":subfolder:filename" */ { getcwd(CompletePath, NAME_MAX); /* we don't need a second colon */ CompletePath[strlen(CompletePath)-1] = '\0'; sstrcat(CompletePath, name); } pathlen = strlen(CompletePath); *err = FSpLocationFromFullPath(pathlen, CompletePath, Spec); return CompletePath; } char *MakeFilenameShorter(const char *LongFilename) { static char filename[35]; /* contents should be never longer than 32 chars */ static unsigned char Num = 0; /* change the number for every call */ /* this var will rollover without a problem */ char tempLongFilename[1024], charnum[5]; char *last_dotpos = tempLongFilename; unsigned long full_length = strlen(LongFilename); unsigned long ext_length = 0; unsigned long num_to_cut = 0; long firstpart_length; char *tmpPtr; short MaxLength = 31; if (full_length <= MaxLength) /* filename is not long */ { return strcpy(filename,LongFilename); } Num++; strcpy(tempLongFilename,LongFilename); /* Look for the last extension pos */ for (tmpPtr = tempLongFilename; *tmpPtr; tmpPtr++) if (*tmpPtr == '.') last_dotpos = tmpPtr; ext_length = strlen(last_dotpos); firstpart_length = last_dotpos - tempLongFilename; if (ext_length > 6) /* up to 5 chars are treated as a */ { /* normal extension like ".html" or ".class" */ firstpart_length = 0; } num_to_cut = full_length - MaxLength; /* number the files to make the names unique */ sprintf(charnum,"~%x", Num); num_to_cut += strlen(charnum); if (firstpart_length == 0) { firstpart_length = full_length; tempLongFilename[firstpart_length - num_to_cut] = 0; sprintf(filename,"%s%s", tempLongFilename, charnum); } else { tempLongFilename[firstpart_length - num_to_cut] = 0; sprintf(filename,"%s%s%s", tempLongFilename, charnum, last_dotpos); } return filename; } zip30/macos/source/pathname.h0100644000076400000060000000430407246614502014340 0ustar edisk/* Copyright (c) 1990-2001 Info-ZIP. All rights reserved. See the accompanying file LICENSE, version 2000-Apr-09 or later (the contents of which are also included in zip.h) for terms of use. If, for some reason, all these files are missing, the Info-ZIP license also may be found at: ftp://ftp.info-zip.org/pub/infozip/license.html */ #ifndef PATHNAME_H #define PATHNAME_H 1 char *StripPartialDir(char *CompletePath, const char *PartialPath, const char *FullPath); char *Real2RfDfFilen(char *RfDfFilen, const char *RealPath, short CurrentFork, short MacZipMode, Boolean DataForkOnly); char *RfDfFilen2Real(char *RealFn, const char *RfDfFilen, short MacZipMode, Boolean DataForkOnly, short *CurrentFork); unsigned short GetVolumeFromPath(const char *FullPath, char *VolumeName); char *GetCompletePath(char *CompletePath, const char *name, FSSpec *Spec, OSErr *err); char *TruncFilename(char *DirPath, const char *FilePath); char *GetFilename(char *CompletePath, const char *name); char *GetFullPathFromSpec(char *CompletePath, FSSpec *Spec, OSErr *err); char *GetFullPathFromID(char *CompletePath, short vRefNum, long dirID, ConstStr255Param name, OSErr *err); char *GetAppName(void); void createArchiveName(char *Path); void FindDesktopFolder(char *Path); char *FindNewExtractFolder(char *ExtractPath, Boolean uniqueFolder); OSErr FSpFindFolder( short vRefNum, /* Volume reference number. */ OSType folderType, /* Folder type taken by FindFolder. */ Boolean createFolder, /* Should we create it if non-existant. */ FSSpec *spec); /* Pointer to resulting directory. */ char *MakeFilenameShorter(const char *LongFilename); /* Rule: UnKnown_EF should always be zero. JohnnyLee_EF, NewZipMode_EF should always greater than all other definitions */ #define UnKnown_EF 0 #define TomBrownZipIt1_EF 10 #define TomBrownZipIt2_EF 20 #define JohnnyLee_EF 30 #define NewZipMode_EF 40 #define ResourceFork -1 #define DataFork 1 #define NoFork 0 #ifndef NAME_MAX #define NAME_MAX 1024 #endif #endif /* PATHNAME_H */ zip30/macos/source/recurse.c0100644000076400000060000003327310154332006014201 0ustar edisk/* These functions are based on Jim Luther's IterateDirectory() found in MoreFiles However, it's heavily modified by Dirk Haase */ /* ** IterateDirectory: File Manager directory iterator routines. ** ** by Jim Luther ** ** File: IterateDirectory.c ** ** Copyright (c) 1995-1998 Jim Luther and Apple Computer, Inc. ** All rights reserved. ** ** You may incorporate this sample code into your applications without ** restriction, though the sample code has been provided "AS IS" and the ** responsibility for its operation is 100% yours. ** ** IterateDirectory is designed to drop into the MoreFiles sample code ** library I wrote while in Apple Developer Technical Support */ /*****************************************************************************/ /* Includes */ /*****************************************************************************/ #include #include #include #include #include #include "zip.h" #include "macstuff.h" #include "helpers.h" #include "recurse.h" #include "macglob.h" #include "pathname.h" /*****************************************************************************/ /* Macros, typedefs */ /*****************************************************************************/ /* The RecurseGlobals structure is used to minimize the amount of ** stack space used when recursively calling RecurseDirectoryLevel ** and to hold global information that might be needed at any time. */ struct RecurseGlobals { short vRefNum; CInfoPBRec cPB; /* the parameter block used for PBGetCatInfo calls */ unsigned char *itemName; /* the name of the current item */ char *FullPath; short FullPathLen; OSErr result; /* temporary holder of results - saves 2 bytes of stack each level */ Boolean quitFlag; /* set to true if filter wants to kill interation */ unsigned short maxLevels; /* Maximum levels to iterate through */ unsigned short currentLevel; /* The current level IterateLevel is on */ }; typedef struct RecurseGlobals RecurseGlobals; typedef RecurseGlobals *RecurseGlobalsPtr; /*****************************************************************************/ /* Global Vars */ /*****************************************************************************/ extern MacZipGlobals MacZip; extern const char ResourceMark[13]; /* "XtraStuf.mac:" var is initialized in file pathname.c */ extern int extra_fields; /* do not create extra fields if false */ static RecurseGlobals theGlobals; static unsigned long DirLevels = 0; static char *buffer; extern int verbose; /* 1=report oddities in zip file structure */ /*****************************************************************************/ /* Prototypes */ /*****************************************************************************/ int procname(char *filename, int caseflag); int MatchWild( char *pPat, char *pStr, int case_sens); Boolean IsZipFile(char *name); static void RecurseDirectoryLevel(long DirID, RecurseGlobals *Globals); static Boolean isRegularItem( RecurseGlobals *Globals); static void ProcessFiles(RecurseGlobals *Globals, Boolean hasDataFork, Boolean hasResourceFork); static void ProcessDirectory(RecurseGlobals *Globals, Boolean IncludeItem, long DirID); static void ProcessItem(RecurseGlobals *Globals, long DirID); /*****************************************************************************/ /* Functions */ /*****************************************************************************/ static void RecurseDirectoryLevel(long DirID, RecurseGlobals *Globals) { char buffer2[23]; /* if maxLevels is zero, we aren't checking levels */ if ( (Globals->maxLevels == 0) || /* if currentLevel < maxLevels, look at this level */ (Globals->currentLevel < Globals->maxLevels) ) { short index = 1; ++Globals->currentLevel; /* go to next level */ if (DirLevels < Globals->currentLevel) DirLevels = Globals->currentLevel; sprintf(buffer2,"Globals->currentLevel: %d",Globals->currentLevel); do { /* Isn't C great... What I'd give for a "WITH theGlobals DO" about now... */ /* Get next source item at the current directory level */ Globals->cPB.dirInfo.ioFDirIndex = index; Globals->cPB.dirInfo.ioDrDirID = DirID; Globals->result = PBGetCatInfoSync((CInfoPBPtr)&Globals->cPB); ShowCounter(false); if ( Globals->result == noErr ) { ProcessItem(Globals, DirID); } /* if ( Globals->result == noErr ) */ ++index; /* prepare to get next item */ /* time to fall back a level? */ } while ( (Globals->result == noErr) && (!Globals->quitFlag) ); if ( (Globals->result == fnfErr) || /* fnfErr is OK - it only means we hit the end of this level */ (Globals->result == afpAccessDenied) ) /* afpAccessDenied is OK, too - it only means we cannot see inside a directory */ { Globals->result = noErr; } --Globals->currentLevel; /* return to previous level as we leave */ } } /*****************************************************************************/ pascal OSErr RecurseDirectory(short vRefNum, long thedirID, ConstStr255Param name, unsigned short maxLevels) { OSErr result; short theVRefNum; Boolean isDirectory; long DirID; /* Get the real directory ID and make sure it is a directory */ result = GetDirectoryID(vRefNum, thedirID, name, &DirID, &isDirectory); if ( result == noErr ) { if ( isDirectory == true ) { /* Get the real vRefNum */ result = DetermineVRefNum(name, vRefNum, &theVRefNum); if ( result == noErr ) { /* Set up the globals we need to access from the recursive routine. */ theGlobals.cPB.hFileInfo.ioNamePtr = theGlobals.itemName; theGlobals.cPB.hFileInfo.ioVRefNum = theVRefNum; theGlobals.itemName[0] = 0; theGlobals.result = noErr; theGlobals.quitFlag = false; theGlobals.maxLevels = maxLevels; theGlobals.currentLevel = 0; /* start at level 0 */ /* Here we go into recursion land... */ RecurseDirectoryLevel(DirID, &theGlobals); result = theGlobals.result; /* set the result */ } } else { result = dirNFErr; /* a file was passed instead of a directory */ } } return ( result ); } /*****************************************************************************/ pascal OSErr FSpRecurseDirectory(const FSSpec *spec, unsigned short maxLevels) { OSErr rc; theGlobals.vRefNum = spec->vRefNum; /* make room for pathnames */ theGlobals.itemName = (unsigned char *) StrCalloc(NAME_MAX); theGlobals.FullPath = StrCalloc(NAME_MAX); buffer = StrCalloc(NAME_MAX); if ((noisy) && (MacZip.DataForkOnly)) printf("\n Warning: Datafork only \n"); /* reset the count to zero */ ShowCounter(true); if (noisy) leftStatusString("Build File List; Items done:"); if (noisy) printf("\n Collecting Filenames ..."); rc = RecurseDirectory(spec->vRefNum, spec->parID, spec->name,maxLevels); printerr("RecurseDirectory:",rc,rc,__LINE__,__FILE__,""); if (noisy) printf("\n... done \n\n %6d matched files found \n", MacZip.FoundFiles); if (noisy) printf(" %6d folders found in %d Levels \n", MacZip.FoundDirectories,DirLevels); if (MacZip.BytesOfData > (1024*1024)) if (noisy) printf(" %4.3f MBytes unzipped size\n\n", (float) MacZip.BytesOfData/(1024*1024)); else if (noisy) printf(" %4.3f KBytes unzipped size\n\n", (float) MacZip.BytesOfData/1024); /* free all memory of pathnames */ theGlobals.itemName = (unsigned char *) StrFree((char *)theGlobals.itemName); theGlobals.FullPath = StrFree(theGlobals.FullPath); buffer = StrFree(buffer); return rc; } /* * Return true if filename == zipfile * After the first match no further check will be done ! * */ Boolean IsZipFile(char *filen) { static firstMatch = false; if (filen == NULL) firstMatch = false; if (!firstMatch) { if (stricmp(filen, MacZip.ZipFullPath) == 0) { firstMatch = true; return true; } } return false; } static Boolean isRegularItem( RecurseGlobals *Globals) { Boolean isInvisible = false, isAlias = false, isSystem = false; isSystem = !((Globals->cPB.hFileInfo.ioFlFndrInfo.fdFlags & (1 << 12)) == 0 ); isInvisible = !((Globals->cPB.hFileInfo.ioFlFndrInfo.fdFlags & (1 << 14)) == 0 ); isAlias = !((Globals->cPB.hFileInfo.ioFlFndrInfo.fdFlags & (1 << 15)) == 0); if (isAlias == true) { return false; } if (MacZip.IncludeInvisible == true) { return true; } if ((isSystem == true) || (isInvisible == true)) { return false; } return true; } static void ProcessFiles(RecurseGlobals *Globals, Boolean hasDataFork, Boolean hasResourceFork) { /* some file statistics */ MacZip.FoundFiles++; if (hasDataFork == true) { MacZip.BytesOfData = Globals->cPB.hFileInfo.ioFlLgLen + MacZip.BytesOfData; MacZip.CurrentFork = DataFork; MacZip.RawCountOfItems++; if (MacZip.DataForkOnly == true) { procname(Globals->FullPath, false); hasResourceFork = false; } else { procname(Real2RfDfFilen(buffer,Globals->FullPath, DataFork, MacZip.MacZipMode, MacZip.DataForkOnly), false); } } if (hasResourceFork == true) { MacZip.BytesOfData = Globals->cPB.hFileInfo.ioFlRLgLen + MacZip.BytesOfData; MacZip.CurrentFork = ResourceFork; MacZip.RawCountOfItems++; procname(Real2RfDfFilen(buffer, Globals->FullPath, ResourceFork, MacZip.MacZipMode, MacZip.DataForkOnly), false); } } static void ProcessDirectory(RecurseGlobals *Globals, Boolean IncludeItem, long DirID) { OSErr rc; MacZip.isDirectory = true; GetFullPathFromID(Globals->FullPath,Globals->vRefNum, DirID, Globals->itemName, &rc); MacZip.RawCountOfItems++; MacZip.FoundDirectories++; if (MacZip.StoreFoldersAlso) { procname(Globals->FullPath, false); } /* We have a directory */ if ( !Globals->quitFlag && IncludeItem) { /* Dive again if the IterateFilterProc didn't say "quit" and dir is not an alias */ RecurseDirectoryLevel(Globals->cPB.dirInfo.ioDrDirID, Globals); } } static void ProcessItem(RecurseGlobals *Globals, long DirID) { OSErr rc; Boolean IncludeItem = false, hasDataFork = false; Boolean hasResourceFork = false; IncludeItem = isRegularItem(Globals); /* Is it a File? */ if ( (Globals->cPB.hFileInfo.ioFlAttrib & ioDirMask) == 0 ) { PToCCpy(Globals->itemName,MacZip.FileName); MacZip.isDirectory = false; hasDataFork = (Globals->cPB.hFileInfo.ioFlLgLen != 0); hasResourceFork = (Globals->cPB.hFileInfo.ioFlRLgLen != 0); /* include also files with zero recource- and data-fork */ if ((hasDataFork == 0) && (hasResourceFork == 0)) hasDataFork = true; if ((hasDataFork == 0) && (hasResourceFork != 0) && (extra_fields == false)) { IncludeItem = false; } GetFullPathFromID(Globals->FullPath,Globals->vRefNum, DirID, Globals->itemName, &rc); printerr("GetFullPathFromID:",rc,rc,__LINE__, __FILE__,MacZip.FileName); if (IncludeItem && /* don't include the zipfile itself */ (!IsZipFile(Globals->FullPath)) ) { if (MATCH(MacZip.Pattern, MacZip.FileName, false) == true) { ProcessFiles(Globals, hasDataFork, hasResourceFork); } /* if (MatchWild( MacZip.FileName,MacZip.Pattern ) == true) */ } /* if (!IsZipFile(Globals->FullPath)) */ } /* Is it a File? */ /* Is it a directory? */ if ( (Globals->cPB.hFileInfo.ioFlAttrib & ioDirMask) != 0 ) { ProcessDirectory(Globals,IncludeItem, DirID); } /* Is it a directory? */ } zip30/macos/source/recurse.h0100644000076400000060000001236406677115516014230 0ustar edisk/* ** IterateDirectory: File Manager directory iterator routines. ** ** by Jim Luther ** ** File: IterateDirectory.h ** ** Copyright (c) 1995-1998 Jim Luther and Apple Computer, Inc. ** All rights reserved. ** ** You may incorporate this sample code into your applications without ** restriction, though the sample code has been provided "AS IS" and the ** responsibility for its operation is 100% yours. ** ** IterateDirectory is designed to drop into the MoreFiles sample code ** library I wrote while in Apple Developer Technical Support */ #ifndef __RECURSEDIRECTORY__ #define __RECURSEDIRECTORY__ #include #include #ifdef __cplusplus extern "C" { #endif /*****************************************************************************/ pascal OSErr RecurseDirectory(short vRefNum, long dirID, ConstStr255Param name, unsigned short maxLevels ); /* Iterate (scan) through a directory's content. The IterateDirectory function performs a recursive iteration (scan) of the specified directory and calls your IterateFilterProc function once for each file and directory found. The maxLevels parameter lets you control how deep the recursion goes. If maxLevels is 1, IterateDirectory only scans the specified directory; if maxLevels is 2, IterateDirectory scans the specified directory and one subdirectory below the specified directory; etc. Set maxLevels to zero to scan all levels. The yourDataPtr parameter can point to whatever data structure you might want to access from within the IterateFilterProc. vRefNum input: Volume specification. dirID input: Directory ID. name input: Pointer to object name, or nil when dirID specifies a directory that's the object. maxLevels input: Maximum number of directory levels to scan or zero to scan all directory levels. iterateFilter input: A pointer to the routine you want called once for each file and directory found by IterateDirectory. yourDataPtr input: A pointer to whatever data structure you might want to access from within the IterateFilterProc. Result Codes noErr 0 No error nsvErr -35 No such volume ioErr -36 I/O error bdNamErr -37 Bad filename fnfErr -43 File not found paramErr -50 No default volume or iterateFilter was NULL dirNFErr -120 Directory not found or incomplete pathname or a file was passed instead of a directory afpAccessDenied -5000 User does not have the correct access afpObjectTypeErr -5025 Directory not found or incomplete pathname __________ See also: RecurseFilterProcPtr, FSpRecurseDirectory */ /*****************************************************************************/ pascal OSErr FSpRecurseDirectory(const FSSpec *spec, unsigned short maxLevels); /* Iterate (scan) through a directory's content. The FSpIterateDirectory function performs a recursive iteration (scan) of the specified directory and calls your IterateFilterProc function once for each file and directory found. The maxLevels parameter lets you control how deep the recursion goes. If maxLevels is 1, FSpIterateDirectory only scans the specified directory; if maxLevels is 2, FSpIterateDirectory scans the specified directory and one subdirectory below the specified directory; etc. Set maxLevels to zero to scan all levels. The yourDataPtr parameter can point to whatever data structure you might want to access from within the IterateFilterProc. spec input: An FSSpec record specifying the directory to scan. maxLevels input: Maximum number of directory levels to scan or zero to scan all directory levels. iterateFilter input: A pointer to the routine you want called once for each file and directory found by FSpIterateDirectory. yourDataPtr input: A pointer to whatever data structure you might want to access from within the IterateFilterProc. Result Codes noErr 0 No error nsvErr -35 No such volume ioErr -36 I/O error bdNamErr -37 Bad filename fnfErr -43 File not found paramErr -50 No default volume or iterateFilter was NULL dirNFErr -120 Directory not found or incomplete pathname afpAccessDenied -5000 User does not have the correct access afpObjectTypeErr -5025 Directory not found or incomplete pathname __________ See also: RecurseFilterProcPtr, RecurseDirectory */ /*****************************************************************************/ #endif /* __RECURSEDIRECTORY__ */ zip30/macos/source/unixlike.c0100644000076400000060000002361610154332006014361 0ustar edisk/* Copyright (c) 1990-1999 Info-ZIP. All rights reserved. See the accompanying file LICENSE, version 1999-Oct-05 or later (the contents of which are also included in zip.h) for terms of use. If, for some reason, both of these files are missing, the Info-ZIP license also may be found at: ftp://ftp.cdrom.com/pub/infozip/license.html */ /*--------------------------------------------------------------------------- unixlike.c Macintosh-specific routines to emulate unixfunctions. ---------------------------------------------------------------------------*/ /*****************************************************************************/ /* Includes */ /*****************************************************************************/ #include "zip.h" #include #include #include #include "unixlike.h" #include "helpers.h" #include "pathname.h" #include "macstuff.h" #include "macglob.h" #include "mactime.h" /*****************************************************************************/ /* Global Vars */ /*****************************************************************************/ extern MacZipGlobals MacZip; extern int errno; /*****************************************************************************/ /* Prototypes */ /*****************************************************************************/ /*****************************************************************************/ /* Functions */ /*****************************************************************************/ /* *---------------------------------------------------------------------- * * MacStat -- * * This function replaces the library version of stat. The stat * function provided by most Mac compiliers is rather broken and * incomplete. * * Results: * See stat documentation. * * Side effects: * See stat documentation. * *---------------------------------------------------------------------- */ int Zmacstat(const char *Fname, struct stat *buf) { OSErr err, rc; short fullPathLength; Handle hFullPath; char path[NAME_MAX], path2[NAME_MAX]; HVolumeParam vpb; static unsigned long count_of_files = 0; AssertStr(Fname,Fname) Assert_it(buf,"","") UserStop(); memset(buf, 0, sizeof(buf)); /* zero out all fields */ RfDfFilen2Real(path2, Fname, MacZip.MacZipMode, MacZip.DataForkOnly, &MacZip.CurrentFork); GetCompletePath(path, path2, &MacZip.fileSpec, &err); err = PrintUserHFSerr((err != -43) && (err != 0), err, path); printerr("GetCompletePath:", err, err, __LINE__, __FILE__, path); if (err != noErr) { errno = err; return -1; } /* Collect here some more information, it's not related to Macstat. (note: filespec gets changed later in this function) */ /* clear string-buffer */ memset(MacZip.FullPath, 0x00, sizeof(MacZip.FullPath)); rc = FSpGetFullPath(&MacZip.fileSpec, &fullPathLength, &hFullPath); strncpy(MacZip.FullPath, *hFullPath, fullPathLength); DisposeHandle(hFullPath); /* we don't need it any more */ /* Collect some more information not related to Macstat */ /* * Fill the fpb & vpb struct up with info about file or directory. */ FSpGetDirectoryID(&MacZip.fileSpec, &MacZip.dirID, &MacZip.isDirectory); vpb.ioVRefNum = MacZip.fpb.hFileInfo.ioVRefNum = MacZip.fileSpec.vRefNum; vpb.ioNamePtr = MacZip.fpb.hFileInfo.ioNamePtr = MacZip.fileSpec.name; if (MacZip.isDirectory) { MacZip.fpb.hFileInfo.ioDirID = MacZip.fileSpec.parID; /* * Directories are executable by everyone. */ buf->st_mode |= UNX_IXUSR | UNX_IXGRP | UNX_IXOTH | UNX_IFDIR; } else { MacZip.fpb.hFileInfo.ioDirID = MacZip.dirID; } MacZip.fpb.hFileInfo.ioFDirIndex = 0; err = PBGetCatInfoSync((CInfoPBPtr)&MacZip.fpb); if (err == noErr) { vpb.ioVolIndex = 0; err = PBHGetVInfoSync((HParmBlkPtr)&vpb); if (err == noErr && buf != NULL) { /* * Files are always readable by everyone. */ buf->st_mode |= UNX_IRUSR | UNX_IRGRP | UNX_IROTH; /* * Use the Volume Info & File Info to fill out stat buf. */ if (MacZip.fpb.hFileInfo.ioFlAttrib & 0x10) { buf->st_mode |= UNX_IFDIR; buf->st_nlink = 2; } else { buf->st_nlink = 1; if (MacZip.fpb.hFileInfo.ioFlFndrInfo.fdFlags & 0x8000) { buf->st_mode |= UNX_IFLNK; } else { buf->st_mode |= UNX_IFREG; } } if (MacZip.fpb.hFileInfo.ioFlFndrInfo.fdType == 'APPL') { /* * Applications are executable by everyone. */ buf->st_mode |= UNX_IXUSR | UNX_IXGRP | UNX_IXOTH; } if ((MacZip.fpb.hFileInfo.ioFlAttrib & 0x01) == 0){ /* * If not locked, then everyone has write acces. */ buf->st_mode |= UNX_IWUSR | UNX_IWGRP | UNX_IWOTH; } buf->st_ino = MacZip.fpb.hFileInfo.ioDirID; buf->st_dev = MacZip.fpb.hFileInfo.ioVRefNum; buf->st_uid = -1; buf->st_gid = -1; buf->st_rdev = 0; if (MacZip.CurrentFork == ResourceFork) buf->st_size = MacZip.fpb.hFileInfo.ioFlRLgLen; else buf->st_size = MacZip.fpb.hFileInfo.ioFlLgLen; buf->st_blksize = vpb.ioVAlBlkSiz; buf->st_blocks = (buf->st_size + buf->st_blksize - 1) / buf->st_blksize; /* * The times returned by the Mac file system are in the * local time zone. We convert them to GMT so that the * epoch starts from GMT. This is also consistent with * what is returned from "clock seconds". */ if (!MacZip.isDirectory) { MacZip.CreatDate = MacZip.fpb.hFileInfo.ioFlCrDat; MacZip.ModDate = MacZip.fpb.hFileInfo.ioFlMdDat; MacZip.BackDate = MacZip.fpb.hFileInfo.ioFlBkDat; } else { MacZip.CreatDate = MacZip.fpb.dirInfo.ioDrCrDat; MacZip.ModDate = MacZip.fpb.dirInfo.ioDrMdDat; MacZip.BackDate = MacZip.fpb.dirInfo.ioDrBkDat; } #ifdef IZ_CHECK_TZ if (!zp_tz_is_valid) { MacZip.HaveGMToffset = false; MacZip.Md_UTCoffs = 0L; MacZip.Cr_UTCoffs = 0L; MacZip.Bk_UTCoffs = 0L; } else #endif { /* Do not use GMT offsets when Md_UTCoffs calculation * fails, since this time stamp is used for time * comparisons in Zip and UnZip operations. * We do not bother when GMT offset calculation fails for * any other time stamp value. Instead we simply assume * a default value of 0. */ MacZip.HaveGMToffset = GetGMToffsetMac(MacZip.ModDate, &MacZip.Md_UTCoffs); if (MacZip.HaveGMToffset) { GetGMToffsetMac(MacZip.CreatDate, &MacZip.Cr_UTCoffs); GetGMToffsetMac(MacZip.BackDate, &MacZip.Bk_UTCoffs); } else { MacZip.Cr_UTCoffs = 0L; MacZip.Bk_UTCoffs = 0L; } } #ifdef DEBUG_TIME { printf("\nZmacstat: MacZip.HaveGMToffset: %d", MacZip.HaveGMToffset); printf("\nZmacstat: Mac modif: %lu local -> UTOffset: %d", MacZip.ModDate, MacZip.Md_UTCoffs); printf("\nZmacstat: Mac creat: %lu local -> UTOffset: %d", MacZip.CreatDate, MacZip.Cr_UTCoffs); printf("\nZmacstat: Mac back: %lu local -> UTOffset: %d", MacZip.BackDate, MacZip.Bk_UTCoffs); } #endif /* DEBUG_TIME */ buf->st_mtime = MacFtime2UnixFtime(MacZip.ModDate); buf->st_ctime = MacFtime2UnixFtime(MacZip.CreatDate); buf->st_atime = buf->st_mtime; #ifdef DEBUG_TIME { printf("\nZmacstat: Unix modif: %lu UTC; Mac: %lu local", buf->st_mtime, MacZip.ModDate); printf("\nZmacstat: Unix creat: %lu UTC; Mac: %lu local\n", buf->st_ctime, MacZip.CreatDate); } #endif /* DEBUG_TIME */ if (noisy) { if (MacZip.StatingProgress) { count_of_files++; InformProgress(MacZip.RawCountOfItems, count_of_files ); } else count_of_files = 0; } } } if (err != noErr) { errno = err; } MacZip.isMacStatValid = true; return (err == noErr ? 0 : -1); } /* *---------------------------------------------------------------------- * * chmod -- * * Results: * See chmod documentation. * * Side effects: * See chmod documentation. * *---------------------------------------------------------------------- */ int chmod(char *path, int mode) { HParamBlockRec hpb; OSErr err; hpb.fileParam.ioNamePtr = C2PStr(path); hpb.fileParam.ioVRefNum = 0; hpb.fileParam.ioDirID = 0; if (mode & 0200) { err = PBHRstFLockSync(&hpb); } else { err = PBHSetFLockSync(&hpb); } if (err != noErr) { errno = err; return -1; } return 0; } zip30/macos/source/unixlike.h0100644000076400000060000000621507011111240014353 0ustar edisk/* Copyright (c) 1990-1999 Info-ZIP. All rights reserved. See the accompanying file LICENSE, version 1999-Oct-05 or later (the contents of which are also included in zip.h) for terms of use. If, for some reason, both of these files are missing, the Info-ZIP license also may be found at: ftp://ftp.cdrom.com/pub/infozip/license.html */ /* * Directory Operations for Mac based on BSD 4.3 * By Jason Linhart, January 1997 */ #ifndef _UNIXLIKE_H #define _UNIXLIKE_H 1 #include #ifndef NAME_MAX #define NAME_MAX 2048 #endif #define UNX_IFMT 0170000 /* Unix file type mask */ #define UNX_IFSOCK 0140000 /* Unix socket (BSD, not SysV or Amiga) */ #define UNX_IFLNK 0120000 /* Unix symbolic link (not SysV, Amiga) */ #define UNX_IFREG 0100000 /* Unix regular file */ #define UNX_IFBLK 0060000 /* Unix block special (not Amiga) */ #define UNX_IFDIR 0040000 /* Unix directory */ #define UNX_IFCHR 0020000 /* Unix character special (not Amiga) */ #define UNX_IFIFO 0010000 /* Unix fifo (BCC, not MSC or Amiga) */ #define UNX_ISUID 04000 /* Unix set user id on execution */ #define UNX_ISGID 02000 /* Unix set group id on execution */ #define UNX_ISVTX 01000 /* Unix directory permissions control */ #define UNX_ENFMT UNX_ISGID /* Unix record locking enforcement flag */ #define UNX_IRWXU 00700 /* Unix read, write, execute: owner */ #define UNX_IRUSR 00400 /* Unix read permission: owner */ #define UNX_IWUSR 00200 /* Unix write permission: owner */ #define UNX_IXUSR 00100 /* Unix execute permission: owner */ #define UNX_IRWXG 00070 /* Unix read, write, execute: group */ #define UNX_IRGRP 00040 /* Unix read permission: group */ #define UNX_IWGRP 00020 /* Unix write permission: group */ #define UNX_IXGRP 00010 /* Unix execute permission: group */ #define UNX_IRWXO 00007 /* Unix read, write, execute: other */ #define UNX_IROTH 00004 /* Unix read permission: other */ #define UNX_IWOTH 00002 /* Unix write permission: other */ #define UNX_IXOTH 00001 /* Unix execute permission: other */ /* historical file modes */ #define S_IREAD 0x100 #define S_IWRITE 0x80 #define S_IEXEC 0x40 #define isatty(arg) 1 #define EINVAL 22 /* Invalid argument */ #define ENAMETOOLONG 63 /* File name too long */ struct dirent { char d_name[NAME_MAX]; }; /* * The following definitions are usually found in fcntl.h. * However, MetroWerks has screwed that file up a couple of times * and all we need are the defines. */ #define O_APPEND 0x0100 /* open the file in append mode */ #define O_CREAT 0x0200 /* create the file if it doesn't exist */ #define O_EXCL 0x0400 /* if the file exists don't create it again */ #define O_TRUNC 0x0800 /* truncate the file after opening it */ int Zmacstat (const char *path, struct stat *buf); int chmod(char *path, int mode); #include "macstuff.h" #endif /* _UNIXLIKE_H */ zip30/macos/source/VolWarn.h0100644000076400000060000000617307011111130014114 0ustar edisk/* Copyright (c) 1990-1999 Info-ZIP. All rights reserved. See the accompanying file LICENSE, version 1999-Oct-05 or later (the contents of which are also included in zip.h) for terms of use. If, for some reason, both of these files are missing, the Info-ZIP license also may be found at: ftp://ftp.cdrom.com/pub/infozip/license.html */ /* This is an Important note about pathnames */ static char DuplicVolumeNote[] = { "\rIMPORTANT NOTE:" \ "\r" \ "\r This port has one weak point: It is based on pathnames !! " \ "\r Because it's a port !! Unlike MacOS: As far as I know all other "\ "\r Operatingsystems (eg.: Unix, DOS, OS/2, ...) are based on pathnames" \ "\r " \ /* a short quote from "Inside Macintintosh, Files"; slightly modified by me */ "\r On a Mac: Files and directories located in the same directory " \ "\r must all have unique names. However, there is no requirement " \ "\r that volumes have unique names. It is perfectly acceptable for two mounted" \ "\r volumes to have the same name. This is one reason why a application should " \ "\r use volume reference numbers rather than volume names to specify volumes," \ "\r but for this Zip-Port I can't use reference numbers. " \ "\r " \ /* end quote */ "\r" \ "\r From the developers point of view:"\ "\r The use of pathnames, however, is highly discouraged. If the user changes"\ "\r names or moves things around, they are worthless." \ "\r Full pathnames are particularly unreliable as a means of identifying files," \ "\r directories or volumes within your application," \ "\r for two primary reasons:" \ "\r" \ "\r* The user can change the name of any element in the path at" \ "\r virtually any time." \ "\r* Volume names on the Macintosh are *not* unique. Multiple" \ "\r mounted volumes can have the same name. For this reason, the use of" \ "\r a full pathname to identify a specific volume may not produce the" \ "\r results you expect. If more than one volume has the same name and" \ "\r a full pathname is used, the File Manager currently uses the first" \ "\r mounted volume it finds with a matching name in the volume queue." \ "\r" \ "\r" \ "\r The main reason is that an attempt to implement support exact saving of" \ "\r the MacOS specific internal file-structures would require a throughout" \ "\r rewrite of major parts of shared code, probably sacrifying compatibility" \ "\r with other systems." \ "\r I have no solution at the moment. The port will just warn you if you try" \ "\r zip from / to a volume which has a duplicate name." \ "\r MacZip has problems to find the archives and files." \ "\r" \ "\r" \ "\r ... and the moral of this story:" \ "\r" \ "\r Don't mount multiple volumes with the same " \ "\r name while zip/unzip is running" \ "\r and "\ "\r My (Big) recommendation: Name all your volumes with a unique name "\ "\r (e.g: add a space character to the name) and" \ "\r MacZip will run without any problem." \ "\r" \ "\r" \ "\r Dirk Haase" \ }; zip30/macos/source/zip_rc.hqx0100644000076400000060000000527106677115746014423 0ustar edisk(This file must be converted with BinHex 4.0) :#RTTF#jbBbjcDA3!8dP84&0*9#%!N!3([`#3"&(E8dP8)3!"!!!([h*-BA8#Q3# 3!aDCQ3d!"RTTF#jbB`!!&[Bi"2[rG!"-5QS!N!1!!*!%"32,j+m2!*!Drj!%8P0 53e*6483"",#mXHDaqlGG!!!GmJ#3"JFj!*!%6Mi!N!MGc!`!P@6pq1R*k4&+Z,d p"5$(b(-Upcc#j%EiHCfjPTq%8h+X8d)MR$`rF[b9Vh`pTLc2jqZ9r'RNq9VN1'& 'MMmj6Sk6#5HFc0J4lN8iHFU2--,*K%Z1NIR+#1XNR("#bE-)2I+FF$*G@H6BL+` *!&6IV1ml1d+22#-$4UEm*#01"T`m*4`Ji(03ThM'$-EBilf-V8-e6Q8bXEVD@Xi 2bilcmGEY"lV6QGjZrK)I1CKZ$BfR4pSbLD'f`F'qVPKb+*(-*V2CPLfaGj1CE+a Z+-$kpr4hpHrCf@d%f66E!A2P-rA6phmUj)QrdYP4r[6)H+cZF"hRV``NHSG5`b! F6-0YBZ$!JH&%#frIb,2TmH4`LVGN4c1(%U1Q8#cf)P44dU"#-`D)I($H4I5qc[j NJLI5)qpN5)Ic[S(-`-&1H(U2L*U'-H`1Y1p&qc#*YVk4(RNUbp(ae(#'R,B[d%B (Nd40$id1C`FhmUlKNBmbkAf$Sra8qpDYcm0,H%GIhbiej(!EESbmC+a*'3dqdlC j)%*H#+!,D!K4#J#3!$9H-J)mB*6L!50R"%"&hi6DD*61[-qq22%f1hkXPq@r)'` (1hjQJ19cKP'bY0#60RQ3!&kd,r))mj-X,LBCCa&CeiX#f`ibZ$9##+[1HUJ34G5 584+#&@p9i[UDj-&PD2rAi0qYdMpMQ""M8FLBT`#FUMje-i6rVXl2qI`jK@XY#eH +%JH[5(`6,qEcH@K,(FfA4rZDNG,4mp60fALH@TT,SC!!5Sf0$HHP31&mP"AfKN) K-!N[&XjM@##`1I,(a"V"#L%@#U9'*'lT-5CaU8GqpLTFkUP"%klmfMLJ1QpH5r2 djNdfhIXJFIqqN!!&1QHe$jUlHF`jZ2I41X8k$@ZbKF1C2"Cq6YZaF(Z+5Yra&63 "alCh62Vm6N(RqR90&)#m`cE3mILqV`@qBmcQkf0"9Ei%#**RRRpcS0DmV!N6DB- &#R112Ym4-1d)GJ(R0,i,0!TEJ!%$#Mj$SFqp80)XU4&"+j!!DmFJk)S2*[(KNMR mHApd)4Im@I2aqEBrpd,EVi3ehd@qETI[eprhmmlp0UGjqhe`q#[[Ljk#GDclAll [P91j$d[[ir`4X1LcbmVcI$8cCd49rY*`E2l+F1l-Uk0CV,edY8%d('d@pD*qVRk L@64FE9KlU9Q%E`3$i@+cD"BSp)'26f,8K%[iL[#3!$-h&aDPY5L2CJBBpF5Kh5k +ASJVqckQ9kG`*C95rEka+29B5U+f"eYIqF&ZC()P-%GbHXQ44)a!l[Z9q3[c5Z! aN!!pGHT"X#q,IJ$8lG#i224dkNXMhd,#3I"ap4JkEk@YlrKEp1r14erRqIYVJY@ RbX4G0GVTc4A5A20`[E`GcX60GGI#0@$KHMqfFB9BIV4&%kr6+kH*J`(FR3lKcJj pNqpN!JiZ-`'&1jQ!a*e-31RCQB$%R8c!dY1CJ19(C`+@AjGIa[qCCq8qH,K8FA% LH$LpGbZiFpp0ehUR[lZTL-[HU3T8q*FVkd5&AaDBjrX##ha2S$UImK6,r-Z9MDM #PaVqNfUH+VqmXplAGpG!G`k,I&I!i[ZC`J,Iba3@rEQC`J,Iba5@rFQGIhNq5h` r-lM2ArAJIYjp(jEjYX!5he+i`cIhZRrjYq)%rjNh@"K4Ej!!V8&p!,8@0C*$l3L bk#`f"%i9DMaRk,i*YC&aj0dFH6G(hXf4Gh2Nh4ajYp5aY(5[I@a#hBBDeh9E'*X Kq3q,)QS*99$0SCj&R68Va[9Ie6lJ9444KDk%dDE9%CrPQhJ,hbD#)RJ8936RJK1 bjb%HMTILXr&#r&Um++SIZ#*1fAP1hM-c'CG*VekG*BkGApkj'DZA13GkPA1JPcN (iC4c%*m@1&[2l0@LLCK%pFUBG%kj4M@2,@pY&UjA+*Y2#Zil5%pF&GI[LBAVh-2 $3I"aCG,5ekC[qL[MlZ1QRP32Ga5YQFY`Cf-[rZ!JX+GrCir-1R)J6J!jdY[ekRU IXFT6',*jNmH[B69Hq&&6$N-NlS3K8Xm03mM2+VTKb253!iSqNDRHIKqNq$hqV6$ %pVF8KPMc@68N$0Q#[KXH1UJL$1P'',*PpB``C"5M'eXG)JbTfDal(BB!AfdN$-' cjq2P-%6bli8Kq,pej"NCErJr%NGk[[Pkpa44M+pBl4Mq$SC![ij'pZ[3j20d)N[ i$qR%J5hSI`01r3hJcl+!m54`kMY9f'+N1PrYaRqe4SCq@E8Hr)$%dK,,5@`LdR2 b$cBKPr+"5-q*AH`)BBm-4AUqlG-DHk"a9QQ`Yi"0+Beefb-pTlj6'Z(2`,ZS0"j +!KY9'SpQ-0f,5U2Q'(Lr+Sd(h`3fV65DpX2VT0+)[!EHKdUMS4ABTdVMX4IJG8T T'*pJ6K'P8IXk0+iTMFB8I'L[i9r!Qp6c`!dlH9,2idGJTp9PD'b(MjH9AZ0cQ02 TqYdI$#8c2*2-$Kr+**,r!`#3!dm4!!!: zip30/macos/ZipLib.h0100644000076400000060000001350007011111060012407 0ustar edisk/* Copyright (c) 1990-1999 Info-ZIP. All rights reserved. See the accompanying file LICENSE, version 1999-Oct-05 or later (the contents of which are also included in zip.h) for terms of use. If, for some reason, both of these files are missing, the Info-ZIP license also may be found at: ftp://ftp.cdrom.com/pub/infozip/license.html */ /*--------------------------------------------------------------------------- ZipLib.h This header-files is global to the project ZipLib. ---------------------------------------------------------------------------*/ /*****************************************************************************/ /* Macros, typedefs */ /*****************************************************************************/ #define MACOS #define MACZIP #define OLDROUTINENAMES 0 /* use new function names only */ #define OLDROUTINELOCATIONS 0 /* use new headerlocations only */ #define SystemSevenOrLater 1 /* Runs only on System 7.0 or later */ /* These functions are defined as a macro instead of a function. so we have to undefine them for replacing (see printf.c) */ #undef getc #undef getchar #undef putchar #undef putc #ifndef ZCONST # define ZCONST const #endif #define NAME_MAX 1024 /*****************************************************************************/ /* Includes standard headers */ /*****************************************************************************/ #include #include #include #include #include #include #include #include #include #include /* Many things are different for mac-users, so we need special mac functions :-) */ int Zmacstat (const char *path, struct stat *buf); #define stat(path, bufPtr) Zmacstat(path, bufPtr) #define lstat(path, bufPtr) Zmacstat(path, bufPtr) int fprintf(FILE *file, const char *format, ...); int printf(const char *format, ...); void perror(const char *parm1); /* #define MAC_DEBUG 1 #define DEBUG 1 */ #ifdef MAC_DEBUG #define LOG_DEBUG 7 /* debug-level messages */ int Print2Syslog(UInt8 priority, const char *format, ...); #include #define Notify(msg) \ { \ (void)Print2Syslog(LOG_DEBUG, "%s (file: %s line: %d)", \ msg, __FILE__, __LINE__); \ } #define Assert_it(cond,msg,kind) \ { \ if (!(cond)) \ { \ (void)Print2Syslog(LOG_DEBUG,"%s failed: [%s] cond: [%s] (file: %s line: %d)", \ kind, msg, #cond, __FILE__, __LINE__); \ } \ } #define AssertBool(b,msg) Assert_it (((b) == TRUE) || ((b) == FALSE),(msg),("AssertBool ")) #define AssertStr(s,msg) \ { \ int s_i = 0; \ Assert_it ((s),(msg),("1. AssertStr ")); \ while ((s)[s_i]) { \ Assert_it ((!iscntrl((s)[s_i]) || ((s)[s_i] == 0x0A) || \ ((s)[s_i] == 0x0D)),(s),("2. AssertStr ")); \ s_i++; \ } \ } #define AssertTime(t,msg) Assert_it (((t).tm_sec >= 0) && ((t).tm_sec < 62) && \ ((t).tm_min >= 0) && ((t).tm_min < 60) && \ ((t).tm_hour >= 0) && ((t).tm_hour < 24) && \ ((t).tm_mday >= 1) && ((t).tm_mday < 32) && \ ((t).tm_mon >= 0) && ((t).tm_mon < 12) && \ ((t).tm_wday >= 0) && ((t).tm_wday < 7) && \ ((t).tm_yday >= 0) && ((t).tm_yday < 366),(msg),("AssertStr ")) #define AssertIntRange(myvalue,minimum,maximum, msg) Assert_it ( \ ((myvalue) >= (minimum)) && ((myvalue) <= (maximum)), msg,("AssertIntRange ")) #define AssertStrNoOverlap(str1,str2,msg) \ { \ long s_i = 0; \ AssertStr((str1),(msg)) \ AssertStr((str2),(msg)) \ if ((str1) < (str2)) \ { \ s_i = strlen((str2)); \ Assert_it ( (((str1) + s_i) < (str2)),(msg),("AssertStrNoOverlap ")); \ } \ else \ { \ s_i = strlen((str1)); \ Assert_it ( (((str2) + s_i) < (str1)),(msg),("AssertStrNoOverlap ")); \ } \ } \ #else #define Assert_it(cond,msg,kind) #define AssertBool(b,msg) #define AssertStr(s,msg) #define AssertTime(t,msg) #define AssertIntRange(myvalue,minimum,maximum,msg) #define AssertStrNoOverlap(str1,str2,msg) #endif zip30/macos/ZipSx.h0100644000076400000060000001347007011111066012307 0ustar edisk/* Copyright (c) 1990-1999 Info-ZIP. All rights reserved. See the accompanying file LICENSE, version 1999-Oct-05 or later (the contents of which are also included in zip.h) for terms of use. If, for some reason, both of these files are missing, the Info-ZIP license also may be found at: ftp://ftp.cdrom.com/pub/infozip/license.html */ /*--------------------------------------------------------------------------- ZipSx.h This header-files is global to the project ZipSioux. ---------------------------------------------------------------------------*/ /*****************************************************************************/ /* Macros, typedefs */ /*****************************************************************************/ #define MACOS #define USE_SIOUX #define MACZIP #define OLDROUTINENAMES 0 /* use new function names only */ #define OLDROUTINELOCATIONS 0 /* use new headerlocations only */ #define SystemSevenOrLater 1 /* Runs only on System 7.0 or later */ /* These functions are defined as a macro instead of a function. so we have to undefine them for replacing (see printf.c) */ #undef getc #undef getchar #undef putchar #ifndef ZCONST # define ZCONST const #endif #define NAME_MAX 1024 /*****************************************************************************/ /* Includes standard headers */ /*****************************************************************************/ #include #include #include #include #include #include #include #include #include #include /* Many things are different for mac-users, so we need special mac functions :-) */ int Zmacstat (const char *path, struct stat *buf); #define stat(path, bufPtr) Zmacstat(path, bufPtr) #define lstat(path, bufPtr) Zmacstat(path, bufPtr) int fprintf(FILE *file, const char *format, ...); int printf(const char *format, ...); void perror(const char *parm1); /* #define MAC_DEBUG 1 */ #ifdef MAC_DEBUG #define LOG_DEBUG 7 /* debug-level messages */ int Print2Syslog(UInt8 priority, const char *format, ...); #include #define Notify(msg) \ { \ (void)Print2Syslog(LOG_DEBUG, "%s (file: %s line: %d)", \ msg, __FILE__, __LINE__); \ } #define Assert_it(cond,msg,kind) \ { \ if (!(cond)) \ { \ (void)Print2Syslog(LOG_DEBUG,"%s failed: [%s] cond: [%s] (file: %s line: %d)", \ kind, msg, #cond, __FILE__, __LINE__); \ } \ } #define AssertBool(b,msg) Assert_it (((b) == TRUE) || ((b) == FALSE),(msg),("AssertBool ")) #define AssertStr(s,msg) \ { \ int s_i = 0; \ Assert_it ((s),(msg),("1. AssertStr ")); \ while ((s)[s_i]) { \ Assert_it ((!iscntrl((s)[s_i]) || ((s)[s_i] == 0x0A) || \ ((s)[s_i] == 0x0D)),(s),("2. AssertStr ")); \ s_i++; \ } \ } #define AssertTime(t,msg) Assert_it (((t).tm_sec >= 0) && ((t).tm_sec < 62) && \ ((t).tm_min >= 0) && ((t).tm_min < 60) && \ ((t).tm_hour >= 0) && ((t).tm_hour < 24) && \ ((t).tm_mday >= 1) && ((t).tm_mday < 32) && \ ((t).tm_mon >= 0) && ((t).tm_mon < 12) && \ ((t).tm_wday >= 0) && ((t).tm_wday < 7) && \ ((t).tm_yday >= 0) && ((t).tm_yday < 366),(msg),("AssertStr ")) #define AssertIntRange(myvalue,minimum,maximum, msg) Assert_it ( \ ((myvalue) >= (minimum)) && ((myvalue) <= (maximum)), msg,("AssertIntRange ")) #define AssertStrNoOverlap(str1,str2,msg) \ { \ long s_i = 0; \ AssertStr((str1),(msg)) \ AssertStr((str2),(msg)) \ if ((str1) < (str2)) \ { \ s_i = strlen((str2)); \ Assert_it ( (((str1) + s_i) < (str2)),(msg),("AssertStrNoOverlap ")); \ } \ else \ { \ s_i = strlen((str1)); \ Assert_it ( (((str2) + s_i) < (str1)),(msg),("AssertStrNoOverlap ")); \ } \ } \ #else #define Assert_it(cond,msg,kind) #define AssertBool(b,msg) #define AssertStr(s,msg) #define AssertTime(t,msg) #define AssertIntRange(myvalue,minimum,maximum,msg) #define AssertStrNoOverlap(str1,str2,msg) #endif zip30/macos/zipup.h0100644000076400000060000000123507011111106012370 0ustar edisk/* Copyright (c) 1990-1999 Info-ZIP. All rights reserved. See the accompanying file LICENSE, version 1999-Oct-05 or later (the contents of which are also included in zip.h) for terms of use. If, for some reason, both of these files are missing, the Info-ZIP license also may be found at: ftp://ftp.cdrom.com/pub/infozip/license.html */ #ifndef O_RDONLY # include #endif #define fhow (O_RDONLY|O_BINARY) #define fbad (-1) typedef int ftype; #define zopen(n,p) MacOpen(n,p) #define zread(f,b,n) read(f,b,n) #define zclose(f) close(f) #define zerr(f) (k == (extent)(-1L)) #define zstdin 0 zip30/macos/ZpPrj.hqx0100644000076400000060000007155106742551332012672 0ustar edisk(This file must be converted with BinHex 4.0) :#9T`8(*U,R0TG!"6594%8dP8)3#3"&66!*!%Ip96593K!!%!!&66FNaKG3)!N!3 @!*!$$39DF&"bDJ#3!aEf1!,VX93!6&MU!*!$J!#3"!,cIF3NA3#3'[q3"%e08(* $9dP&!3b[H&ZZXklEb3#3"3,E[3#3"P40!!$hQ!#3"L8D"RMDS*NlIS6ISVG-[(8 R+hBY21RaEd$i`XJbN!"bQK8YHRN,mmTE("$HbP6f+lXeRq'lH*3I@AbbH%Ef3E+ Yif3KHp54hE%@hq8Fj,%GAml1RLpN-E,i(GQARdH@0q0,K(GffT%p5)X[RVFF@D4 BKrHBaXd@6VD,AXpZB5d!C#'6K@abQi`@mJ[Cj$MPC!8iDT2X[EaXE0rjRCHM[$` Ej#4Rp[RPjG6VcFj"ITHAR9DQepPe(-SAiAji1arZ(-5ApPP[lbMciLAdmP)if0m 4Z#m[-q'q["cNPGI1p`,!!JLip@eQPi2X'farqH4p"**I)T!!,ckH3A`!+i#AjfI 6V9BMbl,P@GDh0P[fhKZcCArkf5`lka2F0rFYkb28qpDfD[R@DP(8@d9PSQMYcUH l#l&K+CqqV@b6b'8EXQaE[)pm16Za$2kVE&Ajrhr50p-icq)mQh-k-9rKr#ThirR rPjaIiecK!m`jJh-@jcQFFcJAF-lMl1)dliLFcVQ"F`IR*Xk0R"GcEZCFalQ0mbl 1fcR[i$c+q@,1jh$HcAQBm`MR4C`2FElF9MERGNj6amLPR&XjIj*c$@F2jmXiAm$ j*XlAFlk"mi@FrjhcMcNrbIN*cSpcISVc6cMr,HHpR$r0q3#eRXTrcYrLI$mR'2- ,R+rKI"hRIH3Bb9R2#IC-iM3GT%lK(-,CcQPUVdlJ(-lCbMQ1Xi(6p)BkME10Xj% c+PDCdr561TN6d2S-jjpa'Lb,I*!!mcpbrKVR@cNIiIaPcSFjIjhc9cKrNI2GR'r Mr#$RKcMIc[R[1Aq9mbfFlq6m*Fi,1*Ga,Z@mKI0IFGl*#5!Dh)bmK[09R,GaAX, j"jarb2RI1(q(FaIR4cJrb[Nqc[Gb(Z#mQA-Ijhl1Jp4a$2rr-qGri@idr`pa2Tr c#j`c1@GcRXXjPh-Kjha1dcX4X#IbK!KDTSmLi&#%2SXmRI-QcLq9Z!9QHAK&RJp `lZ(FbhNGjrfFi0ZA1@rJr$6RRh*qP[1jR(r"H68Rb4GarLERAh1H6mK%r[mHjqp bAXYTHM*b(ZI2F2iXj`61[`QF)`)'4&l"HCccMCcrM[2R16r(qAR1Rq!dI4jj2HF pR$r&qmEbrbAmTmDmG5@R`BL)@2XZiLEchf"#j+Fj$@j%`)h)-cJ0YN6%B*!!fZ" 0"!b*Q-YJ5Z6l13f@4"l,H6RRrq,m"ZHMR,r0#FVclQpbISXh8X0[Fcl'q6MRDNj kp$ZFEqEm1FlAFVk)df"Bj'l1*Cc,1EXjRmhj4Fi(1@rN[*lcMcMr0HFV1DrKT2p IcEQEmcpaIScc2h$Zj2`0c[G`AX&j+HFl*#EQK*KF5AfSiiFjrbYhe2BUcZFYQ8# 8`"SqHK"mJ1I3kr3C28Brd%[d&(J&2Y#Ep#9p$1pa'!D(S)I"!2UBIUI2k&ekQ$k NTkNhA)PD1m`$$m!AqJL1"DHLhq&FB#FB#Zm#3m%Rq0Hr%%46EGlDqbRHVF#K%H! jCH(Hi#JG!5E6*4lH8SZ90Sij`3pl6lJjll@6MSXbZAq0&J$qBllBSmf01Ffr4[l C`lkV[XcL4ASG'Uq6pdGP+lLTLlHfZ[CGhY-)T@1p"c3qUpkHR1ZA["4,,hRFkea YBX@*hcX-dG"#+9Im%9i"mj8`IdC`pR"ZifcRl1$Xj"c&1CTc$1GBcR'FNcQl1'G `VZ*FcEQ@Fb2R*XiYR$GclZHmKI0@cJ1F"cN2F4lQ[)hc+1IYR(G`2Src(Xjl19r !q41F@f-(QGk,(-FjM(-iCbXRM$VH@aj#JTLJCcJ!8S+3!+!HU!JLJMDJ)qJ*@MT N"$e"8C!!&83&)8&+Kk"K"%KC3E!i)0$PJemF2ha%-$h8ZV&k4A@S8HedmNlrlUV k4r+lI'5L-VEe@@SUj"`H)5q"0Af[ML&D&MAMJ*Q(BUqXb8H5K0BVJkB$kF&FTK+ E1,G`MZBF`cQ@Fa,R+-j1cKXiEq5mQA-NjdE1rCbhF0l+HC!!Xiec'fF2Cc[R#-j 9R$GacZ$FblQDFbhR2Xl*R)FjEq-mbRNAjpfFcq0m2ZFpR&XjQcLE1BG`YR!1j4` QQE%pEq+fM@mD("[Z(pkQ6*ArB1m@(2NMrbrTZlE[a'9UA)NZ-1G*h2#q2MlNie# FlAKr`'(q0ph`MVp(96SX3dYqJ(B)h'F3ShNX,hEQPI(CraA+,q4E26%a@U*4G2h S*GZQpp4VDZqA6Ni-IBGlai[LEVbSIX8L6)&*mGBRF[Cp'P`'R8-#ZKG'%!T3Na# 3!-m)-8N-L68ZIi`Zd6(CV9@'cMfh-Y4UGPU0[2,dLj`Tq,X[KR+QI5p6KIl4ahY LPcQ1D'%LG1"lQRGkkX`5C4jc2[L!DZG,#8B,5U,`Fq[1G#3r8(Mci'9Ud,jSF#T ciQZmAjrirRI0jCeZYIacC+Q'iD#62CM9E%`2YX+JZLEVVGQjbYU*LD&c+[cadf` LhS-SY$AS24*%1!"B$AaU%FbHEZBiI&Le*&2dm*m[h!(MBQeX&DQ`Q-m4dY!$bD8 kHP%6%rda"hqX)Y,(1*GLV%NarU3BRe1-mLR'G"6MGiV4*m@3!)"LY%a"B48MHSS 40SAJU"bI-b0DLV%IaELIFKb+X6Xc5U8Bhe115CP42-9iN@)m66&kT4ME8S`!+ND `&'1!bP%MmhBlHQAHENIq6!ilBQEHEJF8c*[YH+'TL4e&-HqfSf(QcBaJ-HTRalI -QaR0XZ0rjXefp0#0fM&5apJFihD-d6&kamJGih@-",S41aQYXQ09M1SaQXGB%f0 hCUc,MZFamX5i(102M-iaYZG'X%`IfUkLVScJ-8E&'"jMCi`p-N,'Q#)M9BcX-BV 'Q"BMLBaU-CE)q"NMMibJ-IE)5"TMN!#-G$%qb@JJif#-"c++a@JM)f+-p6(ZaTJ KSh#-26)#akJG)cf-J$+'b"JAii#-CXPS(b0DGM63M36#+mfiD'a8e)cUfE&(4Kd CKh5MMSa1-LV*b#0MNk!-Sj!!M&'kN8P'*"Q9G118M&bD)4$'`aJTC265MR%bcZP '1aP9C066MABbqXIS'D10M!$+f+!Gph0MPS`&-QVTa[BB(@4-N4%h4J8CE@2Ncih 9-3l(i)SE-Q%iaBfmqX-Q$+-`f-)J#i-SE[L%N8I'C"PjC'5@m8FcHQK(%4PcC%5 6F6X'BaM6C151N8h'laK*C-54N6Y'(XfiR"fhBr5488I'm4LVBlb4F8Q898Bc'FY Nh*049XBecBLQ(FQ%Kc2UL6M+q#hFJh%l0j,,+#lMSCR"(KP@53lhm0'6rT!!Ma[ UBD#(34i'HKMHBCL(34i'HK"a'44#hN"HmSGk'1Y&cf"FQ2N+aL@4LKMrCE5BN@, 'N4QbB-5Bd@)h&X`i-#2'M!XMmM*kc2JK)kb-*6,HbYJK+J9ML)`I-YTS4LJ91+[ !9`@q+["9JFF+r&AJV!*R&6LV`'N&,L[`9S(h#Xa9B+i#Fa@iVm"G"8G3F!F&eLZ iJS*$+,L&JPXSZ)@#@bK`AX%V&,a#`5Z8I)+4BS-IGPcBi!!MbBb1-Tl+q'Cb60[ d$q2CGJcCi*%Ge6-iT-!K"3iTm%H"2`Vm8H#2!Rm8q+2!(`Aq+2$(MLFcrQS`5)& "#Ja5i)S#Ea4iSm!E4@mSX%%jSQQ`4i%j#Xa4p)d#Fa5BSm!I"HiSF%H"1`VF8H# 1!RF8Z+-F$6DiSm!G"HiSF%H"1mUH-pLM`"d&lLK`4p'AM"`UqPf"!`SX925k!JF 9Q+$!"!8Q+,"5JBm+E&$JJJ)A&,LJ`!-&(LM`3)%(#Ma3i)%#$a4iS-!$"4iSm%# "X3T-8'##!K-8H+$J&!T1SH!5#LkKY"8`A%2"+44F3X%I&0a!`8%82%,")a3m3X% M&$a#`5-82%,")a3m3X'R&(a+`DH8)r@')bNiNS+[+(Q5i5E+N@E$663pT1NK63p THNM6EjVHd[55TTFd[D6T58hrDAT+de1DRY,dP+DR0$fPk5G02fRk5G02'KcAm'% 06dC@e["L63pVkUDTQkCZQVTTq,1'2f[iS)C$DlLcKQYV1,D'3fXiY)C$DlLfT[i D,00`F!fHDALeKMYUZ,@'-fViYBCIDrLeKPpVq,@'[fTiVBD6DMLPKXYUH+@'9fT iTBE[DRL`"PmeZ+[Kq"UFe'#N"L-eA&1$NaUFe25LTKFe[DMT3Dd8ErTF`fXe[Dl TG3d@D$"!dr1DRYId[!BM0&a4Jp%DM0$JY!B(0"aCJ`-DRUc"!Jd@D,"!Jh%Dr02 JP!EV0"LSiG%D204`D3f(eR"S$3CUF&1$QaVFe'#3!!Er0IL[`Am09pC`!#d(-"U !JQmVH,L#0bXd!S8fS1$IL[STDU%F#6HDJD)HL[FUhUTiUq+YL[j8p*ULca4pT1J K43mTHNJjGXriY(Q[3RG3p)b#RbZiX,,Z"XXdZ+2",JfQDEL!KJYSY!X0(p"`!3e Id2!%$5I3F!)0*p$`#-dl0*a&`b-dr%H$[aVqSm&RMHDK`9)0(QY`@S2A'Pc@B,N 'bc9BVZ&''McAe&C6Fdep0(LZ`A-0RQX`A-060(a,`m-d2%a66`dAdh!a$5jVF&Q $baTFe[")$Br8p)Q'#fPiNSCVDMLQKYGSZ*''-fNiU+Eq'JkRiD!D(UIK8jUHdh! R66pU1*H'FfNiPiCcDAL@KQGTH*D'@fRk9F1[0$fVk9P0VfUiPSCVDEL@KQYT1+k '(fTiSBB6D[T3``Ze[*!!mAZM%5Pd(iAZSp!8&0U43[qaNaMS)%CV8'J-QJ!0RpE `E!hre["[$Ir@m'm0lpE`EJh[e["Y$Gr@m'd0hpEU*ZJ8B3GIH-fNB'1B3JRj'%8 aRe@'`bJ'fdl93qCGKdIr(k0G&iF0[#%M-bGm-JqU9h[+JqSeiaYjr%&'P,'fP!I eE&M+JlTf@5p2X8P-&!VFXe-H9,V,8aj8[#Y6(T5qUe)He-#V8ai8`fY5(P6&De- H9-IV8Ki8h4Y6(Y6JQe)HP12l8Kl8cGHP2#LMVdTj8&6IP2+JVViQj8&jI8A+Jc, l`T3(pIDG[6c*-6!Ipe"iVdM[339qIXU$8[lbP!FerD'8"mApH-U$+[r6+3r+rBG 5(Y6p$kBm6!$X6AQB%VJKj@'5i2U8KdQ$25N28`L[6hQB9(K$bX-Nd'G5(UDD4U8 m6$f05hQBL*U8mM#jp2k8KmNUjfrAPiGTUkRIb12M+00CAFIbK"Kqp3Y@*5%[Rr2 %D'*LHfYpqd1Q'%8rU[TPTCU9!ZrB&'H)J%d0cjQiHAcFqDRB&leNmjEJSQ'UecM CQLfQFbPHr@*FabPMeHRc*Y[jG(e(hFQek)D4d@'j&[q0Q2c#a@3MMkmhTaZc05I D'Q*m6rbr,IjI&Iq[MIpAarm[@Ra(jh'GXKM83X+ha2rhaIpharmEirp0LqRE9p+ +ebL#f'+Ck)liId6m2b2qEer-fV*LI2YZEIKFj6VMre(arqMiIdcm2cEq(lIiL+% q!PP&aq$*mArABT+aChCf9BZm9TR'hl5,@R8pUE+P'BEVKm9m,ieYpS,irfL-Zcr H(iVr$mIr0mIrpmErqq2r@q,r@q2r!r(r`F9kk-F-ETSFU3"H4kT&[B5!ZXA`qZA "AU-ZTQk0riI(rif,Z4U@"am$Q`X(*[RI&2rEmX+B%cR9+L!QqAUp'"dpr(VhhhD Tq6pX-9IMiGF2MIq(a2mYLlQ'R,!jAd!C&4qcGAjq[ZpAGXmfpecHfH(mT08%'lH MKZq)!"i#`hK'VKNDAcqmTV*QrH$8)(phM!a0+BL'U(aQTLGV3*0flr!0CV`6RKD ki0la6eC+49ZBd)TjNY!!CKar%am6&-kZK6RZZZ9Mch%qRrR`k,*p'r84B-kl2PX jV[V,2,2PlqCM2YNce[6Q[CXDkY+HUZXC0R[cfUi,m$j`mpI-q60rcBFRJ*P)DG) I!4m#TNliQ1e[rGV0jF`imqpYfhGlCEd)4Q3ri%JrmrTf@S3lTLJk-KL00dmF1D0 9*Q3fedk!N!#$'@ZQ2,KM*Ye-FYKm+19MXTHeR"p'(4lE,LHDm)H`8aIFiA(!c$G hq"G-D&3P8ma'-`1q`RPL2"-Q26Bl9DN)$i2*`IQ,qGY)KBHD'M&V5kpCc`J6BQI [D82QckGP0kiQMPR!b1Vjq6ZG'fAqRKPqFY"rdaR5CDD1qINC38KKKYEdE11ERB2 %0i,CIZBBm@%i9e6dCP-Mj`C2'qC1lD`rZI%LB1DI1fScKrFaPiL2`0b!&(91$-d ,MKpeeSZDF-Im2pi!h$(PJ%F!GbJRH!9`"kpF&0K"R6i@LhAm-(Gi3P`3H%5G1,0 Nf6lEUNlI"r`%$"1Ydb-"A`(Lm(GBPYei0VQLBYCbqX2d@p4T('EVJ5`m$&C52p0 ,8AR"KF("*5T@@A`dG`K@6+"`"c)bZmmGRKV#DU*k5c$,cahH$!+j8AZ#(J35`8& QqlPMAKm"KMY`%NQ%1l`pQ2AR$Qm-XHfUelH$k4(Z!$*kKcZm+*J#!@EaD3#[Z+- (K-Nhk!H#4`"hH(2`GZl`bU$1h1&p)GTAJpL$K`"hH%hJ*F!GrK(i#A$(Zr%9i)i DibrJi"f0L$X`(FcKMNNZm*-lqJm["ZlJ%(JkF!F'iIR!(4J"4q#1hXBEJM[k$Bm )lZJ0F)-lkQM"hYcaCN3,lSM"1i)lH!EH%G`a@5&#C+2H+Ki6L4b[M`VBcKfq+8b kF)GR#Ah+(6iN6+a`KhF+lq)1la3Q6lM$"d@mS"VY-cJ#GhL,#-YXe,X$0BFlq)V -4$EU6m+%#(IiH9!Vl["6`EF#kX58UUHr4%k3!*2K"m-GrK,iaA#(PiF`Z5Ca6Ub QQm4FDXiGrK[icA!(IZ%l`adi!VrLMMk(Lh&(2m&aZ+2ZBTMEC)h!,ZjiJaK`0ZN PJcm0Gr3(rF8GILc`$ZlS$haVZ-0r"EcL$Jm8m*ml2%c`Xq%1(aCmEEM$Xi3q09q c&"C-jJjZK*m-Gr!aZ"Khm#+i*(IiPH!h`aeiL4m0Gr3"IMAFd3IieR!(VZ&I`af B!LC`4fq$eGc49rMCF%HYi92Fm@CmEEMM2A!ClZ$1q0a`"jE!EER$CiGBlP"&)$V F`A("(ql`Im%2KcY`'PmFl["h`4q(1caKm-RK$Zj)2jT[L2L"p`phm'&i!AId"pi rh)'le)3lZ!FFK$Y`'3mKlX![[)5iSmrKM0c4*h!dlRJRhN,Fi4-%$R"(Vq-*`Kf H0IJ,FBFR$I8hAiXF!VmKlZKMq$jhm!EmKlL$@q*$a"eiKKm4Gr!LhXXGh!1Zc4f B$Mjc"fk#4Gb"4hJ(F3F@L"V9BKhKGp`4!aIQ$Tk(pa"hq1R!hlQMcq#NjKZUPJ' qFBH4-jj%h+%hi%h%(AS*(NAF`62TFHlJBrJ6F3F[`UH)1hS1[b,Z`'@i'hIJ(6h &(4J%eq!1,)!cFNFIiQ[%(If![a&h["1I)ql`(!*EZ--R#El2(9J,0c6I-2%$rX) G@![[jJj0"GcQMKVMBF3G(MqmLc[k%NmMlUJVRNEF`CI!-HlJ'23AGr3L(NIFJBP J"AGJ%lb*1rS5[b2ZU#1q4pca(VJ$GhJNiB0N[Z&b"IJXGfJpk"MFJArJ*hG`82U D1cJr[)`lH$9p`4dm&Tf"1cJKh)3lF!@[+1lJ-r"PlZ!9V(R!(CK16EJ$Bm"UlX! JH"phB!Gib"hp$0IQM[i4,i6KeS,Hj!kY#mmZml@+2AKhFBH'KBFAGiM4j1'1'X- VZB-$@IFdFiIIM(F9q6jpC15bPAVMFfA[m,U4dHe@*rGNR,99rb"C0k"9Mb$4reV eqa$pVe92$h&DD0@$4[5r9[eM42r$q"SI,AZ(4jESIfek"(Q,A841eGG(p,mfrA' B,1F1hae`L6[mHG!IZ'1b8I5r0MhAi-lFi@&KhQM[m$J5rDp0,a,4rpVd(8'li!j [($(TEG-M"pcM$KmFdIrDp-!3r@m%pEAV+A#(Ra%H80cK833[i!lr(bDaZF26KfP Vl[!KNY8K4ZJj*2VI#,hMd(bi`fF1[XmG[NkLrih3I`N[,qlS[j!!P8'%N!#!ch5 Zld9UKQh3UIlaLhZ90LfCB+HE04Mpm4GQjPMU'f(#A*C+bmcjdR*"KRLhZmQ08,H [Ch*Nq,54CMF[QRQh-McAEV5+r0pRT[Ur6AP)1bHILaTp'0X(QAcISH&iEi$ZScF mlc8)0G[Md%K)frGH9Emd,R`-A'LIRcm3"c&#fVlId9NjM3XIZD(i+B6ERML)&Y, frD(ZffPFq+-ELX(2N!0r1!irK,&p''UB[j[90TPU,PNEQM`-RQb*HFS@L#B23bP EBakcfP!j$`-V25N2`bcE8Ki'AEDRqM$XXMrQDAM31X[NB4$QPT5()CPE8ak'CJk Q2!c8(%Tj',BjR2)`L(0EbX13!-k4P)F"RU-T$m-kGkBm$2,FPI)`N!"cImT$ql2 pLMH9AXQ$UAKGbS24H%[+Jq&i8mU$+IQ3!*3(dr,QP!GMmk'p2%@V4*1(3IJ$k6d -(Gk6mQ!!-5cP`FKKH-U$FAaVbS-C4&[+J`(pL*3(NrVfP)GKpcX5rM!dqjb8Kb( jBbN2`q1hTc`-'ADN1Q+k2c,P`C5r)H9KkBXa+3p,B)a2H9JJBh,+``$j"hTmVj` (+mI1p"i'(UI&2%1qPBGP0kBFHdq)i4H'X#E+2fr"9&SEjIYlr)6!I@'"`h2@5$@ XVIAp,b53!%`d$*`dZh&N+M[`fHJ8C,BRr2`AhD$'h(AM3,CdGYQ"6pqFII`(Vqi krM+"V@0DaSBhE8%[[(kU@ZLPGYrNe1BRF[r3a)4HL*&hEklAp)TkY*Th4C82%iq 2bFIE4DjReZFf0+VQrIV8Q(iBNDpGN4FG&*8KkiZ@8Zr8dQe2[QLp((qaRR$4hHA )KqGhG@rTUfMpEp565cp'kX-@1$-VjIicGLXF['%mMl&l5cA9mjfk9hqpPZKCC6h [6NY#rZjHS44HRrA9rYB4iH`*Vmmc#!5CUV+8f6pZ!a"Ep$)@PCJ$HhV$[hmbHml YhaU[c1RhKTR3a&4,B%(QHX@DbarGGB)p"0dhPY!2ZK)B9TMe*`h@Y!r&JV*KSYl 8KKClZmEU4%[l9@chQXC'P!fX09ac&`0kX5`E-TBhAD%+Qpb@,UELh[T9N91i-[9 NrEE)UPBRjrfXU49j6,h4m!j,aYE*A5hAVX)HX1fCGCF[X$E+)mCD9h$('N4Qci% EZZ4MIDE)k9bCfV#H915-Ur)K9j!!`TkdXe'h0U`&&APXc)GYiZMZd"6eBmfSb&R GaQ9BeGCTIcHfhKbL0R9DXBdEkMDB$+l6&RKmBcCRkVK1'@4#im4*hP5RGHE%UEa M2Q`m*kd[P%RUY*HF2&98XEQYdj+aka3#c4f@J&K#QqQZU"1i8jZeR0k+ZQVCY,V 2L+a3fMKVfEihB+-B&H[%%XlD&SXPA&3l5,'%LfSTLBdhGr3L0QG'ZUNAJE"bT)A j2f[C[YFbE9b[*H,Xl,JDr91[*DKB3YFl`5Dlb0CVIcShi%'ppTlc!Kl8Db-j2q" "[6,1JS!($8lK,Jaid1$+D1F(2'M3i@&4`)-'LlXii%'$0V!A"$aSd,Cd5F#$"Ud eP`BmD,![Z`-H0'T&Z#cJ3D1iY6cJ3D0fDLX#(M4U&ESbp,He"Vi`i%'MY9`9m+" 4kd`QE8hr0@TaZ5EQ`iCaEF#$*LHCe`8mD0,fqU+!"dhfjIU!"deDafi)H0#N4Hh 'J!G0pZ@QJ!G0@S0Z$RM3T(hPPS!(eZjfDm#$CLd"QB3e&U$0@U!bl@TUhDbe-KD fc&GKb`XZQhkfYV2)C)DR0@Z&#KBE'd9V)iZ9XTN5EpBpJ9SCI"NLaQ!*E55i)GU YBJR08$a[`a,D@"X1dIlbXN[c+qR4)IDPXB51JK0$l-[,4fEDp-d3mIk+LDd9F(b )eTeAATTG62eDV199MEBeE,'@9iHG&PVN%pFd@&r6h#%[AVZK-X)l@qJl,+(T[aD YG+m2q0HLGHDHJ(mYpZAH)&1fL$&Q1I)ZV(f(1K&qif6H*FP3qr+Q#TIQMYlBPdp @i5e$R8k&NaJq0&3,BV'%(UT0VPK#$p8'9LbKKfSh+TE3`m5BJjplRQX3$"0E$l( &P*%kKr(f52YMChH`A"dQ0lTYjlS+9Uc@k[3)2U1Q"iD*-8GG0X,FB@plM0+Ep`l 6J[9fHX[JeM"Y3ZmBBE-#dl,djA2fV"X%$iEEPhIZkSK,`m@#Zpbl`0a4ZqHLjCL q(QjIhKhH0e`Hmlc`2QXYq[afZdlGKfY9HSpl'aMUK&[!mBYRkp5j94jhEdCbF`F ZL#9dUpa#,+&Ea6#aK'l9fPFXS9[P,Q)*MF@RXi4Zdkj6,+(EY(mA5qJf-88XSGZ dXaC,k$CYPX85ZNhF%N[S0RYG,+(Ej%CL#6e#e`'aK"iK0a*,k"&LQ9K#Mp"'@bb K4fMT,*E3f'8k5qJ4@YH+*I3)E96&LDKG'9SXSG[P%')*hDiYV&K#YfZl,CE3l9S pLb9dZdD3!')*hDjPVPK#Yf[I+TE3(ES)L#9dKha,,+%lP0A%%VV$(K0,k!kYPX8 5ZN1X&8[S$Zeca4,DZTb+*I4)TAQaK"iTpaG,k*(DUSXPp%Ml@5bK4jTA,+&(DQ8 XPY!Mj59L#GdTrSQmhLPI&%[S6ZhZa4+k8qiVPY#GpVPB3RIk0V'%lY4#@5bK1m9 AXB3H*4m95qK4FNkaK"iPISXPp#KYf-85HT6p,*E3Shbc@%+2dNjC,+&(DI-VPY# MGI!35qM4fUD,*I4ShbIQRD2&2,'%(QhrLbAdD0mTPY#Ma3baK"kYhDjB3Sq4GiS Pp"MjM9K#Me%E%8[S-H+J@%+2XFI%%RU-m@)*28D1,TE3Bm9TXB3H+fm@5qLa1UQ **I4BF8J'2FD+&f)*2GEDL5Ad@2QI@%*E&eZaK"iR*a0,k((b','%(LG(%N[SFH+ b@%+2Xmr&%RUFla&,k((D'SXPp(MjX9K#MpFH@LbKamZra4*k[2aE,+((LhGL#6h HAK*,k2(q&d[S#GUML#Ad",&(,+%Rb&2&%RU#j&!XS5H)k@)*28&F%%[S#GC),+% Rb"h&%RULqS4B3Nq8CiXPp%6aALbK*fUR,jE3%m9VXB5H+,k)*I4%DbD@d1`$l5b K*pPRBJNp5@`35qK*BS0B3Nq51iNPp#5aALbK*iNMBJNpb6U+*I4NY65aK*kXTL1 Z5*2&Bl'%RU`++jE3Nm9lXB5H,'F35qM*B*Q6r#E6Efk5QT@pR59dPfXDLN90&qp cFQfA&XaL#GhP'K0L#GhP@SJbG0)&6MK,k#jUjbbKTp"ccK*kLZX-LLAd&0Fb&%[ S+DlP+CE38l3r&N[S+DkI*jE38qKcC`NpPEc1%RUUkb++*I48ebB85qLTV[JTPY" 6A@94,+'RZK+M@%*2"3HG*I48HXpC3Npcl85aK*lQqSCL#6h0e42&%RSDIHBXSDI 4Cmi5HTUVm)NPp$4`bPP#RdAr1%[SXeb285bKch)94,'%2N[A$l'%2X[e3m85qLc AmK2plbcAk"2plba`c9P#RdeIX9kM[@1e4V%j2PXR&Y(rcYCp"%l%(DZ-bNSBCp[ (S[qGE8q)rRFf1-9DMRc6U6[V1GSlqPK@`TMZ@SUb%XCd9f58P6#QZjUNV)3ahA8 "iHrFXDSL()FlJf@Xp-Jh`jj$cq'1pl'q!(IJK+b%-81A#h#E1pDDK(G`a`U#XK, '$([1p#cI6(#+G4hY(6dR+f(-G$e(@3PMTUY!bNSB-qdj@3PMTUY4bNSB-eeM8&E #Q+R&ZDb%F3kiaPU2pSkHNj8`cY%P4eE#1-F9)f8PM(0F+e9@`MM(05YP*BacA)G 39X)iajk6P6$1"DIX#L2FQEUc(U5p`ajG9X)iejk6P6$1eETG9X)i9aYd@3RMA&H %P*8`cVARC#@-@IDdV)3abji6*ljC[Np@`TLP8iQXK$(,062&hA1@Db$+5KLcA#p 59X+BEFr*5KLcj41b%XCXHdj@`TLYKLmVBFc@qPa@`TKYcmP+',1eETH9-'DlSU5 -)ThR#UDb%XCji"TVAGSlHNkQ8Fl6CPe@`MM2e9e&rcY21h[4rmjc*8A4rmjcc8R 4rqEBFl)5aKa`LV8`lCfT1qYKfMZXff8PM$RfR-bLc(&e@&N*BiiV@-UXaKbjKDb %-GHHNj8`jYV6XK,'A(Y19X+BkrYN*BbjmL&C#@1Z+cR+*-GFEHYP*BajFJYC#@1 H25FVBFac$3"C#@1H25%VBFbcjd6rQqIkRk,rcG2@Ar5rHDk"+IVII,Q&k(rcAGP 6p,rjFJ[4rqE,%8ArQbq1L[ihhe9#4IqE,dF8r@qqp[ULrbe`E9E4raCSSbrkh`* l6[5r"Fk!L2kh3'iKqYm#ZBASI`YF@92d[`@ZXbMkhd*A%aApEk%p*rVI3YmRqYp #ZBASI`YGT96d[iAbCY(r&XSY42mlhp9K4Imlhp9'4Imlhji3rHpmHdld[r1T1bZ DfMZ`Ar5rmee,325rmm8jdIm@ZA+Xk(q,A*&8p,p&VJSUqYmLZB[SIi[NjD,r,A+ PAG(r&SRpS[mY%SG%re[XbUDLrbffjd6r@qbk!U,r,CC$LrkhQ(jJ(94laqU@S[m YGK94dIm@ZckNk(mAf(1LrehJqd6rZd!q*rVI"ESELIjh!E9QV8alaaUCS[pGi&U MS[pGJ)E#fTPm5q`2dIq@Z&+#k(p,A,Y8p,mPpU,SId[N(+,r,E'ZS[mYN4q)rVG %6LRkha*V,2VI%VQ)k(p,A,Y8p,mPVN8UqKqqkkbrDHrS,G(rPMV',2VI8PFm&Ie [UBjKS[mY&AY%re[U@JZLrbf9pi[qYe6X&re[+6'Xd@R[i!'Lrbfe[dArklBr42r VGL9AdIqkl3r4rlVP6+,rGDYYL2lA,GD+rYGYIiMqeff2L[lAEAq)rYGY286rklB HS[peLm'Lrbf6YiRqYmaq&Ie[QEa6p,pPVViUqYmb9h`9r@qCXf1Lrbd64dAr@bB I&Ie[QCJRqYmbqEVSIm[%E0(rPVRDTZKrbq9jS[mYPdH+rVIFZ624rjDVEBMqYe` R10(rPX[242pElMV)S[mYYcp%re[ZZJkLrbfh2d6r@klf*[VIFVQqk(mVe"*%reX K4a6pEi9VdBVqYm+C*G(r9UKeLIkh`M@'42pEBHq+rVI#PCC&re[KfUVH9H3RAIY 8p,m9VKNUJ5[!-PElY(F'#eMadpkCrQ(96hYRDX(+Rh`VAI06p,q9VLJUqYp+-)p 931dGUkD+rVI5Y94&re[TUV#LrkedY9I4reDkJU[SIbYGV96d[j@ZmbVkhdVA(4A pEb@pa9UPpXld-'Z1mPe),9LRe0ka)URSIaHkiURSIaGD$p(r,U4[@028hY%VS[p Gk)U[S[pGk1UaS[pG#+k`[LRI+RU'P8hYRAN$Dj[D1eC@&Ie[P5ZrL[khbRP$dIp @ZFUXk(qVA-e8p,p9VJSVqYmUed)5r@m9[Fh+ThbVID[SIkYGJeAd[p@Z&#[khfT `La93l4hVd)VqYpS99NAr@qekV+,rVAD09Y(r9S0pV02+YiEqC1e@HfIHCYG8iSl e@%Ar@q1DXD,rVA%0@p(reYK2S[qYF9eDdIr@Z&kYk(pVa"M4rpD!@DcYbVH@hQ0 e9hYRmV,#UlfMaU,rVAApA0(reVVUVHKrDm8jdIr@LQfLrkeeV9c4rpEk9Y(reY' hV2aUlqJRdIr@ZEUYk(rVA)&Ap,peiTESIq[%+Y(reVNqV1KrkebY9[5rGI!+9Vl PBpNeeX+eG`B,@!rAhTQkXb+Z[@20@p(r,K)[4Iqlb09h4Iqlb(9K4Iqlb&9M4Iq lb,9e4Iqlb29j4IpE$qkc2Ukp-aM('VRfc[3`kq6D1r0qeXUeGkce+rVIHYIV&Ie [[D[$L[khAJiKqYpkelF9r@mpI)QeFrNfZ#kXk(mE`%h@d,9hF!A4rcEiEY(r0[K ZdImfZ0U[k(mEd%&B1GMHXHDXk(mEA,p@p,m0m#T@&1EEk,UeS[pY"0GB9GMHQ9j PC@&lCpl'kX,fMTi@r@qMDrk+rVI4eAj&rpYSEiRqYa(1b@V$I*[N!D,rEE+R4Ir E"0D`mV#p-rh!kX2f$S`8r@q6EaApEj0i,2VI*[Q0k(qEa#h4rcD*@k,rE4BM4Ir EE$q*rVFCM'"0BAYRHS"eL1dGka+,rVGCr"$pEl1i*IVICYI$&Ie[XlJPqYm@9li 9r@q,DqU+rVI&GAY&rpX#"YQCDqlJ(k,rED%@V&jXleM49r5r,Dj2,2VI&YFd&[e [Laa,p,qYiSISIeYGK9Id[kfZmb[kheE`MV@0lChT6eBfYRIJPZKr@ehE9r5rVDi 9,2VI9VQ)k(pEIEISIcfq@r5r(R&,p,mHF9Vd[alV,ITI$lh01X$fcY51YAlY(9a %p,mHZBMSIcfZ#LckA`pmRY9mqEDj2V$SIpYmUqKrfjaY&re[QaJTqYmfDbckhcE HcfV(pSkH&[e[QcdYqYmf0![@2HEElYUqS[pY&lG%rp[ZQX5LrffhaU,rE3FI@AR ChS%PS[pYTaDX[fc[i1LLrfehY@24rlDl3V$SIc[N(k,rlA!eBp(rGXJM4IrE)@D )rVH$AQ+GBR[(UX1Lrqe`c@E4rbjf2@(4rbjf4@,4rbjfY@E4rbjfK@R4rbkfEd6 rZjMqBG9QH`IA&rh[B[Q6k(mlAA9Bp,qGVPJXqYp1hbIkhdljK1Kr1m&69SqfGh! QdIpfbZp&rpYTr86rfb@(%2e[PkXHLrkh5b0ddIpff4qLrqebr@R4rhEj2Y(rGP% [9Q+fGq#Ck(qla@r4rhEE(k,rlCDML2khfrH*rVGEc8$d[peb"G(rGSXVS[rYMUX [fc[d#G(r,T&2LrjhLAaDp,p,A&GDp,p,A2YDp,p,`&r@TEChk#kLree#h9N&fpl "+8ArHjDV*B[qpbaAB4Ep,r6Q-`KQ0P,F2ZP@IfB[aB0l[QX3&!Eka6G#-KJB+AG F$&YT!11#*+*UL0YR"d$-'%Km(8V-im,H--&Bk"cVYYF0$1c'Dfe1ClEC2pfD'@J AVGVXG,FcX,ZfCq##rJX'DUhTcN#eABqc)5%MAh&&Mj!!PXqbJ[!DZfUfq3L&@E- K$'(eJhT(&G1pPQimQGZcBF`b-KX)MM1rb0`LmiV-+9TI3R-bMmM-),1)c!XbHmJ X)[1#GJPkFc*hb'`JXi,-!M)rb"bJc2q&+Rb0#j`NJcFRh62rH@q'TpdjRmU6UQS )h"F@D&CX#&efAfA2Ir,[2RqIjE#%$3rr$f1UIBdPaIZAa9rX2S2K$NX0"N5h8Y" -T-NGqZ,XE0FFGa$B-p[SeYF0cADkVCQ+hU1(LKVZSVN8UkGCLreSCD,DeAdd&im (+rkMaR,ejZE1"e+XVhYeR3kNa34iN!$ZKH%G+kS2a"Zm0K&lmd[bjS2KkqSGVEm 2E'p!%AYcb$"EEc5+NR'4,E6*h-!H$V5TC1%"ASC,UdAc`4U[h6!QlFK(EYTF'@p hkc2eUrlME4LE)jmG"J*+iGALfIKRMAdpe*[cmr5j(G9Qh[KkNKh9cR5eFD6kNU+ [r!`69PZBm-%@6X`MpNE['0l`8'LP38cikXl-0aYJChl9NHTILVXeaDeNZ21LThq lq)4A#NZdUjlmlbS4GDY@b-Q%aZkh(p**8!&dSQY`6S)UQ"0HJA+Lbd$ZJLXBi$) %MH*L#deZQk)+i2(i)RlCq$ai%eH"EU,,`"d,,KHX!0S%$N!f+@U!R8K3+AFCV&e `IjZ@J0V&CQ%k&PKUK`T%%ed"D+,li*Ri-MLli&)TI@"1"TYUpF-`#5S`6(30KNP 3K@(#+c"-G"Q'AA#P[ef'S#PFE+8TUM!FMbrLNSh2`c"a&4JQZJc$XH"b`3S`61! !$*1L"X1*"*9bPf(B"IHhD3Q'A@`@KQ1"TADS`$$4&4JQZJq'L5r$X!XZPE)-`qX (Til#-!NU-%ad$BC*8)9K`LX`6(3CKPe`TEpGKU!TA'bP+DS`()m[iT+0cm-`F48 B*VS-`l(JFX%+-%cJ!!b6SJE$L359FTGKf!AhYfN*KPeX&SCMJD9fU-!`d48B*VS 2KSN[`l!,,T8b"m1RC+P"BHU80(9#R"U8T`B%UY-59Ep)05"6R45U6NT9&E&U8+l kVVKd5Pik*6!05%bR4DCqQDNU0!e)6B0Ldk$FG%Vk'44r6XNr*`5J33PS3!3k,32 e#d%$8Y"*-HLN(&34K!BPSHm+1+FNR&-LcS#-FeV)kCGbUQ,1J*`c+1J-5MURj*9 "JH@8a(*#C"Q8@3D%PY055lrB-L#hR"4F6NSZ&G&P8(EjVNKb5LBj*C3-5#@RaC* qZD3UQ!a)*S1LbD"XNT`B,8NBk54jZ%YR+!*H1NN!HHN8HG",CmM"AMj"[Krc@C) GQBp209kQF3,i+q4)BdXQK`q"kGJm#+BcP'!`RDB)K-8NrHA+J@%q`FRfb`*L2Mi 1L8&`AfrQB6'GS4mB+i*(1NNr-&C%Mh55!@$X&6l5'@V!@"8rmPP+R9N83$+0-`# -C4%NNk-A'(Z&N!"dKP2!@"&$LNRkbe8$aUSNNXr5ehjPB#`+)lN%9@$X&8I5d*N EH3J5e2!j0IU3!!iZL2RT($P"2jqJMerNK2ed(p5Uh$YM&@3)UPbH(%VRU&@j-%' 8MkqU"lND$ik[9!GB6JjN$)aNp!pP$)aP*!TINI$55IV*@dA'5bFC)'qp8Pik3if m9H@mI*B5)"3P[8cM$*!!Yl+XPmR45pjkTEedKP2NV5,[&C2dPkY'hUSLAcj,ArZ 9b9Y4kXXPU*+hV0bApiI*iQ+3!#-*Ld'#$#S'19+J''4)BQ)K`FfG9M0@Zr$%@h1 XE-[K2U+@iT-GA8SL$9d+GbeED,F8QPC5a0#TN!$#`p)J0!QP33+IiTAMqdVS5&i 3Qi2T)%X'TDXjDQhJBh3TrN4$*a#k&!j!Pf1VRC+%jb$"#A41XqBJK8qE5r(9q[V %14-IL*j"MKSr##62)%Fr2mJ+RS8%9AjJReMK"aQjY"4IJj1d@&S+Vl9E2cr)+k@ &&%9qN!$95B-%II`JUh+9%q6j39'$$E)-mS0!J5hNU2+$J[jD5P*Yk")rb)L[[I% 9IT!!P9k$"!2m)#-CPZ+VpHhM"i'Z&Z5SmB0!93Ybp21$V+C@5&$P"rD*&Ak3!&( N5[%e1%RVFDA`@V[emi1m'&G)8H3(@5NZ50$($l)DF6P"RKm8CEiJbb!r#%5q3Si U2bK)I+8NeBBZmB1-[YFEAq%(*p5p[1SHT1MM"fRG[46ZDJKiTA0Nq8'3!#2*$i) %'Ai3j%MaJb"$NKm%#Ab!,m8RmD#842UP&&lVPa6!9e,%N!#YN!$#!rJJ0!R`33) Ii-[aI59d!"r%jJ!qb*)"q'U1@K[i!&q+2p(3#B![K32`jGKUTb3"2NL3!!6i)%% Di)-82X#AiU[e6IVbQAS1!Rb3!#-*m%'#$-!(19)!(f4)!Rb3!-!(q&*m%Jp+5D4 I5Z'eINN"I#9&$0N++6b!$d+6!"mNm!'q(0pA3JI`3@`1i)-X'B#[jULeJ3r`TIJ 6$Cd!q&)i!&q1VAC+%Z#$"%Q!$a+N!6j)i30m+EjDhd%'ElYpDl@jFlDk-rmQ(X3 bP0k`VMAp-+Vi1GK1*CK!F(&*8Z'#-N6#aDA)JiY+%JBAj*-%2bD*)hkJp*BINUe K#[46B6'%Li9ji1kZNi$ZJP)pPi`5D%r'C!T5DVBFI,[)$'5Ril*&p+(CMbQd83+ #r4"J0hQIVPB5APe3%P*G8"T'ACJ2RAj-ZKBq4")6f'5iZ#`X"@BB,Li(5eR,#aH 8JD@#XB8IQ+KKaViL9X-F,190+Q*KF9M+@P'iS"`XC3E%Nc'CJJ5`9$5eF*%",!A @&E'i0#`9$#Vm`(3EqE#8FCj)a+4J+HX[iB,bX*3CC[GMdV9)`e)!59Ni#U!S"d0 C#-V!6`&kdV#6JC`mh15K*J%c@BM*`8X'@V+`%N"+%8i#+!PJ*!-K"IK)3iF2'aR )b-*&$LTL5aS9@%Fm1XXpiU%"!iP(jhK)2$E,4Z+K'8k5LXa#DLSm!@DT3"p1%jA 2FC9-F",X%m&ahK)2bV+AH'L1`k4M%d`Q(9NXAF"UiY&&EK12$aK10VUhp"QfNiU X0QLDqD3#(Ip*4a@UQq9#mG"HQ#Z4khKd,mb9L(BmZJ4c"G)G$bh#A*Q!Tm+cA45 3!2&%j8X`ed[-%m%CQ#Z3!24iD!RQ!X+HMLb@VJ*c&3SIMkr!A)R1*k),-&HQpUR `3S2QB#iJqmR)!1B+a(pVIIY$A-l&CL(1"3B!jf*cm1BLXq$Q!M23jXGPqmB26R5 0(qCh4kc118K,K5Dl1KBDKc-ANJ8c&jL$XQ4N!XL5F8'a!K"cX88)Fp%"J+9M#iA 1J*FI9fl"0($jB3kfNM(jDQBKb`9Q!@[Gk'KP,C(R2!"CmHJXD-9$!pL+4qH!+ak EKDjiD!Dm8T(ChNQ&*lSR&HMh5U,b14$,"#Hl1a%F"l*i8"E+iU%j-%[(*Z!X(9N XA3"TmHJLU-AM!eM,4[H@2J0YUFKUJkEK,4AS!#iG9DKZ&Z6LS39H9K)IA'b"Pj@ %"aGEj'8&dF%&"VbX,$Mi`@P5%)J0X6SAH9Q[d"!,6I'bJXMJ!SZm,"!BNR&"X8U mV#)YZ1J5,b[*#V(B2#mV5`TqF,i&-l`X%"-5F6PH9K!5iKV$ZRcll-kGH9%*-*5 1AMmemB!bNCmqL!GRCK"5N4I06HHd["RG+V`X2Db3!!SX#S@9%K)GP,"hVLFHA#b KLkb@-$m'P!S-q(433"HE+Tq,bKI2K@C+jmF9#ZFRb!X$3G&+`"'M,GQLpB+'#`f +9J--2d%H0BYJi5M0KNCV1pKGNcG0Q3j8Qc8I9j!!1$hQd+X@!p!$Mb5&HF1qmmD rT6p+JV,1+2%&h"XSG%c+kLed,,jFD+F3$6bb9ZKdJ[,F3+l3[R4BU%"5VmX@14Q G,l%[JG@Hee[HI(L[k&BXE3fUNT5h80SqQ2*CC1ejeG*@!#SIA@#@)23!FT46q05 N9X'"4bCTc-lC*KNb%&J)cr+f62$!``LI[k"ZP%M%JV,VZQLl'iUUr#FG[r$"QBE c+i1e@Yf-8RG$RG*PlAmp'ITH6hcKp35@AqqkT[4f&epmZBY1[pZ&e9lGefmZ[[, UI+qjX-+V`lbqh'j4N3heSU-fHp0-hZaQkm+DBE6rTTPfUqL@Ll,e6'bpjhT0YG& Si4Df-@qdXl'YPD#)fN5ASQ"BfC!!@b2+49$fr05C$BV-CYAQ,CHfLNDYIjTellC @K[TPKHZVDjpD[rbLfMRpP-,'#FN``9k)8CR0reLZZIIN-Z8)AJ&6R01)1AD0M'r CCKBEQeNT*l,Z[SK-Aj!!*&ClZC6DFqXTPC&Y3q-E&KV!aXAl`5D9D[(!@29LYhE c[4ZVdrPLaIeQm,0kpA34UI+C4V2PbfcX%PRA@m`aPG%%jc)@RZ&D)p13!,'fNiF PZciINNP$Gq4$-QQSBMl%KjA$"j1QA-d,9ZIj92&#T)0bUH,&5!GYU-lN*IXb3AI N"9eYeLE(81p)cZUNM%dF+V*S`HH(G(ppEEdJ*TZ)!J8af858*iM*@jAi26lc`[V pH*X+5SANE8dLk`Jm8LhUH@GG4$6hhh2-cF&q)U-Rr-5FG5f`'a[$JfAD&,Th(iD $iL0FE40AA@[(k0TE+j[bDZ%i8+lmX4GRHb!H@BT,i(iL@5`N8b9dX%20GBG)35Q *)`[9$V06HcNZN@kKFM91p-ck`bf6CJ@C[LQ&ji2&HL5blZ#&Q$ji!F$KFq[YrU* 66*FAqrah3e&`FDaDCa9)Fh'S8mYMT1'GjYq0+2EHcHe'F(ecLi[EZr8'IfmU0ED Mh1`TVQahqAqXHf@CB%marC3,`rpMeHeFl-eh0+TG(h1Xb(06APr[qVGlS5VfCPr jekY,pd*KZJp@aZE`8NPYZ,,&k9kS6RFX6hH[2Yd(#p4pX%)Q`LX4&ek0ZRY&kMj BTHjBTKZVHmSiqHmpfUZ([6K3RHjdChIX)0CFlDfA98X%FHG&QBY$jFYL&h%3-E- ,92&)8)RPdS(0NIb+HJHTLCFPlVc+QKKhBGj&!ab0&A"h8S"i+@bP[2ViY6*iF+M 9f0kD+pXJGV82@H1'SUaAr-VGQ2caUpZEpEP'2E4,iLjfCC)PlZblVbX,',mbL'A +[@Hfk*5[L&qj'pX#lST'1TbcFkrA8pk9Zr(H*9IQ"Nb3!##j1Pc8Qpfb4q-hZeU c"@`cNGS2L6@0LdQ8aBAijABaLAC*[-C9a)A%X-i&a-!Q8j98S@*3NkP+)X6[c8a 9dQ8R`'*c)NlZ$AqjP$&%2f-m*,8MYL8ImHZNBZd(`dr@6lB[hh'`X0!F`kRNJGh ha1i*4(N1"Eqq,&Xk9bEq-(6V)&U$Akp%61`Ud@'*Q)6Fl"A-A@l)ZaYDphC"2)3 E#)VI2BQBj'#TpkciYHQbJke!3e*A4pZ0ZL3QF4@V51)PANI0T+95!6C$3XG1*,H j2'S%lh)APY6k!1%&q"#BM["ca&Sj'4$,kEGP1Q*IPM[KZQF([54hA#9kbBp2"AQ *BPG"q,kib(YLr$@lfAYfr3YrMMFcZjZDedh1k'EQj6+@X9NhdB5cTKYP5mrGTQG YCEif2RbAmR2-'#HQ"eLcIS+q-@$@#6(K#ZJF$K-1II%Te$flUX9-p4"T@8Z)DC& i5*iLq5hU3V,FbQpc&j*P*$Rb%qIEQHFR8k6BQ'-mlMV,i(,X+8r&mTc4alTXL%P mY&Fc3G&dK%NV%I&H-h#qDblm0kK1#KI"K4GLmL0XT9iN%BA*Xm+mQ%'b'jTA,$i L&R"J@X3i8K*kpm"ib!'(*2CFAK-824DH[!qQGA)61SQTR0#a5Cc3KUq*A@,VbSf RSb`-fl*dh*Ehhq'c#q5#"k&[J*!!`)1'J!IGpDXkZiUJ+R4RJHQ'XH'"q9[(AXZ +QF&M4H[jHE'R`d#A'FbrVR!fRm'1ZdTpfNb`l3Nbfej'4+qVjF85BfL4i!Ierid (4X)00k-,#6aJ(ra6H""f4Ki6H+!#(RJ1,EHhRAS2Ba1A%RMJk3FKE!K3a!0lUE- 60l@`GHVlkXE'*ST(ASfk[AYife4rifLHR#e$kV[hi$[Z1[U1[*P$pKfH"D3hCeE i4Je16)`q8[PV19HhfrpCpbIHXAEmQMh(mKJI&!TEbl'fdAPiH1Rd1cE[,REdFcj 6elEbV@[A,`h3(cXR0`mY$I!1Lc$AlcU+-,i,6qpRhh(6p*&hj,e*NPm-1IGeCai "%IZ1r8HlqR6IK``JqB([`8Hm(J-F"6HNlliM&)"CA$ib86RfeX%qSqr0,1Ak4pl "YlFe2IY)Mi',eMdM&1!GI(1Q'`aVrV#ZpKhlUppMThEZLRHB!G`IpePff$[cG5d p`5KlaNB[2TBRl8C@V2b1dBH4kV[[#!eJJYX[h[KI#*bb95Ym1dCEfjF'U%G)"6- G`2+NY9cY(E21A5VJ(Id&qIYhe)$mIlpMN!!422'1'qD1&Z68&cDJ*2b`le&X3JB 8J)(Z5,ND9[[M-#iB)3([f(1N3`El)elA2EZqMBarril$4pMlB&eMl`J28%L1jMZ A#-#c8!#P*Aa#f6LkUr%`AdalFKBq()A#!Gl"0iFQHDDZ1`kqidG0B[@'q$i%a54 $PTj35%*101A`!!BA+U'pKLXJqHN[krH8q5BYqD%*QY,f9[jT6E$bMR#6kC!!Tc5 iFRGm6i-lmBiR0EJ6lhK5Jc[jMLFdZ-&hK&*SF29lEpR2"&iNHrc@ekeF1hBUpar )([r'IGRM2RA0SET1ZR9p0VlbcK9hR2abiq[hhPCEU%F)J`CADE5R0EM"GcbT`I8 qi`FDh)Ph2+A"&4m54U$"pHF3rr16l`J&B0bBV!r@,'[%R[p#2l5m-U"p6mZV-TQ `!#f[jb%T3VlfSG%YNipd%%`RI'+k+$aJ+LMXC(VQeU--cKKh-VNApr*-I6'Q%ci aK@-mYhq-DGilISM!XHQCJ5QF[kY(q-hdc,'P!(`kc@)j#bqX,+k#NrP'ISF4Q)I 81[ST4R$L(8mbJK2[H",*6llM#53II%Gi!*+(,mc6pGBec''HVY*S6c1#`AFmb3K kRr%$4R$L(8pTHF@(a0ia)$1CGpL0P%lJd*(m5*raL"Xk8C6SHdFSJ*E(&b)`,mC +'08[SGK8%Gqmip$fhGpqarEYZapqKdc[XkCANF)0r4p[&I1+5Sjrm&DT[H2dY-U J@Ka#-+hb)`q5'00j`S1NeKrK!@Vk2hKeP1[a2Dq1@Pe2UpHRqjl[5Bq0@MhX1jl `aULp3hCeUJc#G5cj-3IR&6LSr02UGH8Gi44cF%pTAP5eGl,K(c@[%qpi8[-kmBi R0Dq6lhK#maTm4hM!r0T6@P9[2@)-lLP0TrFG2p"d"YpaNJP@J&@qN!!+Pk4`!#d QYAA!d%H")&X(0#DRj0$6,l@HR,H1BmM+&`ShJf5r-lL,$65L0chhr0,pHY+CFbZ ZZI[*h+r+6RrarZa(VQXFUZ[%keGRQfjrdiTRAhfAmG'EUTpCU-FCIm8''Xr80Fc "YIS-h@8$M4#iVfGbC2LdN5BDpX'm@aQHDcGDaAGpIcI"38KVZ%MSLPeUD-cA-($ 5l-D4UHc!THH(!'-frrR*Di1rG$IFDHRXXJ22I%Efm4qmZ[0f3LEdEFa1(K[HY!@ RSHZRUS@Z-IG06Qeq)[F268b8cPV[f&b[UISm@XflSXU(L8H2qhLl++Fm2VHK86A [ekH3!&(-rmHCa$LDpI@GY,jS`BM9MkjBj+(4HVD+[pH8GrZc-rRlKM,`hZb(q2H 0XQDcpF&@*j9hFl+ePDc[CmUlml+RmHr&-4p@qQq2GjZcl14ha#IZjY6Bjr,C!*! !0A`-k,lrlHYffqX'"P5ejh4QQrhXiM'A)BZpXp2GcX$ZfTk"#rS[')$*(afSYZX $5j)dJ%CS-+"SIk%[hmJe3q2VKpG8eU`IR"VNlik4SDNe5kXd3#-l*hKI$![-mN- )KrZP60k1-d@B-(P'm2H@P+HG[lHQ2#2jHc$PkH6[SC4R&(m2Tca`cpY5RM(m2C, bM1A[dC4R%Rr[6(NQmrHZP!ISZMrPJ5rAaccQUTaR0F&e+Fp'JTY5RNebq90jc)b `1M(PkH([JC4R'hr[5AQB+AX6JS'(Kj8mGa2HN!$HFar"Be1HPa!m-Z9jJ1#1P1H Pr,dqeI&"`M[6Hhk+i#NTcrd%Mcq@j``)i8[YF0EbD"*NKl2UAJ'KTamlR1'D9E2 ,$MIj3Z0QN!$1j#jf1(ZQVQ%11bHFD96XF&DrpjEpj4k9NlHqEZADX91jrd$fq$I ZbalhU@X1eAA5VHZcmC9hVVMMj*FEAlrhYYT#2Fk-AhBiLpiA&3kd#FXePhHkeBI dZ*!!K)qp3N*N2SYTCb!)fmVpMiq'!,D9q`UEbrREbRhQCVH91qBfF'(UfmU&ebJ -pGRb93GYp@FLe*jcIiS,iaI#8"Zeq1T`Z@hckS'!8"JT[2NHk$E6p(RS([c#"k! pqCC,qUlY1h%C5mkj,k5JCbZ2!L8F8X6%N!"5eH`3'cQLkdF[f6DpTekE+&UlYdi bZK*G%U"`q[jKM[pAm1+kK6fFQcLhFDlLA-fjNA-,jpfFScR(F)lPR-3jQA-8CbG R1fFEj`M1NC`c1'rK[)rc*C`2F,k8md&i01XDARCX,6b6Kh80RjhbG2$hmT5(G3f [6(PBer#UP!IalHU8Kh80VdPj@0I`fT4R((q[5hPBer$'P!FamUD8"ijiAmV$91c V8KkceQ(NG5N2`emReL%dHFckKj%hT$aQrF2)De)Hl%9HQ2+`rZ%9+3rV(cirjB( aI#EPH5(KSe1H&r(h$5Q2@4-aFPh+BpBV2,R@SFPMeMp8I5N2DbGf(FYcjSh`SA2 !$H&pjQcRl1$Xj"c&1CTcM*`I2JpAKiI$XH(2F'0i,j`@[JSAK4I#qH"cF$9iQ19 BU686KckD"&NcXES19HMTjiEU&erdX,0`@-NA#MH$C,m`932+-&V$Y-B!KXm`2XY d3L(S6ZScQaX0f65qDA"XZ(pifcG`hNlH@[CVrXMrV*d4,hRb`C%$R(rqD1jLEG2 S6Fmp[p3"*jdjYq+DZjr-rDVXp"I[chlNZXDKZNkmIR@fkIBhVAMfeAFC(lfTqTQ &HTca9kaYqNaG`aa@[6XMGeREp!`%BCR0,5b`bFFbQlZZ[AHCcBh2F*R0SfmR*,a NQFd`Qp8G)kG2GQYZmm,-c0&@)lp[QM@ffCieRq+NdbllNb83DK0HYlTM+!`'K-4 mBET,iRA'T461l"1B8qN,SpMX08aJ1BNcq35qH(+YNc2["8BCEX)+``MH-j(c#h& $V5r'kGqrF#mpmhdTX[-[Pa[c4V)[aXlkDScrbh#[IMM'I5h'ICeYfIRqUTaBMQ4 ha[ar(E[UEf+qEf52+IrrEAcR0m0rY6UqkqciIhVm2b2Qr9CmclGMh-3BpeKmrq1 aMYm*HEb1#G9P8Q&RAi`(0@qmZ$AEV'%T9NaNA38`46*XLSdP[c1rG@66qZCXB`N !"l,3d!r"+DA6%f#$E(4LU6FAP2P#!0Ce-kqUVrDhC[r[%H"mcf$T31-@KJSGk*2 HZc1lK1q-*81&5Ba0Kq'S-'Gf#9p)mIa,b)ZbmVekrYqlm,E[c(3"!cc"4B`(*55 FaVR90SPDJ3fI$!,92Y4HqDVf`#@a+a`#&d*PqMl4UfG5%MJCl`SDZCd6Kfq'mh( %EZ$%+4ZAl$'FZ(@c-eJ(j`M1PSJ&Z(HhFJlPC0q`8C`iGSrN(-[Cb6PZ+BIb[Qf 1lESL-jhZi9hIM[eUPUdf,MdK1KERmk('(6cF*M2j-j1iQqm0Dq"p)q2lkQlV"AD r`VE`hZI(+4E5Uir[mq0QdLI0qfHkjHD1#D4U)&rN,Z,BBM)4erK-rR60G$Z(mc@ k$CV8bArIX"qMc@I2Y$Z(ihEF4)[[RHRZ2&bR4VCDLjc+ZkPhiRe0lqI2Vmed'ke liaEZ*IqULG&10e[q"AGIQacL1Rq$2h2+AGEU2[3HlXi,F3HI$p4X#R([(65(&cI bAm8J,qjAAX$Gh""hP(k0V!jahcR("T2hI8aFmZ)qi@k$bf+q4rRc8"NAIHSRZ9X Hqjlpe6D(I!ql41D+%0IbjX9q5K#ECc1('1[,4&bcZ9eI*Z)Dpbhf65+ZjAf,IC1 )fr2V[IlirFZiNeeqphbdeam(a9AC$(1IQ#Vpm4XIjUiRa"e`efhTM`FrapeP-Hj RH[eal58@91*H[G!IGDqmNl[,Ber5Rejr4+IXb5Y#A)Fpj08TqT+riNj`m"G@,p3 THVUB)CZUYPqd8+IS#phD8RC,I35mP$T&Alk&ZcXLlKVmN!!k45rl-qi-2YKm2pI Vil2&0[+$kp4'k[4+0d58h9mll$q[6[T*Rq)12+&pIRDK6VV2A[pfL"[bSB8kkCF kFrTBL*Yaad+Gp-@rc0hMXBrT6kp1H[LVh*PGk[L@[R1K6ZV2k5d(MGeLQeFRYCq P&Kh$(Q+0Qd,rIH9hL9XCFAU5A-UVklV2%bFlZcA*2b6IPrqCZ+YM(*[SHIRUAJY h8qAZGbD1hHfmI0'9p*EbAB5mTjI[VKF6*cMG4"p,(far#RdJHq"&6KBc[,KYY3Z )Hh1Xhk[i-cA8pHh'I65q!kiRrG&XAF&R)2'qKIl3,`*Ve0q%Z+%Z-1ReKci$6U6 q0[)!qY*lRck0RPIr&2[l&EhhcB5R+V',IUAZdRm["`m82@*j#FZmbIZ@`@r99b* 1rc*raT9aNAH!P9VqDm,(mGDfDd2FErdLFI"Gmld+rY%3qLEb02L`PYqDI,2Jah0 [$A&AITBiq+lj4T!!3adIiUk&HfKj-Hrq2B[VaGh`am5"lF4pDU'ZN5IF5KbFQcJ ifA$MMXrrfpR%JIrJUhQ61LlNqp3r%LFFZdQHXc,%(3*lY([rm3lUEYpKS28"iLC %r[3R[%0f$A`aNp[DA4piKmNK1"(jrp4'4r`B$BG6TiDii@ka*rJa",i5Z6$%IC' HeR'Rf(fmThiLe1qVD!Mk#5(ZY@q&,lD(I!rF6Gc8%0FU"lSqa+hm#q+Q44b#-bd *F4I6NeUmSNlS&F0Lhm`Qc[5)M3-RT-q@fdr6Babm6ITXrkZ*NfA[4UTcr(D)H`p [dq+YqFj'$e"RKEK4p,D@Hj)2h(mia!eP0d)0[lCi4RpErR&mrN[`84ehqecm,Zk NRbDq4#iZIB-Z)6Md+*a@"hkXR[A&(Jlp+9a,"hkXpVb`Kd26fDT9"hkXpY+[$SI Qd%-kEUJi(plTF1J&Vb,1B,AY*lLAp-HGRb"Z3Dc(bhVpd3'2e%q*G@9h4-'26R" D2cA%E8,RF$Kd%Ea(Xd1LlH0hpA$SCA"F(IF5(UDZ*1qiiUA%A4$L0X06(3jp4*b !2e)RH+h8qe*Lp)q(Z0Ir83q(ERdpFD)(Y)Q$JN-cl$p2$e$Ai4cLiC!!@9'$r[$ d!(8pQaFk(2ShD"XkkJ&M`"k(3epq*A(#cpVNiB*$M@#"M[bXaIF,$Mh(ZSTr3E[ i+(dfrAELi)1d'$a-qZc2i-BkEPSl(ClUF1Kcm%XGYdImHIL3!-1KYlfE10Q%GXQ 024cDLGDLikSI(El(im'4#ATBK`eXe9XqeX1Kc3HiJpp42rLcdcqmc6PX[VGm'Fc m303riR'40kZ2I6VU(iQi$KeDR2i4Mp1VA(GiAp3r%[R'LSq#IbhL)VU@HIH[`9m GrVd@(Up(3Yb(U+Z(ImIRri%lc@k5a2hqTKlqADA@*6V+'cl6`lpAQdpdP!jjTr6 P#ML%MMV+-(QGlF[MmhI"QcA[XR@LVi5(I84H*AZd[J9mF[MhN!$i,FXr,j!![`V qAB9fSXXG+mdlf#YIm1qem'1p1G6[@q#T`lqAL+qbIhi,f1EKhr(j[r`)FHKA*Y9 MD+`1rqTrMMM`h(a,h5&6m'mY'S'@6jP8Mm2I(!rl@lL3!0iDqV*1(9,`le+iVik kdI9I1SKraqFr)$m6h@L2pE,iGhcqGM"H4peS*(c&iGp9k-3kkNB,ZA0pGJ303$m RpJ&i)(hfQ(Km9BKlUhJLq(H*20[61I4ap+Z(ImIRhb0HHMU(2PiG3["[S4a,&SF p+Mm8([B&qEfhEV-q!9cfm1rir#I4)(6Fd,VeAaEa,llITPi&$fLk,H*I)Zj4GCc 24[b,ad9'hD$@i9mLhbKU%m1r4,iMERlTi9rG(iKcKYq4Ec3mAr![qMbd62fL%$I M,3[mVqjkZ)F15f[VTi'TJRpe0mK6Aa$LKS"hJRr4Xq`ESrPBR(MP3Pp'XlmMcQ# [VCr*iI6#0m+9pG8acR!D`DhSFm3RlXhI&R"+m#pk$KLKeAQS+hUKKhr4&k$&k*G &r%"AN!"hX$QT$MU62NqYb-1rZLqK9HMr&h%DMG29qeH*)cqdefJcJRr4R`!l0$c 8pMhij1&Ip!`d"5fI0Arh`Q@&rp@pPEN'$DFMEYk[,H"Ih4[T-Id,i4e[**r`[qK b0!r0HrRHl2XprKGYJR&DcC0hdbFHrNA24[[3kUl`*(L&p0RH$a,h81`$F%[dc[2 3ZE@m$lS06RMi&jeKGe-0CbGZ2ca@q&rGAm1400S&FEI)%ccmLfk&BfYe$qU%rLf kmLr"bEAp6MkMK`VrUrX!ZE9e-(m2fK1HAKKj#4LQj4hQlf&Q1qSLRhL1ld!,jAe SXCiq&aN&Fl9kX[NHNFm,hSpr'h(SYm6"ai6RAI%QiPi6hMId$rRRkAD4[@J6@Th Ir$hI2[0dZmLBZSlT8q+1bVfN6S[S#DhHDrlH$MpdGET'r[(kq!jd5DR6@,LG9Qq (ek+h5CfDj8RHRUakcXehT%j[KPYVDQAMk$HTdb'iR9C$0Rr[kZQ,NBYqM`"2(p9 AbKfP6K2JkYSj#22hERLfUe1RrIe`L,Z(A[(UC2LCd@)d1'rj4a`r)Um'1c5kQFh h"ldkGGe-!2Q*-jcHeHQ2k@hY,!Ed!Aj[kh4mrJjjfb-alS1p1Vd0E8@(29reci0 9VNl23S28kY[d2Ea3k[40Z,j@4b81RLae@Lm2"XISEhLMe1R6B)%11mAUUpACT8k [&+F0YK2h)R&@qZNAdBVdlm3q0K`dFXS-HjV(Z40apkR(I@QQHYr'fir)JcfFDhi E'V5'Aj!!lhki8AfSGr-Pe%kMT4$h-R6+ZX!2QRm*,926bm3pf01IQYk2VUc9YBL MRlak0rmQ'V4fYS8iH-A9)@kRZLNk$h(`L6H'Z!I%!h!2qN#pjAh[rJ)"4YHbF3C 2ACeZG6NKG"jJhf#'e+RTYp'U0"SbFDp5(jGk2b`rH(q-3kH81Xf#NqL`DDaq[EU fe1P+HPZr0mBaKq(9UHNVmM0i",#2VLh[Hm"h'pb`F8E2P6SeI36Xdmie!0HQ,ed rrD5D%r-[`#pp)rAq1*U)GTk)12LN9kHQVm)9p3GL($c%Ue26qq3I[a[MQ,f3!$T p5pd4[3iHKQiZGCU#4U$9Bi(hH$mel9HI0[K'h-1pIQVq@IX!hBCh`0qN6Tm8bm& Em!bq,rh8U2i02`9qk6qTdjqM9@Zd'Z,HUZiMIIm+Z)K@*`GqdF'ppcAHBTfBU5% 1r9IH[3*ZS1NG'iIZ+A'2q1k24(k*VL&a9cPRi-eKk0qbYlbjMBEIK`2V-)HKhiP 1*('0Tk(Yk6#(SGmPGjGmAd-ld'%13pmJYjDicm*&0&SaFEr1ZpAji4hhUQ-C$B' iGpJhZd2F,(NB1J"aCMBLmUS3plKkkLG#h$["!q(aM4H+LfBHMEKh`IrGqckYR[( *%2GZF9EHph*a&ai(c$+(+1qE3UpUjKTXR1'"lRdcl32$PBKl,rc%[HpCkVl-#J' rr*IhVD8(p+G$h2[8YH9pCm%4p5dacZ#1Hpm'iicH50a[dJrZIBqTVe0ri*Fj5RR I+p&H0E-*0Jlp5plh#E"!bq1)-h0)lRd2b*rXM0lr"`#3!edP!!!: zip30/man/0040755000076400000060000000000011033727770010546 5ustar ediskzip30/man/zip.10100644000076400000060000024677611025603714011445 0ustar edisk.\" ========================================================================= .\" Copyright (c) 1990-2008 Info-ZIP. All rights reserved. .\" .\" See the accompanying file LICENSE, version 2007-Mar-4 or later .\" (the contents of which are also included in zip.h) for terms of use. .\" If, for some reason, all these files are missing, the Info-ZIP license .\" also may be found at: ftp://ftp.info-zip.org/pub/infozip/license.html .\" ========================================================================== .\" .\" zip.1 by Mark Adler, Jean-loup Gailly and R. P. C. Rodgers .\" updated by E. Gordon for Zip 3.0 (8 May 2005, 24 December 2006, .\" 4 February 2007, 27 May 2007, 4 June 2007 by EG; 12 June 2007 by CS; .\" 30 August 2007, 27 April 2008, 25 May 2008, 27 May 2008 by EG, .\" 7 June 2008 by SMS and EG; 12 June 2008 by EG) .\" .TH ZIP 1L "16 June 2008 (v3.0)" Info-ZIP .SH NAME zip \- package and compress (archive) files .SH SYNOPSIS .B zip .RB [\- aABcdDeEfFghjklLmoqrRSTuvVwXyz!@$ ] [\-\-longoption ...] .RB [\- b " path]" .RB [\- n " suffixes]" .RB [\- t " date]" .RB [\- tt " date]" [\fIzipfile\fR [\fIfile\fR \.\|.\|.]] [\fB-xi\fR list] .PP .B zipcloak (see separate man page) .PP .B zipnote (see separate man page) .PP .B zipsplit (see separate man page) .PP Note: Command line processing in .I zip has been changed to support long options and handle all options and arguments more consistently. Some old command lines that depend on command line inconsistencies may no longer work. .SH DESCRIPTION .I zip is a compression and file packaging utility for Unix, VMS, MSDOS, OS/2, Windows 9x/NT/XP, Minix, Atari, Macintosh, Amiga, and Acorn RISC OS. It is analogous to a combination of the Unix commands .IR tar (1) and .IR compress (1) and is compatible with PKZIP (Phil Katz's ZIP for MSDOS systems). .LP A companion program .RI ( unzip (1L)) unpacks .I zip archives. The .I zip and .IR unzip (1L) programs can work with archives produced by PKZIP (supporting most PKZIP features up to PKZIP version 4.6), and PKZIP and PKUNZIP can work with archives produced by \fIzip\fP (with some exceptions, notably streamed archives, but recent changes in the zip file standard may facilitate better compatibility). .I zip version 3.0 is compatible with PKZIP 2.04 and also supports the Zip64 extensions of PKZIP 4.5 which allow archives as well as files to exceed the previous 2 GB limit (4 GB in some cases). \fIzip\fP also now supports \fBbzip2\fP compression if the \fBbzip2\fP library is included when \fIzip\fP is compiled. Note that PKUNZIP 1.10 cannot extract files produced by PKZIP 2.04 or \fIzip\ 3.0\fP. You must use PKUNZIP 2.04g or \fIunzip\ 5.0p1\fP (or later versions) to extract them. .PP See the \fBEXAMPLES\fP section at the bottom of this page for examples of some typical uses of \fIzip\fP. .PP \fBLarge\ Archives\ and\ Zip64.\fP .I zip automatically uses the Zip64 extensions when files larger than 4 GB are added to an archive, an archive containing Zip64 entries is updated (if the resulting archive still needs Zip64), the size of the archive will exceed 4 GB, or when the number of entries in the archive will exceed about 64K. Zip64 is also used for archives streamed from standard input as the size of such archives are not known in advance, but the option \fB\-fz\-\fP can be used to force \fIzip\fP to create PKZIP 2 compatible archives (as long as Zip64 extensions are not needed). You must use a PKZIP 4.5 compatible unzip, such as \fIunzip\ 6.0\fP or later, to extract files using the Zip64 extensions. .PP In addition, streamed archives, entries encrypted with standard encryption, or split archives created with the pause option may not be compatible with PKZIP as data descriptors are used and PKZIP at the time of this writing does not support data descriptors (but recent changes in the PKWare published zip standard now include some support for the data descriptor format \fIzip\fP uses). .PP \fBMac OS X.\fP Though previous Mac versions had their own \fIzip\fP port, \fIzip\fP supports Mac OS X as part of the Unix port and most Unix features apply. References to "MacOS" below generally refer to MacOS versions older than OS X. Support for some Mac OS features in the Unix Mac OS X port, such as resource forks, is expected in the next \fIzip\fP release. .PP For a brief help on \fIzip\fP and \fIunzip\fP, run each without specifying any parameters on the command line. .SH "USE" .PP The program is useful for packaging a set of files for distribution; for archiving files; and for saving disk space by temporarily compressing unused files or directories. .LP The .I zip program puts one or more compressed files into a single .I zip archive, along with information about the files (name, path, date, time of last modification, protection, and check information to verify file integrity). An entire directory structure can be packed into a .I zip archive with a single command. Compression ratios of 2:1 to 3:1 are common for text files. .I zip has one compression method (deflation) and can also store files without compression. (If \fBbzip2\fP support is added, \fIzip\fP can also compress using \fBbzip2\fP compression, but such entries require a reasonably modern unzip to decompress. When \fBbzip2\fP compression is selected, it replaces deflation as the default method.) .I zip automatically chooses the better of the two (deflation or store or, if \fBbzip2\fP is selected, \fBbzip2\fP or store) for each file to be compressed. .LP \fBCommand\ format.\fP The basic command format is .IP \fBzip\fR options archive inpath inpath ... .LP where \fBarchive\fR is a new or existing \fIzip\fR archive and \fBinpath\fR is a directory or file path optionally including wildcards. When given the name of an existing .I zip archive, .I zip will replace identically named entries in the .I zip archive (matching the relative names as stored in the archive) or add entries for new names. For example, if .I foo.zip exists and contains .I foo/file1 and .IR foo/file2 , and the directory .I foo contains the files .I foo/file1 and .IR foo/file3 , then: .IP \fCzip -r foo.zip foo\fP .LP or more concisely .IP \fCzip -r foo foo\fP .LP will replace .I foo/file1 in .I foo.zip and add .I foo/file3 to .IR foo.zip . After this, .I foo.zip contains .IR foo/file1 , .IR foo/file2 , and .IR foo/file3 , with .I foo/file2 unchanged from before. .LP So if before the zip command is executed \fIfoo.zip\fP has: .IP \fC foo/file1 foo/file2 .LP and directory foo has: .IP \fC file1 file3\fP .LP then \fIfoo.zip\fP will have: .IP \fC foo/file1 foo/file2 foo/file3\fP .LP where \fIfoo/file1\fP is replaced and \fIfoo/file3\fP is new. .LP \fB\-@\ file\ lists.\fP If a file list is specified as \fB\-@\fP [Not on MacOS], .I zip takes the list of input files from standard input instead of from the command line. For example, .IP \fCzip -@ foo\fP .LP will store the files listed one per line on stdin in \fIfoo.zip\fP. .LP Under Unix, this option can be used to powerful effect in conjunction with the \fIfind\fP\ (1) command. For example, to archive all the C source files in the current directory and its subdirectories: .IP \fCfind . -name "*.[ch]" -print | zip source -@\fP .LP (note that the pattern must be quoted to keep the shell from expanding it). .LP \fBStreaming\ input\ and\ output.\fP .I zip will also accept a single dash ("-") as the zip file name, in which case it will write the zip file to standard output, allowing the output to be piped to another program. For example: .IP \fCzip -r - . | dd of=/dev/nrst0 obs=16k\fP .LP would write the zip output directly to a tape with the specified block size for the purpose of backing up the current directory. .LP .I zip also accepts a single dash ("-") as the name of a file to be compressed, in which case it will read the file from standard input, allowing zip to take input from another program. For example: .IP \fCtar cf - . | zip backup -\fP .LP would compress the output of the tar command for the purpose of backing up the current directory. This generally produces better compression than the previous example using the -r option because .I zip can take advantage of redundancy between files. The backup can be restored using the command .IP \fCunzip -p backup | tar xf -\fP .LP When no zip file name is given and stdout is not a terminal, .I zip acts as a filter, compressing standard input to standard output. For example, .IP \fCtar cf - . | zip | dd of=/dev/nrst0 obs=16k\fP .LP is equivalent to .IP \fCtar cf - . | zip - - | dd of=/dev/nrst0 obs=16k\fP .LP .I zip archives created in this manner can be extracted with the program .I funzip which is provided in the .I unzip package, or by .I gunzip which is provided in the .I gzip package (but some .I gunzip may not support this if .I zip used the Zip64 extensions). For example: .IP \fPdd if=/dev/nrst0 ibs=16k | funzip | tar xvf -\fC .LP The stream can also be saved to a file and .I unzip used. .LP If Zip64 support for large files and archives is enabled and \fIzip\fR is used as a filter, \fIzip\fR creates a Zip64 archive that requires a PKZIP 4.5 or later compatible unzip to read it. This is to avoid amgibuities in the zip file structure as defined in the current zip standard (PKWARE AppNote) where the decision to use Zip64 needs to be made before data is written for the entry, but for a stream the size of the data is not known at that point. If the data is known to be smaller than 4 GB, the option \fB\-fz\-\fP can be used to prevent use of Zip64, but \fIzip\fP will exit with an error if Zip64 was in fact needed. \fIzip\ 3\fR and \fIunzip\ 6\fR and later can read archives with Zip64 entries. Also, \fIzip\fP removes the Zip64 extensions if not needed when archive entries are copied (see the \fB\-U\fP (\fB\-\-copy\fP) option). .LP When directing the output to another file, note that all options should be before the redirection including \fB-x\fP. For example: .IP \fPzip archive "*.h" "*.c" -x donotinclude.h orthis.h > tofile\fC .LP \fBZip\ files.\fP When changing an existing .I zip archive, .I zip will write a temporary file with the new contents, and only replace the old one when the process of creating the new version has been completed without error. .LP If the name of the .I zip archive does not contain an extension, the extension \fB.zip\fP is added. If the name already contains an extension other than \fB.zip\fP, the existing extension is kept unchanged. However, split archives (archives split over multiple files) require the \fB.zip\fP extension on the last split. .PP \fBScanning\ and\ reading\ files.\fP When \fIzip\fP starts, it scans for files to process (if needed). If this scan takes longer than about 5 seconds, \fIzip\fP will display a "Scanning files" message and start displaying progress dots every 2 seconds or every so many entries processed, whichever takes longer. If there is more than 2 seconds between dots it could indicate that finding each file is taking time and could mean a slow network connection for example. (Actually the initial file scan is a two-step process where the directory scan is followed by a sort and these two steps are separated with a space in the dots. If updating an existing archive, a space also appears between the existing file scan and the new file scan.) The scanning files dots are not controlled by the \fB\-ds\fP dot size option, but the dots are turned off by the \fB\-q\fP quiet option. The \fB\-sf\fP show files option can be used to scan for files and get the list of files scanned without actually processing them. .LP If \fIzip\fR is not able to read a file, it issues a warning but continues. See the \fB\-MM\fP option below for more on how \fIzip\fP handles patterns that are not matched and files that are not readable. If some files were skipped, a warning is issued at the end of the zip operation noting how many files were read and how many skipped. .PP \fBCommand\ modes.\fP \fIzip\fP now supports two distinct types of command modes, \fBexternal\fP and \fBinternal\fP. The \fBexternal\fP modes (add, update, and freshen) read files from the file system (as well as from an existing archive) while the \fBinternal\fP modes (delete and copy) operate exclusively on entries in an existing archive. .LP .TP .BI add\ \ \ \ \ \ Update existing entries and add new files. If the archive does not exist create it. This is the default mode. .TP .BI update\ \fP(\fB\-u\fP) Update existing entries if newer on the file system and add new files. If the archive does not exist issue warning then create a new archive. .TP .BI freshen\ \fP(\fB\-f\fP) Update existing entries of an archive if newer on the file system. Does not add new files to the archive. .TP .BI delete\ \fP(\fB\-d\fP) Select entries in an existing archive and delete them. .TP .BI copy\ \fP(\fB\-U\fP) Select entries in an existing archive and copy them to a new archive. This new mode is similar to \fBupdate\fP but command line patterns select entries in the existing archive rather than files from the file system and it uses the \fB\-\-out\fP option to write the resulting archive to a new file rather than update the existing archive, leaving the original archive unchanged. .LP The new File Sync option (\fB\-FS\fP) is also considered a new mode, though it is similar to \fBupdate\fP. This mode synchronizes the archive with the files on the OS, only replacing files in the archive if the file time or size of the OS file is different, adding new files, and deleting entries from the archive where there is no matching file. As this mode can delete entries from the archive, consider making a backup copy of the archive. Also see \fB\-DF\fP for creating difference archives. See each option description below for details and the \fBEXAMPLES\fP section below for examples. .PP \fBSplit\ archives.\fP \fIzip\fP version 3.0 and later can create split archives. A \fBsplit archive\fP is a standard zip archive split over multiple files. (Note that split archives are not just archives split in to pieces, as the offsets of entries are now based on the start of each split. Concatenating the pieces together will invalidate these offsets, but \fIunzip\fP can usually deal with it. \fIzip\fP will usually refuse to process such a spliced archive unless the \fB\-FF\fP fix option is used to fix the offsets.) .LP One use of split archives is storing a large archive on multiple removable media. For a split archive with 20 split files the files are typically named (replace ARCHIVE with the name of your archive) ARCHIVE.z01, ARCHIVE.z02, ..., ARCHIVE.z19, ARCHIVE.zip. Note that the last file is the \fB.zip\fP file. In contrast, \fBspanned archives\fP are the original multi-disk archive generally requiring floppy disks and using volume labels to store disk numbers. \fIzip\fP supports split archives but not spanned archives, though a procedure exists for converting split archives of the right size to spanned archives. The reverse is also true, where each file of a spanned archive can be copied in order to files with the above names to create a split archive. .LP Use \fB\-s\fP to set the split size and create a split archive. The size is given as a number followed optionally by one of k (kB), m (MB), g (GB), or t (TB) (the default is m). The \fB\-sp\fP option can be used to pause \fIzip\fP between splits to allow changing removable media, for example, but read the descriptions and warnings for both \fB\-s\fP and \fB\-sp\fP below. .LP Though \fIzip\fP does not update split archives, \fIzip\fP provides the new option \fB\-O\fP (\fB\-\-output\-file\fP or \fB\-\-out\fP) to allow split archives to be updated and saved in a new archive. For example, .IP \fCzip inarchive.zip foo.c bar.c \-\-out outarchive.zip\fP .LP reads archive \fBinarchive.zip\fP, even if split, adds the files \fBfoo.c\fP and \fBbar.c\fP, and writes the resulting archive to \fBoutarchive.zip\fP. If \fBinarchive.zip\fP is split then \fBoutarchive.zip\fP defaults to the same split size. Be aware that if \fBoutarchive.zip\fP and any split files that are created with it already exist, these are always overwritten as needed without warning. This may be changed in the future. .PP \fBUnicode.\fP Though the zip standard requires storing paths in an archive using a specific character set, in practice zips have stored paths in archives in whatever the local character set is. This creates problems when an archive is created or updated on a system using one character set and then extracted on another system using a different character set. When compiled with Unicode support enabled on platforms that support wide characters, \fIzip\fP now stores, in addition to the standard local path for backward compatibility, the UTF-8 translation of the path. This provides a common universal character set for storing paths that allows these paths to be fully extracted on other systems that support Unicode and to match as close as possible on systems that don't. On Win32 systems where paths are internally stored as Unicode but represented in the local character set, it's possible that some paths will be skipped during a local character set directory scan. \fIzip\fP with Unicode support now can read and store these paths. Note that Win 9x systems and FAT file systems don't fully support Unicode. Be aware that console windows on Win32 and Unix, for example, sometimes don't accurately show all characters due to how each operating system switches in character sets for display. However, directory navigation tools should show the correct paths if the needed fonts are loaded. .PP \fBCommand line format.\fP This version of .I zip has updated command line processing and support for long options. .PP Short options take the form .IP \fC-s[-][s[-]...][value][=value][\ value]\fP .LP where s is a one or two character short option. A short option that takes a value is last in an argument and anything after it is taken as the value. If the option can be negated and "-" immediately follows the option, the option is negated. Short options can also be given as separate arguments .IP \fC-s[-][value][=value][\ value]\ -s[-][value][=value][\ value]\ ...\fP .LP Short options in general take values either as part of the same argument or as the following argument. An optional = is also supported. So .IP \fC-ttmmddyyyy\fP .LP and .IP \fC-tt=mmddyyyy\fP .LP and .IP \fC-tt mmddyyyy\fP .LP all work. The \fB\-x\fP and \fB\-i\fP options accept lists of values and use a slightly different format described below. See the \fB\-x\fP and \fB\-i\fP options. .PP Long options take the form .IP \fC--longoption[-][=value][ value]\fP .LP where the option starts with --, has a multicharacter name, can include a trailing dash to negate the option (if the option supports it), and can have a value (option argument) specified by preceeding it with = (no spaces). Values can also follow the argument. So .IP \fC--before-date=mmddyyyy\fP .LP and .IP \fC--before-date mmddyyyy\fP .LP both work. Long option names can be shortened to the shortest unique abbreviation. See the option descriptions below for which support long options. To avoid confusion, avoid abbreviating a negatable option with an embedded dash ("-") at the dash if you plan to negate it (the parser would consider a trailing dash, such as for the option \fB\-\-some\-option\fP using \fB\-\-some\-\fP as the option, as part of the name rather than a negating dash). This may be changed to force the last dash in \fB\-\-some\-\fP to be negating in the future. .SH "OPTIONS" .TP .PD 0 .BI \-a .TP .PD .B \-\-ascii [Systems using EBCDIC] Translate file to ASCII format. .TP .PD 0 .B \-A .TP .PD .B \-\-adjust-sfx Adjust self-extracting executable archive. A self-extracting executable archive is created by prepending the SFX stub to an existing archive. The .B \-A option tells .I zip to adjust the entry offsets stored in the archive to take into account this "preamble" data. .LP Note: self-extracting archives for the Amiga are a special case. At present, only the Amiga port of \fIzip\fP is capable of adjusting or updating these without corrupting them. -J can be used to remove the SFX stub if other updates need to be made. .TP .PD 0 .B \-AC .TP .PD .B \-\-archive-clear [WIN32] Once archive is created (and tested if \fB\-T\fP is used, which is recommended), clear the archive bits of files processed. WARNING: Once the bits are cleared they are cleared. You may want to use the \fB\-sf\fP show files option to store the list of files processed in case the archive operation must be repeated. Also consider using the \fB\-MM\fP must match option. Be sure to check out \fB\-DF\fP as a possibly better way to do incremental backups. .TP .PD 0 .B \-AS .TP .PD .B \-\-archive-set [WIN32] Only include files that have the archive bit set. Directories are not stored when \fB\-AS\fP is used, though by default the paths of entries, including directories, are stored as usual and can be used by most unzips to recreate directories. The archive bit is set by the operating system when a file is modified and, if used with \fB\-AC\fP, \fB\-AS\fP can provide an incremental backup capability. However, other applications can modify the archive bit and it may not be a reliable indicator of which files have changed since the last archive operation. Alternative ways to create incremental backups are using \fB\-t\fP to use file dates, though this won't catch old files copied to directories being archived, and \fB\-DF\fP to create a differential archive. .TP .PD 0 .B \-B .TP .PD .B \-\-binary [VM/CMS and MVS] force file to be read binary (default is text). .TP .B \-B\fRn [TANDEM] set Edit/Enscribe formatting options with n defined as .RS bit 0: Don't add delimiter (Edit/Enscribe) .RE .RS bit 1: Use LF rather than CR/LF as delimiter (Edit/Enscribe) .RE .RS bit 2: Space fill record to maximum record length (Enscribe) .RE .RS bit 3: Trim trailing space (Enscribe) .RE .RS bit 8: Force 30K (Expand) large read for unstructured files .RE .TP .PD 0 .BI \-b\ \fRpath .TP .PD .B \-\-temp-path\ \fRpath Use the specified .I path for the temporary .I zip archive. For example: .RS .IP \fCzip -b /tmp stuff *\fP .RE .IP will put the temporary .I zip archive in the directory .IR /tmp , copying over .I stuff.zip to the current directory when done. This option is useful when updating an existing archive and the file system containing this old archive does not have enough space to hold both old and new archives at the same time. It may also be useful when streaming in some cases to avoid the need for data descriptors. Note that using this option may require \fIzip\fP take additional time to copy the archive file when done to the destination file system. .TP .PD 0 .B \-c .TP .PD .B \-\-entry-comments Add one-line comments for each file. File operations (adding, updating) are done first, and the user is then prompted for a one-line comment for each file. Enter the comment followed by return, or just return for no comment. .TP .PD 0 .B \-C .TP .PD .B \-\-preserve-case [VMS] Preserve case all on VMS. Negating this option (\fB\-C-\fP) downcases. .TP .PD 0 .B \-C2 .TP .PD .BI \-\-preserve-case-2 [VMS] Preserve case ODS2 on VMS. Negating this option (\fB\-C2-\fP) downcases. .TP .PD 0 .B \-C5 .TP .PD .B \-\-preserve-case-5 [VMS] Preserve case ODS5 on VMS. Negating this option (\fB\-C5-\fP) downcases. .TP .PD 0 .B \-d .TP .PD .B \-\-delete Remove (delete) entries from a .I zip archive. For example: .RS .IP \fCzip -d foo foo/tom/junk foo/harry/\\* \\*.o\fP .RE .IP will remove the entry .IR foo/tom/junk , all of the files that start with .IR foo/harry/ , and all of the files that end with .B \&.o (in any path). Note that shell pathname expansion has been inhibited with backslashes, so that .I zip can see the asterisks, enabling .I zip to match on the contents of the .I zip archive instead of the contents of the current directory. (The backslashes are not used on MSDOS-based platforms.) Can also use quotes to escape the asterisks as in .RS .IP \fCzip -d foo foo/tom/junk "foo/harry/*" "*.o"\fP .RE .IP Not escaping the asterisks on a system where the shell expands wildcards could result in the asterisks being converted to a list of files in the current directory and that list used to delete entries from the archive. .IP Under MSDOS, .B \-d is case sensitive when it matches names in the .I zip archive. This requires that file names be entered in upper case if they were zipped by PKZIP on an MSDOS system. (We considered making this case insensitive on systems where paths were case insensitive, but it is possible the archive came from a system where case does matter and the archive could include both \fBBar\fP and \fBbar\fP as separate files in the archive.) But see the new option \fB\-ic\fP to ignore case in the archive. .TP .PD 0 .B \-db .TP .PD .B \-\-display-bytes Display running byte counts showing the bytes zipped and the bytes to go. .TP .PD 0 .B \-dc .TP .PD .B \-\-display-counts Display running count of entries zipped and entries to go. .TP .PD 0 .B \-dd .TP .PD .B \-\-display-dots Display dots while each entry is zipped (except on ports that have their own progress indicator). See \fB-ds\fR below for setting dot size. The default is a dot every 10 MB of input file processed. The \fB-v\fR option also displays dots (previously at a much higher rate than this but now \fB\-v\fP also defaults to 10 MB) and this rate is also controlled by \fB-ds\fR. .TP .PD 0 .B \-df .TP .PD .B \-\-datafork [MacOS] Include only data-fork of files zipped into the archive. Good for exporting files to foreign operating-systems. Resource-forks will be ignored at all. .TP .PD 0 .B \-dg .TP .PD .B \-\-display-globaldots Display progress dots for the archive instead of for each file. The command .RS .IP zip -qdgds 10m .RE .IP will turn off most output except dots every 10 MB. .TP .PD 0 .B \-ds\ \fRsize .TP .PD .B \-\-dot-size\ \fRsize Set amount of input file processed for each dot displayed. See \fB-dd\fR to enable displaying dots. Setting this option implies \fB-dd\fR. Size is in the format nm where n is a number and m is a multiplier. Currently m can be k (KB), m (MB), g (GB), or t (TB), so if n is 100 and m is k, size would be 100k which is 100 KB. The default is 10 MB. .IP The \fB-v\fR option also displays dots and now defaults to 10 MB also. This rate is also controlled by this option. A size of 0 turns dots off. .IP This option does not control the dots from the "Scanning files" message as \fIzip\fP scans for input files. The dot size for that is fixed at 2 seconds or a fixed number of entries, whichever is longer. .TP .PD 0 .B \-du .TP .PD .B \-\-display-usize Display the uncompressed size of each entry. .TP .PD 0 .B \-dv .TP .PD .B \-\-display-volume Display the volume (disk) number each entry is being read from, if reading an existing archive, and being written to. .TP .PD 0 .B \-D .TP .PD .B \-\-no-dir-entries Do not create entries in the .I zip archive for directories. Directory entries are created by default so that their attributes can be saved in the zip archive. The environment variable ZIPOPT can be used to change the default options. For example under Unix with sh: .RS .IP ZIPOPT="-D"; export ZIPOPT .RE .IP (The variable ZIPOPT can be used for any option, including \fB\-i\fP and \fB\-x\fP using a new option format detailed below, and can include several options.) The option .B \-D is a shorthand for .B \-x "*/" but the latter previously could not be set as default in the ZIPOPT environment variable as the contents of ZIPOPT gets inserted near the beginning of the command line and the file list had to end at the end of the line. .IP This version of .I zip does allow .B \-x and .B \-i options in ZIPOPT if the form .IP \fC .BR \-x \ file\ file\ ... \ @\fP .IP is used, where the @ (an argument that is just @) terminates the list. .TP .PD 0 .B \-DF .TP .PD .B \-\-difference-archive Create an archive that contains all new and changed files since the original archive was created. For this to work, the input file list and current directory must be the same as during the original \fIzip\fP operation. .IP For example, if the existing archive was created using .RS .IP \fCzip -r foofull . .RE .IP from the \fIbar\fP directory, then the command .RS .IP \fCzip -r foofull . -DF --out foonew .RE .IP also from the \fIbar\fP directory creates the archive \fIfoonew\fP with just the files not in \fIfoofull\fP and the files where the size or file time of the files do not match those in \fIfoofull\fP. Note that the timezone environment variable TZ should be set according to the local timezone in order for this option to work correctly. A change in timezone since the original archive was created could result in no times matching and all files being included. A possible approach to backing up a directory might be to create a normal archive of the contents of the directory as a full backup, then use this option to create incremental backups. .TP .PD 0 .B \-e .TP .PD .B \-\-encrypt Encrypt the contents of the .I zip archive using a password which is entered on the terminal in response to a prompt (this will not be echoed; if standard error is not a tty, .I zip will exit with an error). The password prompt is repeated to save the user from typing errors. .TP .PD 0 .B \-E .TP .PD .B \-\-longnames [OS/2] Use the .LONGNAME Extended Attribute (if found) as filename. .TP .PD 0 .B \-f .TP .PD .B \-\-freshen Replace (freshen) an existing entry in the .I zip archive only if it has been modified more recently than the version already in the .I zip archive; unlike the update option .RB ( \-u ) this will not add files that are not already in the .I zip archive. For example: .RS .IP \fCzip -f foo\fP .RE .IP This command should be run from the same directory from which the original .I zip command was run, since paths stored in .I zip archives are always relative. .IP Note that the timezone environment variable TZ should be set according to the local timezone in order for the \fB\-f\fP, \fB\-u\fP and \fB\-o\fP options to work correctly. .IP The reasons behind this are somewhat subtle but have to do with the differences between the Unix-format file times (always in GMT) and most of the other operating systems (always local time) and the necessity to compare the two. A typical TZ value is ``MET-1MEST'' (Middle European time with automatic adjustment for ``summertime'' or Daylight Savings Time). .IP The format is TTThhDDD, where TTT is the time zone such as MET, hh is the difference between GMT and local time such as -1 above, and DDD is the time zone when daylight savings time is in effect. Leave off the DDD if there is no daylight savings time. For the US Eastern time zone EST5EDT. .TP .PD 0 .B \-F .TP .B \-\-fix\ \ \ \ \ \ .TP .B \-FF .TP .PD .B \-\-fixfix\ \ Fix the .I zip archive. The \fB\-F\fP option can be used if some portions of the archive are missing, but requires a reasonably intact central directory. The input archive is scanned as usual, but \fIzip\fP will ignore some problems. The resulting archive should be valid, but any inconsistent entries will be left out. .IP When doubled as in \fB\-FF\fP, the archive is scanned from the beginning and \fIzip\fP scans for special signatures to identify the limits between the archive members. The single .B \-F is more reliable if the archive is not too much damaged, so try this option first. .IP If the archive is too damaged or the end has been truncated, you must use \fB\-FF\fP. This is a change from \fIzip\ 2.32\fP, where the \fB\-F\fP option is able to read a truncated archive. The \fB\-F\fP option now more reliably fixes archives with minor damage and the \fB\-FF\fP option is needed to fix archives where \fB\-F\fP might have been sufficient before. .IP Neither option will recover archives that have been incorrectly transferred in ascii mode instead of binary. After the repair, the .B \-t option of .I unzip may show that some files have a bad CRC. Such files cannot be recovered; you can remove them from the archive using the .B \-d option of \fIzip\fP. .IP Note that \fB\-FF\fP may have trouble fixing archives that include an embedded zip archive that was stored (without compression) in the archive and, depending on the damage, it may find the entries in the embedded archive rather than the archive itself. Try \fB\-F\fP first as it does not have this problem. .IP The format of the fix commands have changed. For example, to fix the damaged archive \fIfoo.zip\fP, .RS .IP \fCzip -F foo --out foofix .RE .IP tries to read the entries normally, copying good entries to the new archive \fIfoofix.zip\fP. If this doesn't work, as when the archive is truncated, or if some entries you know are in the archive are missed, then try .RS .IP \fCzip -FF foo --out foofixfix .RE .IP and compare the resulting archive to the archive created by \fB\-F\fP. The \fB\-FF\fP option may create an inconsistent archive. Depending on what is damaged, you can then use the \fB\-F\fP option to fix that archive. .IP A split archive with missing split files can be fixed using \fB\-F\fP if you have the last split of the archive (the \fB\.zip\fP file). If this file is missing, you must use \fB\-FF\fP to fix the archive, which will prompt you for the splits you have. .IP Currently the fix options can't recover entries that have a bad checksum or are otherwise damaged. .TP .PD 0 .B \-FI .TP .PD .B \-\-fifo [Unix] Normally \fIzip\fP skips reading any FIFOs (named pipes) encountered, as \fIzip\fP can hang if the FIFO is not being fed. This option tells \fIzip\fP to read the contents of any FIFO it finds. .TP .PD 0 .B \-FS .TP .PD .B \-\-filesync Synchronize the contents of an archive with the files on the OS. Normally when an archive is updated, new files are added and changed files are updated but files that no longer exist on the OS are not deleted from the archive. This option enables a new mode that checks entries in the archive against the file system. If the file time and file size of the entry matches that of the OS file, the entry is copied from the old archive instead of being read from the file system and compressed. If the OS file has changed, the entry is read and compressed as usual. If the entry in the archive does not match a file on the OS, the entry is deleted. Enabling this option should create archives that are the same as new archives, but since existing entries are copied instead of compressed, updating an existing archive with \fB\-FS\fP can be much faster than creating a new archive. Also consider using \fB\-u\fP for updating an archive. .IP For this option to work, the archive should be updated from the same directory it was created in so the relative paths match. If few files are being copied from the old archive, it may be faster to create a new archive instead. .IP Note that the timezone environment variable TZ should be set according to the local timezone in order for this option to work correctly. A change in timezone since the original archive was created could result in no times matching and recompression of all files. .IP This option deletes files from the archive. If you need to preserve the original archive, make a copy of the archive first or use the \fB\-\-out\fP option to output the updated archive to a new file. Even though it may be slower, creating a new archive with a new archive name is safer, avoids mismatches between archive and OS paths, and is preferred. .TP .PD 0 .B \-g .TP .PD .B \-\-grow \ \ \ \ \ \ Grow (append to) the specified .I zip archive, instead of creating a new one. If this operation fails, .I zip attempts to restore the archive to its original state. If the restoration fails, the archive might become corrupted. This option is ignored when there's no existing archive or when at least one archive member must be updated or deleted. .TP .PD 0 .B \-h .TP .PD 0 .B \-? .TP .PD .B \-\-help \ \ \ \ \ \ Display the .I zip help information (this also appears if .I zip is run with no arguments). .TP .PD 0 .B \-h2 .TP .PD .B \-\-more-help Display extended help including more on command line format, pattern matching, and more obscure options. .TP .PD 0 .B \-i\ \fRfiles .TP .PD .B \-\-include\ \fRfiles Include only the specified files, as in: .RS .IP \fCzip -r foo . -i \\*.c\fP .RE .IP which will include only the files that end in .IR \& .c in the current directory and its subdirectories. (Note for PKZIP users: the equivalent command is .RS .IP \fCpkzip -rP foo *.c\fP .RE .IP PKZIP does not allow recursion in directories other than the current one.) The backslash avoids the shell filename substitution, so that the name matching is performed by .I zip at all directory levels. [This is for Unix and other systems where \\ escapes the next character. For other systems where the shell does not process * do not use \\ and the above is .RS .IP \fCzip -r foo . -i *.c\fP .RE .IP Examples are for Unix unless otherwise specified.] So to include dir, a directory directly under the current directory, use .RS .IP \fCzip -r foo . -i dir/\\* .RE .IP or .RS .IP \fCzip -r foo . -i "dir/*" .RE .IP to match paths such as dir/a and dir/b/file.c [on ports without wildcard expansion in the shell such as MSDOS and Windows .RS .IP \fCzip -r foo . -i dir/* .RE .IP is used.] Note that currently the trailing / is needed for directories (as in .RS .IP \fCzip -r foo . -i dir/ .RE .IP to include directory dir). .IP The long option form of the first example is .RS .IP \fCzip -r foo . --include \\*.c .RE .IP and does the same thing as the short option form. .IP Though the command syntax used to require \fB-i\fR at the end of the command line, this version actually allows \fB\-i\fP (or \fB\-\-include\fP) anywhere. The list of files terminates at the next argument starting with \fB-\fR, the end of the command line, or the list terminator \fB@\fR (an argument that is just @). So the above can be given as .RS .IP zip -i \\*.c @ -r foo .\fP .RE .IP for example. There must be a space between the option and the first file of a list. For just one file you can use the single value form .RS .IP \fCzip -i\\*.c -r foo .\fP .RE .IP (no space between option and value) or .RS .IP \fCzip --include=\\*.c -r foo .\fP .RE .IP as additional examples. The single value forms are not recommended because they can be confusing and, in particular, the \fB\-ifile\fP format can cause problems if the first letter of \fBfile\fP combines with \fBi\fP to form a two-letter option starting with \fBi\fP. Use \fB\-sc\fP to see how your command line will be parsed. .IP Also possible: .RS .IP \fCzip -r foo . -i@include.lst\fP .RE .IP which will only include the files in the current directory and its subdirectories that match the patterns in the file include.lst. .IP Files to \fB\-i\fR and \fB\-x\fR are patterns matching internal archive paths. See \fB-R\fR for more on patterns. .TP .PD 0 .B \-I .TP .PD .B \-\-no-image [Acorn RISC OS] Don't scan through Image files. When used, \fIzip\fP will not consider Image files (eg. DOS partitions or Spark archives when SparkFS is loaded) as directories but will store them as single files. For example, if you have SparkFS loaded, zipping a Spark archive will result in a zipfile containing a directory (and its content) while using the 'I' option will result in a zipfile containing a Spark archive. Obviously this second case will also be obtained (without the 'I' option) if SparkFS isn't loaded. .TP .PD 0 .B \-ic .TP .PD .B \-\-ignore-case [VMS, WIN32] Ignore case when matching archive entries. This option is only available on systems where the case of files is ignored. On systems with case-insensitive file systems, case is normally ignored when matching files on the file system but is not ignored for -f (freshen), -d (delete), -U (copy), and similar modes when matching against archive entries (currently -f ignores case on VMS) because archive entries can be from systems where case does matter and names that are the same except for case can exist in an archive. The \fB\-ic\fR option makes all matching case insensitive. This can result in multiple archive entries matching a command line pattern. .TP .PD 0 .B \-j .TP .PD .B \-\-junk-paths Store just the name of a saved file (junk the path), and do not store directory names. By default, .I zip will store the full path (relative to the current directory). .TP .PD 0 .B \-jj .TP .PD .B \-\-absolute-path [MacOS] record Fullpath (+ Volname). The complete path including volume will be stored. By default the relative path will be stored. .TP .PD 0 .B \-J .TP .PD .B \-\-junk-sfx Strip any prepended data (e.g. a SFX stub) from the archive. .TP .PD 0 .B \-k .TP .PD .B \-\-DOS-names Attempt to convert the names and paths to conform to MSDOS, store only the MSDOS attribute (just the user write attribute from Unix), and mark the entry as made under MSDOS (even though it was not); for compatibility with PKUNZIP under MSDOS which cannot handle certain names such as those with two dots. .TP .PD 0 .B \-l .TP .PD .B \-\-to-crlf Translate the Unix end-of-line character LF into the MSDOS convention CR LF. This option should not be used on binary files. This option can be used on Unix if the zip file is intended for PKUNZIP under MSDOS. If the input files already contain CR LF, this option adds an extra CR. This is to ensure that \fBunzip -a\fP on Unix will get back an exact copy of the original file, to undo the effect of \fBzip -l\fP. See \fB-ll\fR for how binary files are handled. .TP .PD 0 .B \-la .TP .PD .B \-\-log-append Append to existing logfile. Default is to overwrite. .TP .PD 0 .B \-lf\ \fPlogfilepath .TP .PD .B \-\-logfile-path\ \fPlogfilepath Open a logfile at the given path. By default any existing file at that location is overwritten, but the \fB\-la\fP option will result in an existing file being opened and the new log information appended to any existing information. Only warnings and errors are written to the log unless the \fB\-li\fP option is also given, then all information messages are also written to the log. .TP .PD 0 .B \-li .TP .PD .B \-\-log-info Include information messages, such as file names being zipped, in the log. The default is to only include the command line, any warnings and errors, and the final status. .TP .PD 0 .B \-ll .TP .PD .B \-\-from-crlf Translate the MSDOS end-of-line CR LF into Unix LF. This option should not be used on binary files. This option can be used on MSDOS if the zip file is intended for unzip under Unix. If the file is converted and the file is later determined to be binary a warning is issued and the file is probably corrupted. In this release if \fB-ll\fR detects binary in the first buffer read from a file, \fIzip\fR now issues a warning and skips line end conversion on the file. This check seems to catch all binary files tested, but the original check remains and if a converted file is later determined to be binary that warning is still issued. A new algorithm is now being used for binary detection that should allow line end conversion of text files in \fBUTF-8\fR and similar encodings. .TP .PD 0 .B \-L .TP .PD .B \-\-license Display the .I zip license. .TP .PD 0 .B \-m .TP .PD .B \-\-move \ \ \ Move the specified files into the .I zip archive; actually, this deletes the target directories/files after making the specified .I zip archive. If a directory becomes empty after removal of the files, the directory is also removed. No deletions are done until .I zip has created the archive without error. This is useful for conserving disk space, but is potentially dangerous so it is recommended to use it in combination with .B \-T to test the archive before removing all input files. .TP .PD 0 .B \-MM .TP .PD .B \-\-must-match All input patterns must match at least one file and all input files found must be readable. Normally when an input pattern does not match a file the "name not matched" warning is issued and when an input file has been found but later is missing or not readable a missing or not readable warning is issued. In either case .I zip continues creating the archive, with missing or unreadable new files being skipped and files already in the archive remaining unchanged. After the archive is created, if any files were not readable .I zip returns the OPEN error code (18 on most systems) instead of the normal success return (0 on most systems). With \fB\-MM\fP set, .I zip exits as soon as an input pattern is not matched (whenever the "name not matched" warning would be issued) or when an input file is not readable. In either case \fIzip\fR exits with an OPEN error and no archive is created. .IP This option is useful when a known list of files is to be zipped so any missing or unreadable files will result in an error. It is less useful when used with wildcards, but \fIzip\fR will still exit with an error if any input pattern doesn't match at least one file and if any matched files are unreadable. If you want to create the archive anyway and only need to know if files were skipped, don't use .B \-MM and just check the return code. Also \fB\-lf\fP could be useful. .TP .PD 0 .BI \-n\ \fRsuffixes .TP .PD .B \-\-suffixes\ \fRsuffixes Do not attempt to compress files named with the given \fBsuffixes\fR. Such files are simply stored (0% compression) in the output zip file, so that .I zip doesn't waste its time trying to compress them. The suffixes are separated by either colons or semicolons. For example: .RS .IP \fCzip -rn .Z:.zip:.tiff:.gif:.snd foo foo\fP .RE .IP will copy everything from .I foo into .IR foo.zip , but will store any files that end in .IR .Z , .IR .zip , .IR .tiff , .IR .gif , or .I .snd without trying to compress them (image and sound files often have their own specialized compression methods). By default, .I zip does not compress files with extensions in the list .I .Z:.zip:.zoo:.arc:.lzh:.arj. Such files are stored directly in the output archive. The environment variable ZIPOPT can be used to change the default options. For example under Unix with csh: .RS .IP setenv ZIPOPT "-n .gif:.zip" .RE .IP To attempt compression on all files, use: .RS .IP zip -n : foo .RE .IP The maximum compression option .B \-9 also attempts compression on all files regardless of extension. .IP On Acorn RISC OS systems the suffixes are actually filetypes (3 hex digit format). By default, \fIzip\fP does not compress files with filetypes in the list DDC:D96:68E (i.e. Archives, CFS files and PackDir files). .TP .PD 0 .B \-nw .TP .PD .B \-\-no-wild Do not perform internal wildcard processing (shell processing of wildcards is still done by the shell unless the arguments are escaped). Useful if a list of paths is being read and no wildcard substitution is desired. .TP .PD 0 .B \-N .TP .PD .B \-\-notes [Amiga, MacOS] Save Amiga or MacOS filenotes as zipfile comments. They can be restored by using the -N option of \fIunzip\fP. If -c is used also, you are prompted for comments only for those files that do not have filenotes. .TP .PD 0 .B \-o .TP .PD .B \-\-latest-time Set the "last modified" time of the .I zip archive to the latest (oldest) "last modified" time found among the entries in the .I zip archive. This can be used without any other operations, if desired. For example: .IP \fCzip -o foo\fP .IP will change the last modified time of \fBfoo.zip\fP to the latest time of the entries in .BR foo.zip . .TP .PD 0 .B \-O \fPoutput-file .TP .PD .B \-\-output-file \fPoutput-file Process the archive changes as usual, but instead of updating the existing archive, output the new archive to output-file. Useful for updating an archive without changing the existing archive and the input archive must be a different file than the output archive. This option can be used to create updated split archives. It can also be used with \fB\-U\fP to copy entries from an existing archive to a new archive. See the \fBEXAMPLES\fP section below. Another use is converting \fIzip\fP files from one split size to another. For instance, to convert an archive with 700 MB CD splits to one with 2 GB DVD splits, can use: .RS .IP zip -s 2g cd-split.zip --out dvd-split.zip .RE .IP which uses copy mode. See \fB\-U\fP below. Also: .RS .IP zip -s 0 split.zip --out unsplit.zip .RE .IP will convert a split archive to a single-file archive. Copy mode will convert stream entries (using data descriptors and which should be compatible with most unzips) to normal entries (which should be compatible with all unzips), except if standard encryption was used. For archives with encrypted entries, \fIzipcloak\fP will decrypt the entries and convert them to normal entries. .TP .PD 0 .B \-p .TP .PD .B \-\-paths Include relative file paths as part of the names of files stored in the archive. This is the default. The \fB\-j\fP option junks the paths and just stores the names of the files. .TP .PD 0 .B \-P\ \fRpassword .TP .PD .B \-\-password\ \fRpassword Use \fIpassword\fP to encrypt zipfile entries (if any). \fBTHIS IS INSECURE!\fP Many multi-user operating systems provide ways for any user to see the current command line of any other user; even on stand-alone systems there is always the threat of over-the-shoulder peeking. Storing the plaintext password as part of a command line in an automated script is even worse. Whenever possible, use the non-echoing, interactive prompt to enter passwords. (And where security is truly important, use strong encryption such as Pretty Good Privacy instead of the relatively weak standard encryption provided by zipfile utilities.) .TP .PD 0 .B \-q .TP .PD .B \-\-quiet Quiet mode; eliminate informational messages and comment prompts. (Useful, for example, in shell scripts and background tasks). .TP .PD 0 .BI \-Q\fRn .TP .PD .B \-\-Q\-flag\ \fRn [QDOS] store information about the file in the file header with n defined as .RS bit 0: Don't add headers for any file .RE .RS bit 1: Add headers for all files .RE .RS bit 2: Don't wait for interactive key press on exit .RE .TP .PD 0 .B \-r .TP .PD .B \-\-recurse\-paths Travel the directory structure recursively; for example: .RS .IP zip -r foo.zip foo .RE .IP or more concisely .RS .IP zip -r foo foo .RE .IP In this case, all the files and directories in .B foo are saved in a .I zip archive named \fBfoo.zip\fP, including files with names starting with \fB"."\fP, since the recursion does not use the shell's file-name substitution mechanism. If you wish to include only a specific subset of the files in directory \fBfoo\fP and its subdirectories, use the \fB\-i\fP option to specify the pattern of files to be included. You should not use \fB\-r\fP with the name \fB".*"\fP, since that matches \fB".."\fP which will attempt to zip up the parent directory (probably not what was intended). .IP Multiple source directories are allowed as in .RS .IP \fCzip -r foo foo1 foo2\fP .RE .IP which first zips up \fBfoo1\fP and then \fBfoo2\fP, going down each directory. .IP Note that while wildcards to \fB-r\fR are typically resolved while recursing down directories in the file system, any \fB-R\fN, \fB-x\fR, and \fB-i\fR wildcards are applied to internal archive pathnames once the directories are scanned. To have wildcards apply to files in subdirectories when recursing on Unix and similar systems where the shell does wildcard substitution, either escape all wildcards or put all arguments with wildcards in quotes. This lets \fIzip\fR see the wildcards and match files in subdirectories using them as it recurses. .TP .PD 0 .B \-R .TP .PD .B \-\-recurse\-patterns Travel the directory structure recursively starting at the current directory; for example: .RS .IP \fCzip -R foo "*.c"\fP .RE .IP In this case, all the files matching \fB*.c\fP in the tree starting at the current directory are stored into a .I zip archive named \fBfoo.zip\fP. Note that \fB*.c\fP will match \fBfile.c\fP, \fBa/file.c\fP and \fBa/b/.c\fP. More than one pattern can be listed as separate arguments. Note for PKZIP users: the equivalent command is .RS .IP \fCpkzip -rP foo *.c\fP .RE .IP Patterns are relative file paths as they appear in the archive, or will after zipping, and can have optional wildcards in them. For example, given the current directory is \fBfoo\fP and under it are directories \fBfoo1\fP and \fBfoo2\fP and in \fBfoo1\fP is the file \fBbar.c\fP, .RS .IP \fCzip -R foo/*\fP .RE .IP will zip up \fBfoo\fP, \fBfoo/foo1\fP, \fBfoo/foo1/bar.c\fP, and \fBfoo/foo2\fP. .RS .IP \fCzip -R */bar.c\fP .RE .IP will zip up \fBfoo/foo1/bar.c\fP. See the note for \fB-r\fR on escaping wildcards. .TP .PD 0 .B \-RE .TP .PD .B \-\-regex [WIN32] Before \fIzip\fP \fI3.0\fP, regular expression list matching was enabled by default on Windows platforms. Because of confusion resulting from the need to escape "[" and "]" in names, it is now off by default for Windows so "[" and "]" are just normal characters in names. This option enables [] matching again. .TP .PD 0 .B \-s\ \fPsplitsize .TP .PD .B \-\-split\-size\ \fPsplitsize Enable creating a split archive and set the split size. A split archive is an archive that could be split over many files. As the archive is created, if the size of the archive reaches the specified split size, that split is closed and the next split opened. In general all splits but the last will be the split size and the last will be whatever is left. If the entire archive is smaller than the split size a single-file archive is created. Split archives are stored in numbered files. For example, if the output archive is named \fBarchive\fP and three splits are required, the resulting archive will be in the three files \fBarchive.z01\fP, \fBarchive.z02\fP, and \fBarchive.zip\fP. Do not change the numbering of these files or the archive will not be readable as these are used to determine the order the splits are read. Split size is a number optionally followed by a multiplier. Currently the number must be an integer. The multiplier can currently be one of \fBk\fP (kilobytes), \fBm\fP (megabytes), \fBg\fP (gigabytes), or \fBt\fP (terabytes). As 64k is the minimum split size, numbers without multipliers default to megabytes. For example, to create a split archive called \fBfoo\fP with the contents of the \fBbar\fP directory with splits of 670 MB that might be useful for burning on CDs, the command: .RS .IP zip -s 670m -r foo bar .RE .IP could be used. Currently the old splits of a split archive are not excluded from a new archive, but they can be specifically excluded. If possible, keep the input and output archives out of the path being zipped when creating split archives. Using \fB\-s\fP without \fB\-sp\fP as above creates all the splits where \fBfoo\fP is being written, in this case the current directory. This split mode updates the splits as the archive is being created, requiring all splits to remain writable, but creates split archives that are readable by any unzip that supports split archives. See \fB\-sp\fP below for enabling split pause mode which allows splits to be written directly to removable media. The option \fB\-sv\fP can be used to enable verbose splitting and provide details of how the splitting is being done. The \fB\-sb\fP option can be used to ring the bell when \fIzip\fP pauses for the next split destination. Split archives cannot be updated, but see the \fB\-O\fP (\fB\-\-out\fP) option for how a split archive can be updated as it is copied to a new archive. A split archive can also be converted into a single-file archive using a split size of 0 or negating the \fB\-s\fP option: .RS .IP zip -s 0 split.zip --out single.zip .RE .IP Also see \fB\-U\fP (\fB\-\-copy\fP) for more on using copy mode. .TP .PD 0 .B \-sb .TP .PD .B \-\-split\-bell If splitting and using split pause mode, ring the bell when \fIzip\fP pauses for each split destination. .TP .PD 0 .B \-sc .TP .PD .B \-\-show\-command Show the command line starting \fIzip\fP as processed and exit. The new command parser permutes the arguments, putting all options and any values associated with them before any non-option arguments. This allows an option to appear anywhere in the command line as long as any values that go with the option go with it. This option displays the command line as \fIzip\fP sees it, including any arguments from the environment such as from the \fBZIPOPT\fP variable. Where allowed, options later in the command line can override options earlier in the command line. .TP .PD 0 .B \-sf .TP .PD .B \-\-show\-files Show the files that would be operated on, then exit. For instance, if creating a new archive, this will list the files that would be added. If the option is negated, \fB\-sf\-\fP, output only to an open log file. Screen display is not recommended for large lists. .TP .PD 0 .B \-so .TP .PD .B \-\-show\-options Show all available options supported by \fIzip\fP as compiled on the current system. As this command reads the option table, it should include all options. Each line includes the short option (if defined), the long option (if defined), the format of any value that goes with the option, if the option can be negated, and a small description. The value format can be no value, required value, optional value, single character value, number value, or a list of values. The output of this option is not intended to show how to use any option but only show what options are available. .TP .PD 0 .B \-sp .TP .PD .B \-\-split\-pause If splitting is enabled with \fB\-s\fP, enable split pause mode. This creates split archives as \fB\-s\fP does, but stream writing is used so each split can be closed as soon as it is written and \fIzip\fP will pause between each split to allow changing split destination or media. Though this split mode allows writing splits directly to removable media, it uses stream archive format that may not be readable by some unzips. Before relying on splits created with \fB\-sp\fP, test a split archive with the unzip you will be using. To convert a stream split archive (created with \fB\-sp\fP) to a standard archive see the \fB\-\-out\fP option. .TP .PD 0 .B \-su .TP .PD .B \-\-show\-unicode As \fB\-sf\fP, but also show Unicode version of the path if exists. .TP .PD 0 .B \-sU .TP .PD .B \-\-show\-just\-unicode As \fB\-sf\fP, but only show Unicode version of the path if exists, otherwise show the standard version of the path. .TP .PD 0 .B \-sv .TP .PD .B \-\-split\-verbose Enable various verbose messages while splitting, showing how the splitting is being done. .TP .PD 0 .B \-S .TP .PD .B \-\-system-hidden [MSDOS, OS/2, WIN32 and ATARI] Include system and hidden files. .RS [MacOS] Includes finder invisible files, which are ignored otherwise. .RE .TP .PD 0 .BI \-t\ \fRmmddyyyy .TP .PD .B \-\-from\-date\ \fRmmddyyyy Do not operate on files modified prior to the specified date, where .B mm is the month (00-12), .B dd is the day of the month (01-31), and .B yyyy is the year. The .I ISO\ 8601 date format .B yyyy\-mm\-dd is also accepted. For example: .RS .IP \fCzip -rt 12071991 infamy foo\fP \fCzip -rt 1991-12-07 infamy foo\fP .RE .IP will add all the files in .B foo and its subdirectories that were last modified on or after 7 December 1991, to the .I zip archive .BR infamy.zip . .TP .PD 0 .BI \-tt\ \fRmmddyyyy .TP .PD .B \-\-before\-date\ \fRmmddyyyy Do not operate on files modified after or at the specified date, where .B mm is the month (00-12), .B dd is the day of the month (01-31), and .B yyyy is the year. The .I ISO\ 8601 date format .B yyyy\-mm\-dd is also accepted. For example: .RS .IP \fCzip -rtt 11301995 infamy foo\fP \fCzip -rtt 1995-11-30 infamy foo\fP .RE .IP will add all the files in .B foo and its subdirectories that were last modified before 30 November 1995, to the .I zip archive .BR infamy.zip . .TP .PD 0 .B \-T .TP .PD .B \-\-test\ \ \ \ Test the integrity of the new zip file. If the check fails, the old zip file is unchanged and (with the .B -m option) no input files are removed. .TP .PD 0 .B \-TT\ \fPcmd .TP .PD .B \-\-unzip-command\ \fPcmd Use command cmd instead of 'unzip -tqq' to test an archive when the \fB\-T\fP option is used. On Unix, to use a copy of unzip in the current directory instead of the standard system unzip, could use: .IP \fC zip archive file1 file2 -T -TT "./unzip -tqq"\fP .IP In cmd, {} is replaced by the name of the temporary archive, otherwise the name of the archive is appended to the end of the command. The return code is checked for success (0 on Unix). .TP .PD 0 .B \-u .TP .PD .B \-\-update Replace (update) an existing entry in the .I zip archive only if it has been modified more recently than the version already in the .I zip archive. For example: .RS .IP \fCzip -u stuff *\fP .RE .IP will add any new files in the current directory, and update any files which have been modified since the .I zip archive .I stuff.zip was last created/modified (note that .I zip will not try to pack .I stuff.zip into itself when you do this). .IP Note that the .B \-u option with no input file arguments acts like the .B \-f (freshen) option. .TP .PD 0 .B \-U .TP .PD .B \-\-copy\-entries Copy entries from one archive to another. Requires the \fB\-\-out\fP option to specify a different output file than the input archive. Copy mode is the reverse of \fB\-d\fP delete. When delete is being used with \fB\-\-out\fP, the selected entries are deleted from the archive and all other entries are copied to the new archive, while copy mode selects the files to include in the new archive. Unlike \fB\-u\fP update, input patterns on the command line are matched against archive entries only and not the file system files. For instance, .RS .IP \fCzip inarchive "*.c" --copy --out outarchive\fP .RE .IP copies entries with names ending in \fB\.c\fP from \fBinarchive\fP to \fBoutarchive\fP. The wildcard must be escaped on some systems to prevent the shell from substituting names of files from the file system which may have no relevance to the entries in the archive. If no input files appear on the command line and \fB\-\-out\fP is used, copy mode is assumed: .RS .IP \fCzip inarchive --out outarchive\fP .RE .IP This is useful for changing split size for instance. Encrypting and decrypting entries is not yet supported using copy mode. Use \fIzipcloak\fP for that. .TP .PD 0 .B \-UN\ \fRv .TP .PD .B \-\-unicode\ \fRv Determine what \fIzip\fP should do with Unicode file names. \fIzip\ 3.0\fP, in addition to the standard file path, now includes the UTF\-8 translation of the path if the entry path is not entirely 7-bit ASCII. When an entry is missing the Unicode path, \fIzip\fP reverts back to the standard file path. The problem with using the standard path is this path is in the local character set of the zip that created the entry, which may contain characters that are not valid in the character set being used by the unzip. When \fIzip\fP is reading an archive, if an entry also has a Unicode path, \fIzip\fP now defaults to using the Unicode path to recreate the standard path using the current local character set. This option can be used to determine what \fIzip\fP should do with this path if there is a mismatch between the stored standard path and the stored UTF-8 path (which can happen if the standard path was updated). In all cases, if there is a mismatch it is assumed that the standard path is more current and \fIzip\fP uses that. Values for \fBv\fP are .RS .IP q \- quit if paths do not match .IP w \- warn, continue with standard path .IP i \- ignore, continue with standard path .IP n \- no Unicode, do not use Unicode paths .RE .IP The default is to warn and continue. Characters that are not valid in the current character set are escaped as \fB#Uxxxx\fP and \fB#Lxxxxxx\fP, where x is an ASCII character for a hex digit. The first is used if a 16-bit character number is sufficient to represent the Unicode character and the second if the character needs more than 16 bits to represent it's Unicode character code. Setting \fB\-UN\fP to .RS .IP e \- escape .RE .IP as in .RS .IP \fCzip archive -sU -UN=e\fP .RE .IP forces \fIzip\fP to escape all characters that are not printable 7-bit ASCII. Normally \fIzip\fP stores UTF\-8 directly in the standard path field on systems where UTF\-8 is the current character set and stores the UTF\-8 in the new extra fields otherwise. The option .RS .IP u \- UTF\-8 .RE .IP as in .RS .IP \fCzip archive dir -r -UN=UTF8\fP .RE .IP forces \fIzip\fP to store UTF\-8 as native in the archive. Note that storing UTF\-8 directly is the default on Unix systems that support it. This option could be useful on Windows systems where the escaped path is too large to be a valid path and the UTF\-8 version of the path is smaller, but native UTF\-8 is not backward compatible on Windows systems. .TP .PD 0 .B \-v .TP .PD .B \-\-verbose Verbose mode or print diagnostic version info. .IP Normally, when applied to real operations, this option enables the display of a progress indicator during compression (see \fB-dd\fR for more on dots) and requests verbose diagnostic info about zipfile structure oddities. .IP However, when .B \-v is the only command line argument a diagnostic screen is printed instead. This should now work even if stdout is redirected to a file, allowing easy saving of the information for sending with bug reports to Info-ZIP. The version screen provides the help screen header with program name, version, and release date, some pointers to the Info-ZIP home and distribution sites, and shows information about the target environment (compiler type and version, OS version, compilation date and the enabled optional features used to create the .I zip executable). .TP .PD 0 .B \-V .TP .PD .B \-\-VMS\-portable [VMS] Save VMS file attributes. (Files are truncated at EOF.) When a -V archive is unpacked on a non-VMS system, some file types (notably Stream_LF text files and pure binary files like fixed-512) should be extracted intact. Indexed files and file types with embedded record sizes (notably variable-length record types) will probably be seen as corrupt elsewhere. .TP .PD 0 .B \-VV .TP .PD .B \-\-VMS\-specific [VMS] Save VMS file attributes, and all allocated blocks in a file, including any data beyond EOF. Useful for moving ill-formed files among VMS systems. When a -VV archive is unpacked on a non-VMS system, almost all files will appear corrupt. .TP .PD 0 .B \-w .TP .PD .B \-\-VMS\-versions [VMS] Append the version number of the files to the name, including multiple versions of files. Default is to use only the most recent version of a specified file. .TP .PD 0 .B \-ww .TP .PD .B \-\-VMS\-dot\-versions [VMS] Append the version number of the files to the name, including multiple versions of files, using the \.nnn format. Default is to use only the most recent version of a specified file. .TP .PD 0 .BI \-ws .TP .PD .B \-\-wild\-stop\-dirs Wildcards match only at a directory level. Normally \fIzip\fP handles paths as strings and given the paths .RS .IP /foo/bar/dir/file1.c .IP /foo/bar/file2.c .RE .IP an input pattern such as .RS .IP /foo/bar/* .RE .IP normally would match both paths, the * matching \fBdir/file1.c\fP and \fBfile2.c\fP. Note that in the first case a directory boundary (/) was crossed in the match. With \fB\-ws\fP no directory bounds will be included in the match, making wildcards local to a specific directory level. So, with \fB\-ws\fP enabled, only the second path would be matched. When using \fB\-ws\fP, use ** to match across directory boundaries as * does normally. .TP .PD 0 .BI \-x\ \fRfiles .TP .PD .B \-\-exclude\ \fRfiles Explicitly exclude the specified files, as in: .RS .IP \fCzip -r foo foo -x \\*.o\fP .RE .IP which will include the contents of .B foo in .B foo.zip while excluding all the files that end in \fB.o\fP. The backslash avoids the shell filename substitution, so that the name matching is performed by .I zip at all directory levels. .IP Also possible: .RS .IP \fCzip -r foo foo -x@exclude.lst\fP .RE .IP which will include the contents of .B foo in .B foo.zip while excluding all the files that match the patterns in the file \fBexclude.lst\fP. .IP The long option forms of the above are .RS .IP \fCzip -r foo foo --exclude \\*.o\fP .RE .IP and .RS .IP \fCzip -r foo foo --exclude @exclude.lst\fP .RE .IP Multiple patterns can be specified, as in: .RS .IP \fCzip -r foo foo -x \\*.o \\*.c\fP .RE .IP If there is no space between \fB\-x\fP and the pattern, just one value is assumed (no list): .RS .IP \fCzip -r foo foo -x\\*.o\fP .RE .IP .IP See \fB-i\fR for more on include and exclude. .TP .PD 0 .B \-X .TP .PD .B \-\-no\-extra Do not save extra file attributes (Extended Attributes on OS/2, uid/gid and file times on Unix). The zip format uses extra fields to include additional information for each entry. Some extra fields are specific to particular systems while others are applicable to all systems. Normally when \fIzip\fP reads entries from an existing archive, it reads the extra fields it knows, strips the rest, and adds the extra fields applicable to that system. With \fB\-X\fP, \fIzip\fP strips all old fields and only includes the Unicode and Zip64 extra fields (currently these two extra fields cannot be disabled). Negating this option, \fB\-X\-\fP, includes all the default extra fields, but also copies over any unrecognized extra fields. .TP .PD 0 .B \-y .TP .PD .B \-\-symlinks For UNIX and VMS (V8.3 and later), store symbolic links as such in the .I zip archive, instead of compressing and storing the file referred to by the link. This can avoid multiple copies of files being included in the archive as \fIzip\fP recurses the directory trees and accesses files directly and by links. .TP .PD 0 .B \-z .TP .PD .B \-\-archive\-comment Prompt for a multi-line comment for the entire .I zip archive. The comment is ended by a line containing just a period, or an end of file condition (^D on Unix, ^Z on MSDOS, OS/2, and VMS). The comment can be taken from a file: .RS .IP \fCzip -z foo < foowhat\fP .RE .TP .PD 0 .B \-Z\ \fRcm .TP .PD .B \-\-compression\-method\ \fRcm Set the default compression method. Currently the main methods supported by \fIzip\fP are \fBstore\fP and \fBdeflate\fP. Compression method can be set to: \fBstore\fP \- Setting the compression method to \fBstore\fP forces \fIzip\fP to store entries with no compression. This is generally faster than compressing entries, but results in no space savings. This is the same as using \fB\-0\fP (compression level zero). \fBdeflate\fP \- This is the default method for \fIzip\fP. If \fIzip\fP determines that storing is better than deflation, the entry will be stored instead. \fBbzip2\fP \- If \fBbzip2\fP support is compiled in, this compression method also becomes available. Only some modern unzips currently support the \fBbzip2\fP compression method, so test the unzip you will be using before relying on archives using this method (compression method 12). For example, to add \fBbar.c\fP to archive \fBfoo\fP using \fBbzip2\fP compression: .RS .IP zip -Z bzip2 foo bar.c .RE .IP The compression method can be abbreviated: .RS .IP zip -Zb foo bar.c .RE .IP .TP .PD 0 .BI \-# .TP .PD .B (\-0, \-1, \-2, \-3, \-4, \-5, \-6, \-7, \-8, \-9) Regulate the speed of compression using the specified digit .BR # , where .B \-0 indicates no compression (store all files), .B \-1 indicates the fastest compression speed (less compression) and .B \-9 indicates the slowest compression speed (optimal compression, ignores the suffix list). The default compression level is .BR \-6. Though still being worked, the intention is this setting will control compression speed for all compression methods. Currently only deflation is controlled. .TP .PD 0 .B \-! .TP .PD .B \-\-use\-privileges [WIN32] Use priviliges (if granted) to obtain all aspects of WinNT security. .TP .PD 0 .B \-@ .TP .PD .B \-\-names\-stdin Take the list of input files from standard input. Only one filename per line. .TP .PD 0 .B \-$ .TP .PD .B \-\-volume\-label [MSDOS, OS/2, WIN32] Include the volume label for the drive holding the first file to be compressed. If you want to include only the volume label or to force a specific drive, use the drive name as first file name, as in: .RS .IP \fCzip -$ foo a: c:bar\fP .RE .IP .SH "EXAMPLES" The simplest example: .IP \fCzip stuff *\fP .LP creates the archive .I stuff.zip (assuming it does not exist) and puts all the files in the current directory in it, in compressed form (the \fB\&.zip\fP suffix is added automatically, unless the archive name contains a dot already; this allows the explicit specification of other suffixes). .LP Because of the way the shell on Unix does filename substitution, files starting with "." are not included; to include these as well: .IP \fCzip stuff .* *\fP .LP Even this will not include any subdirectories from the current directory. .LP To zip up an entire directory, the command: .IP \fCzip -r foo foo\fP .LP creates the archive .IR foo.zip , containing all the files and directories in the directory .I foo that is contained within the current directory. .LP You may want to make a .I zip archive that contains the files in .IR foo , without recording the directory name, .IR foo . You can use the .B \-j option to leave off the paths, as in: .IP \fCzip -j foo foo/*\fP .LP If you are short on disk space, you might not have enough room to hold both the original directory and the corresponding compressed .I zip archive. In this case, you can create the archive in steps using the .B \-m option. If .I foo contains the subdirectories .IR tom , .IR dick , and .IR harry , you can: .IP \fCzip -rm foo foo/tom\fP .br \fCzip -rm foo foo/dick\fP .br \fCzip -rm foo foo/harry\fP .LP where the first command creates .IR foo.zip , and the next two add to it. At the completion of each .I zip command, the last created archive is deleted, making room for the next .I zip command to function. .LP Use \fB\-s\fP to set the split size and create a split archive. The size is given as a number followed optionally by one of k (kB), m (MB), g (GB), or t (TB). The command .IP \fCzip -s 2g -r split.zip foo\fP .LP creates a split archive of the directory foo with splits no bigger than 2\ GB each. If foo contained 5\ GB of contents and the contents were stored in the split archive without compression (to make this example simple), this would create three splits, split.z01 at 2\ GB, split.z02 at 2\ GB, and split.zip at a little over 1\ GB. .LP The \fB\-sp\fP option can be used to pause \fIzip\fP between splits to allow changing removable media, for example, but read the descriptions and warnings for both \fB\-s\fP and \fB\-sp\fP below. .LP Though \fIzip\fP does not update split archives, \fIzip\fP provides the new option \fB\-O\fP (\fB\-\-output\-file\fP) to allow split archives to be updated and saved in a new archive. For example, .IP \fCzip inarchive.zip foo.c bar.c \-\-out outarchive.zip\fP .LP reads archive \fBinarchive.zip\fP, even if split, adds the files \fBfoo.c\fP and \fBbar.c\fP, and writes the resulting archive to \fBoutarchive.zip\fP. If \fBinarchive.zip\fP is split then \fBoutarchive.zip\fP defaults to the same split size. Be aware that \fBoutarchive.zip\fP and any split files that are created with it are always overwritten without warning. This may be changed in the future. .SH "PATTERN MATCHING" This section applies only to Unix. Watch this space for details on MSDOS and VMS operation. However, the special wildcard characters \fB*\fR and \fB[]\fR below apply to at least MSDOS also. .LP The Unix shells (\fIsh\fP, \fIcsh\fP, \fIbash\fP, and others) normally do filename substitution (also called "globbing") on command arguments. Generally the special characters are: .TP .B ? match any single character .TP .B * match any number of characters (including none) .TP .B [] match any character in the range indicated within the brackets (example: [a\-f], [0\-9]). This form of wildcard matching allows a user to specify a list of characters between square brackets and if any of the characters match the expression matches. For example: .RS .IP \fCzip archive "*.[hc]"\fP .RE .IP would archive all files in the current directory that end in \fB.h\fP or \fB.c\fP. Ranges of characters are supported: .RS .IP \fCzip archive "[a\-f]*"\fP .RE .IP would add to the archive all files starting with "a" through "f". Negation is also supported, where any character in that position not in the list matches. Negation is supported by adding \fB!\fP or \fB^\fP to the beginning of the list: .RS .IP \fCzip archive "*.[!o]"\fP .RE .IP matches files that don't end in ".o". On WIN32, [] matching needs to be turned on with the -RE option to avoid the confusion that names with [ or ] have caused. .LP When these characters are encountered (without being escaped with a backslash or quotes), the shell will look for files relative to the current path that match the pattern, and replace the argument with a list of the names that matched. .LP The .I zip program can do the same matching on names that are in the .I zip archive being modified or, in the case of the .B \-x (exclude) or .B \-i (include) options, on the list of files to be operated on, by using backslashes or quotes to tell the shell not to do the name expansion. In general, when .I zip encounters a name in the list of files to do, it first looks for the name in the file system. If it finds it, it then adds it to the list of files to do. If it does not find it, it looks for the name in the .I zip archive being modified (if it exists), using the pattern matching characters described above, if present. For each match, it will add that name to the list of files to be processed, unless this name matches one given with the .B \-x option, or does not match any name given with the .B \-i option. .LP The pattern matching includes the path, and so patterns like \\*.o match names that end in ".o", no matter what the path prefix is. Note that the backslash must precede every special character (i.e. ?*[]), or the entire argument must be enclosed in double quotes (""). .LP In general, use backslashes or double quotes for paths that have wildcards to make .I zip do the pattern matching for file paths, and always for paths and strings that have spaces or wildcards for \fB\-\i\fP, \fB\-x\fP, \fB\-R\fP, \fB\-d\fP, and \fB\-U\fP and anywhere \fIzip\fP needs to process the wildcards. .SH "ENVIRONMENT" .LP The following environment variables are read and used by .I zip as described. .TP .B ZIPOPT\ \ contains default options that will be used when running \fIzip\fR. The contents of this environment variable will get added to the command line just after the \fBzip\fR command. .TP .B ZIP\ \ \ \ \ [Not on RISC OS and VMS] see ZIPOPT .TP .B Zip$Options [RISC OS] see ZIPOPT .TP .B Zip$Exts [RISC OS] contains extensions separated by a : that will cause native filenames with one of the specified extensions to be added to the zip file with basename and extension swapped. .TP .B ZIP_OPTS [VMS] see ZIPOPT .SH "SEE ALSO" compress(1), shar(1L), tar(1), unzip(1L), gzip(1L) .SH DIAGNOSTICS The exit status (or error level) approximates the exit codes defined by PKWARE and takes on the following values, except under VMS: .RS .IP 0 normal; no errors or warnings detected. .IP 2 unexpected end of zip file. .IP 3 a generic error in the zipfile format was detected. Processing may have completed successfully anyway; some broken zipfiles created by other archivers have simple work-arounds. .IP 4 \fIzip\fP was unable to allocate memory for one or more buffers during program initialization. .IP 5 a severe error in the zipfile format was detected. Processing probably failed immediately. .IP 6 entry too large to be processed (such as input files larger than 2 GB when not using Zip64 or trying to read an existing archive that is too large) or entry too large to be split with \fIzipsplit\fP .IP 7 invalid comment format .IP 8 \fIzip\fP -T failed or out of memory .IP 9 the user aborted \fIzip\fP prematurely with control-C (or similar) .IP 10 \fIzip\fP encountered an error while using a temp file .IP 11 read or seek error .IP 12 \fIzip\fP has nothing to do .IP 13 missing or empty zip file .IP 14 error writing to a file .IP 15 \fIzip\fP was unable to create a file to write to .IP 16 bad command line parameters .IP 18 \fIzip\fP could not open a specified file to read .IP 19 \fIzip\fP was compiled with options not supported on this system .RE .PP VMS interprets standard Unix (or PC) return values as other, scarier-looking things, so \fIzip\fP instead maps them into VMS-style status codes. In general, \fIzip\fP sets VMS Facility = 1955 (0x07A3), Code = 2* Unix_status, and an appropriate Severity (as specified in ziperr.h). More details are included in the VMS-specific documentation. See [.vms]NOTES.TXT and [.vms]vms_msg_gen.c. .PD .SH BUGS .I zip 3.0 is not compatible with PKUNZIP 1.10. Use .I zip 1.1 to produce .I zip files which can be extracted by PKUNZIP 1.10. .PP .I zip files produced by .I zip 3.0 must not be .I updated by .I zip 1.1 or PKZIP 1.10, if they contain encrypted members or if they have been produced in a pipe or on a non-seekable device. The old versions of .I zip or PKZIP would create an archive with an incorrect format. The old versions can list the contents of the zip file but cannot extract it anyway (because of the new compression algorithm). If you do not use encryption and use regular disk files, you do not have to care about this problem. .LP Under VMS, not all of the odd file formats are treated properly. Only stream-LF format .I zip files are expected to work with .IR zip . Others can be converted using Rahul Dhesi's BILF program. This version of .I zip handles some of the conversion internally. When using Kermit to transfer zip files from VMS to MSDOS, type "set file type block" on VMS. When transfering from MSDOS to VMS, type "set file type fixed" on VMS. In both cases, type "set file type binary" on MSDOS. .LP Under some older VMS versions, \fIzip\fP may hang for file specifications that use DECnet syntax .I foo::*.*. .LP On OS/2, zip cannot match some names, such as those including an exclamation mark or a hash sign. This is a bug in OS/2 itself: the 32-bit DosFindFirst/Next don't find such names. Other programs such as GNU tar are also affected by this bug. .LP Under OS/2, the amount of Extended Attributes displayed by DIR is (for compatibility) the amount returned by the 16-bit version of DosQueryPathInfo(). Otherwise OS/2 1.3 and 2.0 would report different EA sizes when DIRing a file. However, the structure layout returned by the 32-bit DosQueryPathInfo() is a bit different, it uses extra padding bytes and link pointers (it's a linked list) to have all fields on 4-byte boundaries for portability to future RISC OS/2 versions. Therefore the value reported by .I zip (which uses this 32-bit-mode size) differs from that reported by DIR. .I zip stores the 32-bit format for portability, even the 16-bit MS-C-compiled version running on OS/2 1.3, so even this one shows the 32-bit-mode size. .SH AUTHORS Copyright (C) 1997-2008 Info-ZIP. .LP Currently distributed under the Info-ZIP license. .LP Copyright (C) 1990-1997 Mark Adler, Richard B. Wales, Jean-loup Gailly, Onno van der Linden, Kai Uwe Rommel, Igor Mandrichenko, John Bush and Paul Kienitz. .LP Original copyright: .LP Permission is granted to any individual or institution to use, copy, or redistribute this software so long as all of the original files are included, that it is not sold for profit, and that this copyright notice is retained. .LP LIKE ANYTHING ELSE THAT'S FREE, ZIP AND ITS ASSOCIATED UTILITIES ARE PROVIDED AS IS AND COME WITH NO WARRANTY OF ANY KIND, EITHER EXPRESSED OR IMPLIED. IN NO EVENT WILL THE COPYRIGHT HOLDERS BE LIABLE FOR ANY DAMAGES RESULTING FROM THE USE OF THIS SOFTWARE. .LP Please send bug reports and comments using the web page at: .IR www.info-zip.org . For bug reports, please include the version of .IR zip (see \fIzip\ \-h\fR), the make options used to compile it (see \fIzip\ \-v\fR), the machine and operating system in use, and as much additional information as possible. .SH ACKNOWLEDGEMENTS Thanks to R. P. Byrne for his .I Shrink.Pas program, which inspired this project, and from which the shrink algorithm was stolen; to Phil Katz for placing in the public domain the .I zip file format, compression format, and .ZIP filename extension, and for accepting minor changes to the file format; to Steve Burg for clarifications on the deflate format; to Haruhiko Okumura and Leonid Broukhis for providing some useful ideas for the compression algorithm; to Keith Petersen, Rich Wales, Hunter Goatley and Mark Adler for providing a mailing list and .I ftp site for the Info-ZIP group to use; and most importantly, to the Info-ZIP group itself (listed in the file .IR infozip.who ) without whose tireless testing and bug-fixing efforts a portable .I zip would not have been possible. Finally we should thank (blame) the first Info-ZIP moderator, David Kirschbaum, for getting us into this mess in the first place. The manual page was rewritten for Unix by R. P. C. Rodgers and updated by E. Gordon for \fIzip\fR 3.0. .\" end of file zip30/man/zipcloak.10100644000076400000060000000373611010533546012441 0ustar edisk.TH zipcloak 1 "v3.0 of 8 May 2008" .SH NAME zipcloak \- encrypt entries in a zipfile .SH SYNOPSIS .I zipcloak .RB [ \-d ] .RB [ \-b\ path ] .RB [ \-h ] .RB [ \-v ] .RB [ \-L ] zipfile .SH ARGUMENTS .in +13 .ti -13 zipfile Zipfile to encrypt entries in .SH OPTIONS .TP .PD 0 .B \-b\ \fPpath .TP .PD .B \-\-temp\-path \fPpath Use the directory given by path for the temporary zip file. .TP .PD 0 .B \-d .TP .PD .B \-\-decrypt Decrypt encrypted entries (copy if given wrong password). .TP .PD 0 .B \-h .TP .PD .B \-\-help\ Show a short help. .TP .PD 0 .B \-L .TP .PD .B \-\-license Show software license. .TP .PD 0 .B \-O\ \fPpath .TP .PD .B \-\-output\-file\ \fPzipfile Write output to new archive zipfile, leaving original archive as is. .TP .PD 0 .B \-q .TP .PD .B \-\-quiet Quiet operation. Suppresses some informational messages. .TP .PD 0 .B \-v .TP .PD .B \-\-version Show version information. .SH DESCRIPTION .I zipcloak encrypts all unencrypted entries in the zipfile. This is the default action. .TP The \-d option is used to decrypt encrypted entries in the zipfile. .TP \fIzipcloak \fBuses original zip encryption which is considered weak. .TP Note: The encryption code of this program is not copyrighted and is put in the public domain. It was originally written in Europe and can be freely distributed from any country including the U.S.A. (Previously if this program was imported into the U.S.A, it could not be re-exported from the U.S.A to another country.) See the file README.CR included in the source distribution for more on this. Otherwise, the Info-ZIP license applies. .SH EXAMPLES To be added. .SH BUGS Large files (> 2 GB) and large archives not yet supported. Split archives not yet supported. A work around is to convert the split archive to a single-file archive using \fIzip\fP and then use \fIzipcloak\fP on the single-file archive. If needed, the resulting archive can then be split again using \fIzip\fP. .SH SEE ALSO zip(1), unzip(1) .SH AUTHOR Info-ZIP zip30/man/zipnote.10100644000076400000060000000325111010533464012304 0ustar edisk.TH zipnote 1 "v3.0 of 8 May 2008" .SH NAME zipnote \- write the comments in zipfile to stdout, edit comments and rename files in zipfile .SH SYNOPSIS .I zipnote .RB [ \-w ] .RB [ \-b\ path ] .RB [ \-h ] .RB [ \-v ] .RB [ \-L ] zipfile .SH ARGUMENTS .in +13 .ti -13 zipfile Zipfile to read comments from or edit. .SH OPTIONS .TP .BI \-w Write comments to a zipfile from stdin (see below). .TP .BI \-b\ \fRpath Use path for the temporary zip file. .TP .BI \-h Show a short help. .TP .BI \-v Show version information. .TP .BI \-L Show software license. .SH DESCRIPTION .I zipnote writes the comments in a zipfile to stdout. This is the default mode. A second mode allows updating the comments in a zipfile as well as allows changing the names of the files in the zipfile. These modes are described below. .SH EXAMPLES To write all comments in a zipfile to stdout use for example .LP .nf zipnote foo.zip > foo.tmp .fi .LP This writes all comments in the zipfile .I foo.zip to the file .I foo.tmp in a specific format. .LP If desired, this file can then be edited to change the comments and then used to update the zipfile. .LP .nf zipnote -w foo.zip < foo.tmp .fi .LP The names of the files in the zipfile can also be changed in this way. This is done by following lines like .nf "@ name" .fi in the created temporary file (called .I foo.tmp here) with lines like .nf "@=newname" .fi and then using the -w option as above. .SH BUGS The temporary file format is rather specific and zipnote is rather picky about it. It should be easier to change file names in a script. Does not yet support large (> 2 GB) or split archives. .SH SEE ALSO zip(1), unzip(1) .SH AUTHOR Info-ZIP zip30/man/zipsplit.10100644000076400000060000000217211010533454012472 0ustar edisk.TH zipnote 1 "v3.0 of 8 May 2008" .SH NAME zipsplit \- split a zipfile into smaller zipfiles .SH SYNOPSIS .I zipsplit .RB [ \-t ] .RB [ \-i ] .RB [ \-p ] .RB [ \-s ] .RB [ \-n\ size ] .RB [ \-r\ room ] .RB [ \-b\ path ] .RB [ \-h ] .RB [ \-v ] .RB [ \-L ] zipfile .SH ARGUMENTS .in +13 .ti -13 zipfile Zipfile to split. .SH OPTIONS .TP .BI \-t Report how many files it will take, but don't make them. .TP .BI \-i Make index (zipsplit.idx) and count its size against first zip file. .TP .BI \-n\ \fRsize Make zip files no larger than "size" (default = 36000). .TP .BI \-r\ \fRroom Leave room for "room" bytes on the first disk (default = 0). .TP .BI \-b\ \fRpath Use path for the output zip files. .TP .BI \-p Pause between output zip files. .TP .BI \-s Do a sequential split even if it takes more zip files. .TP .BI \-h Show a short help. .TP .BI \-v Show version information. .TP .BI \-L Show software license. .SH DESCRIPTION .I zipsplit reads a zipfile and splits it into smaller zipfiles. .SH EXAMPLES To be filled in. .SH BUGS Does not yet support large (> 2 GB) or split archives. .SH SEE ALSO zip(1), unzip(1) .SH AUTHOR Info-ZIP zip30/match.S0100644000076400000060000003353110176404176011214 0ustar edisk/* Copyright (c) 1990-2005 Info-ZIP. All rights reserved. See the accompanying file LICENSE, version 2004-May-22 or later (the contents of which are also included in zip.h) for terms of use. If, for some reason, both of these files are missing, the Info-ZIP license also may be found at: ftp://ftp.info-zip.org/pub/infozip/license.html */ /* * match.s by Jean-loup Gailly. Translated to 32 bit code by Kai Uwe Rommel. * The 68020 version has been written by Francesco Potorti` * with adaptations by Carsten Steger , * Andreas Schwab and * Kristoffer Eriksson */ /* This file is NOT used in conjunction with zlib. */ #ifndef USE_ZLIB /* Preprocess with -DNO_UNDERLINE if your C compiler does not prefix * external symbols with an underline character '_'. */ #if defined(NO_UNDERLINE) || defined(__ELF__) # define _prev prev # define _window window # define _match_start match_start # define _prev_length prev_length # define _good_match good_match # define _nice_match nice_match # define _strstart strstart # define _max_chain_length max_chain_length # define _match_init match_init # define _longest_match longest_match #endif #ifdef DYN_ALLOC error: DYN_ALLOC not yet supported in match.s #endif /* Use 16-bytes alignment if your assembler supports it. Warning: gas * uses a log(x) parameter (.align 4 means 16-bytes alignment). On SVR4 * the parameter is a number of bytes. */ #ifndef ALIGNMENT # define ALIGNMENT 4 #endif #ifndef WSIZE # define WSIZE 32768 #endif #define MIN_MATCH 3 #define MAX_MATCH 258 #define MIN_LOOKAHEAD (MAX_MATCH + MIN_MATCH + 1) #define MAX_DIST (WSIZE - MIN_LOOKAHEAD) #if defined(i386) || defined(_I386) || defined(_i386) || defined(__i386) /* This version is for 386 Unix or OS/2 in 32 bit mode. * Warning: it uses the AT&T syntax: mov source,dest * This file is only optional. If you want to force the C version, * add -DNO_ASM to CFLAGS in Makefile and set OBJA to an empty string. * If you have reduced WSIZE in (g)zip.h, then make sure this is * assembled with an equivalent -DWSIZE=. * This version assumes static allocation of the arrays (-DDYN_ALLOC not used). */ .file "match.S" .globl _match_init .globl _longest_match .text _match_init: ret /*----------------------------------------------------------------------- * Set match_start to the longest match starting at the given string and * return its length. Matches shorter or equal to prev_length are discarded, * in which case the result is equal to prev_length and match_start is * garbage. * IN assertions: cur_match is the head of the hash chain for the current * string (strstart) and its distance is <= MAX_DIST, and prev_length >= 1 */ .align ALIGNMENT _longest_match: /* int longest_match(cur_match) */ #define cur_match 20(%esp) /* return address */ /* esp+16 */ push %ebp /* esp+12 */ push %edi /* esp+8 */ push %esi /* esp+4 */ push %ebx /* esp */ /* * match equ esi * scan equ edi * chain_length equ ebp * best_len equ ebx * limit equ edx */ mov cur_match,%esi mov _strstart,%edx mov _max_chain_length,%ebp /* chain_length = max_chain_length */ mov %edx,%edi sub $(MAX_DIST),%edx /* limit = strstart-MAX_DIST */ cld /* string ops increment si and di */ jae limit_ok sub %edx,%edx /* limit = NIL */ limit_ok: add $2+_window,%edi /* edi = offset(window+strstart+2) */ mov _prev_length,%ebx /* best_len = prev_length */ movw -2(%edi),%cx /* cx = scan[0..1] */ movw -3(%ebx,%edi),%ax /* ax = scan[best_len-1..best_len] */ cmp _good_match,%ebx /* do we have a good match already? */ jb do_scan shr $2,%ebp /* chain_length >>= 2 */ jmp do_scan .align ALIGNMENT long_loop: /* at this point, edi == scan+2, esi == cur_match */ movw -3(%ebx,%edi),%ax /* ax = scan[best_len-1..best_len] */ movw -2(%edi),%cx /* cx = scan[0..1] */ short_loop: /* * at this point, di == scan+2, si == cur_match, * ax = scan[best_len-1..best_len] and cx = scan[0..1] */ and $(WSIZE-1), %esi dec %ebp /* --chain_length */ movw _prev(,%esi,2),%si /* cur_match = prev[cur_match] */ /* top word of esi is still 0 */ jz the_end cmp %edx,%esi /* cur_match <= limit ? */ jbe the_end do_scan: cmpw _window-1(%ebx,%esi),%ax/* check match at best_len-1 */ jne short_loop cmpw _window(%esi),%cx /* check min_match_length match */ jne short_loop add $2+_window,%esi /* si = match */ mov $((MAX_MATCH>>1)-1),%ecx/* scan for at most MAX_MATCH bytes */ mov %edi,%eax /* ax = scan+2 */ repe; cmpsw /* loop until mismatch */ je maxmatch /* match of length MAX_MATCH? */ mismatch: movb -2(%edi),%cl /* mismatch on first or second byte? */ xchg %edi,%eax /* edi = scan+2, eax = end of scan */ subb -2(%esi),%cl /* cl = 0 if first bytes equal */ sub %edi,%eax /* eax = len */ sub $2+_window,%esi /* esi = cur_match + len */ sub %eax,%esi /* esi = cur_match */ subb $1,%cl /* set carry if cl == 0 (cannot use DEC) */ adc $0,%eax /* eax = carry ? len+1 : len */ cmp %ebx,%eax /* len > best_len ? */ jle long_loop mov %esi,_match_start /* match_start = cur_match */ mov %eax,%ebx /* ebx = best_len = len */ #ifdef FULL_SEARCH cmp $(MAX_MATCH),%eax /* len >= MAX_MATCH ? */ #else cmp _nice_match,%eax /* len >= nice_match ? */ #endif jl long_loop the_end: mov %ebx,%eax /* result = eax = best_len */ pop %ebx pop %esi pop %edi pop %ebp ret .align ALIGNMENT maxmatch: cmpsb jmp mismatch #else /* !(i386 || _I386 || _i386 || __i386) */ /* ======================== 680x0 version ================================= */ #if defined(m68k)||defined(mc68k)||defined(__mc68000__)||defined(__MC68000__) # ifndef mc68000 # define mc68000 # endif #endif #if defined(__mc68020__) || defined(__MC68020__) || defined(sysV68) # ifndef mc68020 # define mc68020 # endif #endif #if defined(mc68020) || defined(mc68000) #if (defined(mc68020) || defined(NeXT)) && !defined(UNALIGNED_OK) # define UNALIGNED_OK #endif #ifdef sysV68 /* Try Motorola Delta style */ # define GLOBAL(symbol) global symbol # define TEXT text # define FILE(filename) file filename # define invert_maybe(src,dst) dst,src # define imm(data) &data # define reg(register) %register # define addl add.l # define addql addq.l # define blos blo.b # define bhis bhi.b # define bras bra.b # define clrl clr.l # define cmpmb cmpm.b # define cmpw cmp.w # define cmpl cmp.l # define lslw lsl.w # define lsrl lsr.l # define movel move.l # define movew move.w # define moveb move.b # define moveml movem.l # define subl sub.l # define subw sub.w # define subql subq.l # define IndBase(bd,An) (bd,An) # define IndBaseNdxl(bd,An,Xn) (bd,An,Xn.l) # define IndBaseNdxw(bd,An,Xn) (bd,An,Xn.w) # define predec(An) -(An) # define postinc(An) (An)+ #else /* default style (Sun 3, NeXT, Amiga, Atari) */ # define GLOBAL(symbol) .globl symbol # define TEXT .text # define FILE(filename) .even # define invert_maybe(src,dst) src,dst # if defined(sun) || defined(mc68k) # define imm(data) #data # else # define imm(data) \#data # endif # define reg(register) register # define blos bcss # if defined(sun) || defined(mc68k) # define movel movl # define movew movw # define moveb movb # endif # define IndBase(bd,An) An@(bd) # define IndBaseNdxl(bd,An,Xn) An@(bd,Xn:l) # define IndBaseNdxw(bd,An,Xn) An@(bd,Xn:w) # define predec(An) An@- # define postinc(An) An@+ #endif /* styles */ #define Best_Len reg(d0) /* unsigned */ #define Cur_Match reg(d1) /* Ipos */ #define Loop_Counter reg(d2) /* int */ #define Scan_Start reg(d3) /* unsigned short */ #define Scan_End reg(d4) /* unsigned short */ #define Limit reg(d5) /* IPos */ #define Chain_Length reg(d6) /* unsigned */ #define Scan_Test reg(d7) #define Scan reg(a0) /* *uch */ #define Match reg(a1) /* *uch */ #define Prev_Address reg(a2) /* *Pos */ #define Scan_Ini reg(a3) /* *uch */ #define Match_Ini reg(a4) /* *uch */ #define Stack_Pointer reg(sp) GLOBAL (_match_init) GLOBAL (_longest_match) TEXT FILE ("match.S") _match_init: rts /*----------------------------------------------------------------------- * Set match_start to the longest match starting at the given string and * return its length. Matches shorter or equal to prev_length are discarded, * in which case the result is equal to prev_length and match_start is * garbage. * IN assertions: cur_match is the head of the hash chain for the current * string (strstart) and its distance is <= MAX_DIST, and prev_length >= 1 */ /* int longest_match (cur_match) */ #ifdef UNALIGNED_OK # define pushreg 15928 /* d2-d6/a2-a4 */ # define popreg 7292 #else # define pushreg 16184 /* d2-d7/a2-a4 */ # define popreg 7420 #endif _longest_match: movel IndBase(4,Stack_Pointer),Cur_Match moveml imm(pushreg),predec(Stack_Pointer) movel _max_chain_length,Chain_Length movel _prev_length,Best_Len movel imm(_prev),Prev_Address movel imm(_window+MIN_MATCH),Match_Ini movel _strstart,Limit movel Match_Ini,Scan_Ini addl Limit,Scan_Ini subw imm(MAX_DIST),Limit bhis L__limit_ok clrl Limit L__limit_ok: cmpl invert_maybe(_good_match,Best_Len) blos L__length_ok lsrl imm(2),Chain_Length L__length_ok: subql imm(1),Chain_Length #ifdef UNALIGNED_OK movew IndBase(-MIN_MATCH,Scan_Ini),Scan_Start movew IndBaseNdxw(-MIN_MATCH-1,Scan_Ini,Best_Len),Scan_End #else moveb IndBase(-MIN_MATCH,Scan_Ini),Scan_Start lslw imm(8),Scan_Start moveb IndBase(-MIN_MATCH+1,Scan_Ini),Scan_Start moveb IndBaseNdxw(-MIN_MATCH-1,Scan_Ini,Best_Len),Scan_End lslw imm(8),Scan_End moveb IndBaseNdxw(-MIN_MATCH,Scan_Ini,Best_Len),Scan_End #endif bras L__do_scan L__long_loop: #ifdef UNALIGNED_OK movew IndBaseNdxw(-MIN_MATCH-1,Scan_Ini,Best_Len),Scan_End #else moveb IndBaseNdxw(-MIN_MATCH-1,Scan_Ini,Best_Len),Scan_End lslw imm(8),Scan_End moveb IndBaseNdxw(-MIN_MATCH,Scan_Ini,Best_Len),Scan_End #endif L__short_loop: lslw imm(1),Cur_Match movew IndBaseNdxl(0,Prev_Address,Cur_Match),Cur_Match cmpw invert_maybe(Limit,Cur_Match) dbls Chain_Length,L__do_scan bras L__return L__do_scan: movel Match_Ini,Match addl Cur_Match,Match #ifdef UNALIGNED_OK cmpw invert_maybe(IndBaseNdxw(-MIN_MATCH-1,Match,Best_Len),Scan_End) bne L__short_loop cmpw invert_maybe(IndBase(-MIN_MATCH,Match),Scan_Start) bne L__short_loop #else moveb IndBaseNdxw(-MIN_MATCH-1,Match,Best_Len),Scan_Test lslw imm(8),Scan_Test moveb IndBaseNdxw(-MIN_MATCH,Match,Best_Len),Scan_Test cmpw invert_maybe(Scan_Test,Scan_End) bne L__short_loop moveb IndBase(-MIN_MATCH,Match),Scan_Test lslw imm(8),Scan_Test moveb IndBase(-MIN_MATCH+1,Match),Scan_Test cmpw invert_maybe(Scan_Test,Scan_Start) bne L__short_loop #endif movew imm((MAX_MATCH-MIN_MATCH+1)-1),Loop_Counter movel Scan_Ini,Scan L__scan_loop: cmpmb postinc(Match),postinc(Scan) dbne Loop_Counter,L__scan_loop subl Scan_Ini,Scan addql imm(MIN_MATCH-1),Scan cmpl invert_maybe(Best_Len,Scan) bls L__short_loop movel Scan,Best_Len movel Cur_Match,_match_start #ifdef FULL_SEARCH cmpl invert_maybe(imm(MAX_MATCH),Best_Len) #else cmpl invert_maybe(_nice_match,Best_Len) #endif blos L__long_loop L__return: moveml postinc(Stack_Pointer),imm(popreg) rts #else error: this asm version is for 386 or 680x0 only #endif /* mc68000 || mc68020 */ #endif /* i386 || _I386 || _i386 || __i386 */ #endif /* !USE_ZLIB */ zip30/msdos/0040755000076400000060000000000011033727770011120 5ustar ediskzip30/msdos/crc_i86.asm0100644000076400000060000003076010547735336013070 0ustar edisk;=========================================================================== ; Copyright (c) 1990-2007 Info-ZIP. All rights reserved. ; ; See the accompanying file LICENSE, version 2000-Apr-09 or later ; (the contents of which are also included in zip.h) for terms of use. ; If, for some reason, all these files are missing, the Info-ZIP license ; also may be found at: ftp://ftp.info-zip.org/pub/infozip/license.html ;=========================================================================== ; Created by Christian Spieler, last modified 07 Jan 2007. ; TITLE crc_i86.asm NAME crc_i86 ; ; Optimized 8086 assembler version of the CRC32 calculation loop, intended ; for real mode Info-ZIP programs (Zip 2.1, UnZip 5.2, and later versions). ; Supported compilers are Microsoft C (DOS real mode) and Borland C(++) ; (Turbo C). Watcom C (16bit) should also work. ; This module was inspired by a similar module for the Amiga (Paul Kienitz). ; ; It replaces the `ulg crc32(ulg crc, ZCONST uch *buf, extent len)' function ; in crc32.c. ; ; In March/April 1997, the code has been revised to incorporate Rodney Brown's ; ideas for optimized access to the data buffer. For 8086 real mode code, ; the data buffer is now accessed by aligned word-wide read operations. ; This new optimization may be turned off by defining the macro switch ; NO_16_BIT_LOADS. ; ; In December 1998, the loop branch commands were changed from "loop dest" ; into "dec cx; jnz dest". On modern systems (486 and newer), the latter ; code is usually much faster (e.g. 1 clock cycle compared to 5 for "loop" ; on Pentium MMX). For the 286, the penalty of "dec cx; jnz" is one clock ; cycle (12 vs. 11 cycles); on an 8088 the cycle counts are 22 (dec cx; jnz) ; vs. 18 (loop). I decided to optimize for newer CPU models by default, because ; I expect that old 80286 or 8088 dinosaurier machines may be rarely used ; nowadays. In case you want optimum performance for these old CPU models ; you should define the OPTIMIZE_286_88 macro switch on the assembler's ; command line. ; Likewise, "jcxz" was replaced by "jz", because the latter is faster on ; 486 and newer CPUs (without any penalty on 80286 and older CPU models). ; ; In January 2007, the "hand-made" memory model setup section has been guarded ; against redefinition of @CodeSize and @DataSize symbols, to work around a ; problem with current Open Watcom (version 1.6) wasm assembler. ; ; The code in this module should work with all kinds of C memory models ; (except Borland's __HUGE__ model), as long as the following ; restrictions are not violated: ; ; - The implementation assumes that the char buffer is confined to a ; 64k segment. The pointer `s' to the buffer must be in a format that ; all bytes can be accessed by manipulating the offset part, only. ; This means: ; + no huge pointers ; + char buffer size < 64 kByte ; ; - Since the buffer size argument `n' is of type `size_t' (= unsigned short) ; for this routine, the char buffer size is limited to less than 64 kByte, ; anyway. So, the assumption above should be easily fulfilled. ; ;============================================================================== ; ; Do NOT assemble this source if external crc32 routine from zlib gets used, ; or only the precomputed CRC_32_Table is needed. ; ifndef USE_ZLIB ifndef CRC_TABLE_ONLY ; ; Setup of amount of assemble time informational messages: ; ifdef DEBUG VERBOSE_INFO EQU 1 else ifdef _AS_MSG_ VERBOSE_INFO EQU 1 else VERBOSE_INFO EQU 0 endif endif ; ; Selection of memory model, and initialization of memory model ; related macros: ; ifndef __SMALL__ ifndef __COMPACT__ ifndef __MEDIUM__ ifndef __LARGE__ ifndef __HUGE__ ; __SMALL__ EQU 1 endif endif endif endif endif ifdef __HUGE__ ; .MODEL Huge ifndef @CodeSize @CodeSize EQU 1 endif ifndef @DataSize @DataSize EQU 1 endif Save_DS EQU 1 if VERBOSE_INFO if1 %out Assembling for C, Huge memory model endif endif else ifdef __LARGE__ ; .MODEL Large ifndef @CodeSize @CodeSize EQU 1 endif ifndef @DataSize @DataSize EQU 1 endif if VERBOSE_INFO if1 %out Assembling for C, Large memory model endif endif else ifdef __COMPACT__ ; .MODEL Compact ifndef @CodeSize @CodeSize EQU 0 endif ifndef @DataSize @DataSize EQU 1 endif if VERBOSE_INFO if1 %out Assembling for C, Compact memory model endif endif else ifdef __MEDIUM__ ; .MODEL Medium ifndef @CodeSize @CodeSize EQU 1 endif ifndef @DataSize @DataSize EQU 0 endif if VERBOSE_INFO if1 %out Assembling for C, Medium memory model endif endif else ; .MODEL Small ifndef @CodeSize @CodeSize EQU 0 endif ifndef @DataSize @DataSize EQU 0 endif if VERBOSE_INFO if1 %out Assembling for C, Small memory model endif endif endif endif endif endif if @CodeSize LCOD_OFS EQU 2 else LCOD_OFS EQU 0 endif IF @DataSize LDAT_OFS EQU 2 else LDAT_OFS EQU 0 endif ifdef Save_DS ; (di,si,ds)+(size, return address) SAVE_REGS EQU 6+(4+LCOD_OFS) else ; (di,si)+(size, return address) SAVE_REGS EQU 4+(4+LCOD_OFS) endif ; ; Selection of the supported CPU instruction set and initialization ; of CPU type related macros: ; ifdef __686 Use_286_code EQU 1 Align_Size EQU 4 ; dword alignment on Pentium II/III/IV Alig_PARA EQU 1 ; paragraph aligned code segment else ifdef __586 Use_286_code EQU 1 Align_Size EQU 4 ; dword alignment on Pentium Alig_PARA EQU 1 ; paragraph aligned code segment else ifdef __486 Use_286_code EQU 1 Align_Size EQU 4 ; dword alignment on 32 bit processors Alig_PARA EQU 1 ; paragraph aligned code segment else ifdef __386 Use_286_code EQU 1 Align_Size EQU 4 ; dword alignment on 32 bit processors Alig_PARA EQU 1 ; paragraph aligned code segment else ifdef __286 Use_286_code EQU 1 Align_Size EQU 2 ; word alignment on 16 bit processors Alig_PARA EQU 0 ; word aligned code segment else ifdef __186 Use_186_code EQU 1 Align_Size EQU 2 ; word alignment on 16 bit processors Alig_PARA EQU 0 ; word aligned code segment else Align_Size EQU 2 ; word alignment on 16 bit processors Alig_PARA EQU 0 ; word aligned code segment endif ;?__186 endif ;?__286 endif ;?__386 endif ;?__486 endif ;?__586 endif ;?__686 ifdef Use_286_code .286 Have_80x86 EQU 1 else ifdef Use_186_code .186 Have_80x86 EQU 1 else .8086 Have_80x86 EQU 0 endif ;?Use_186_code endif ;?Use_286_code ; ; Declare the segments used in this module: ; if @CodeSize if Alig_PARA CRC32_TEXT SEGMENT PARA PUBLIC 'CODE' else CRC32_TEXT SEGMENT WORD PUBLIC 'CODE' endif CRC32_TEXT ENDS else ;!@CodeSize if Alig_PARA _TEXT SEGMENT PARA PUBLIC 'CODE' else _TEXT SEGMENT WORD PUBLIC 'CODE' endif _TEXT ENDS endif ;?@CodeSize _DATA SEGMENT WORD PUBLIC 'DATA' _DATA ENDS _BSS SEGMENT WORD PUBLIC 'BSS' _BSS ENDS DGROUP GROUP _BSS, _DATA if @DataSize ASSUME DS: nothing, SS: DGROUP else ASSUME DS: DGROUP, SS: DGROUP endif if @CodeSize EXTRN _get_crc_table:FAR else EXTRN _get_crc_table:NEAR endif Do_CRC MACRO mov bl,al sub bh,bh if Have_80x86 shl bx,2 else shl bx,1 shl bx,1 endif mov al,ah mov ah,dl mov dl,dh sub dh,dh xor ax,WORD PTR [bx][si] xor dx,WORD PTR [bx+2][si] ENDM ; Do_1 MACRO if @DataSize xor al,BYTE PTR es:[di] else xor al,BYTE PTR [di] endif inc di Do_CRC ENDM ; Do_2 MACRO ifndef NO_16_BIT_LOADS if @DataSize xor ax,WORD PTR es:[di] else xor ax,WORD PTR [di] endif add di,2 Do_CRC Do_CRC else Do_1 Do_1 endif ENDM ; Do_4 MACRO Do_2 Do_2 ENDM ; IF @CodeSize CRC32_TEXT SEGMENT ASSUME CS: CRC32_TEXT else _TEXT SEGMENT ASSUME CS: _TEXT endif ; Line 37 ; ;ulg crc32(ulg crc, ; ZCONST uch *buf, ; extent len) ; PUBLIC _crc32 if @CodeSize _crc32 PROC FAR else _crc32 PROC NEAR endif if Have_80x86 enter WORD PTR 0,0 else push bp mov bp,sp endif push di push si if @DataSize ; crc = 4+LCOD_OFS DWORD (unsigned long) ; buf = 8+LCOD_OFS DWORD PTR BYTE (uch *) ; len = 12+LCOD_OFS WORD (unsigned int) else ; crc = 4+LCOD_OFS DWORD (unsigned long) ; buf = 8+LCOD_OFS WORD PTR BYTE (uch *) ; len = 10+LCOD_OFS WORD (unsigned int) endif ; if @DataSize mov ax,WORD PTR [bp+8+LCOD_OFS] ; buf or ax,WORD PTR [bp+10+LCOD_OFS] ; == NULL ? else cmp WORD PTR [bp+8+LCOD_OFS],0 ; buf == NULL ? endif jne crc_update sub ax,ax ; crc = 0 cwd ifndef NO_UNROLLED_LOOPS jmp fine else jmp SHORT fine endif ; crc_update: call _get_crc_table ; When used with compilers that conform to the Microsoft/Borland standard ; C calling convention, model-dependent handling is not needed, because ; _get_crc_table returns NEAR pointer. ; But Watcom C is different and does not allow one to assume DS pointing to ; DGROUP. So, we load DS with DGROUP, to be safe. ;if @DataSize ; push ds ; mov ds,dx ; ASSUME DS: nothing ;endif mov si,ax ;crc_table if @DataSize push ds mov ax,SEG DGROUP mov ds,ax ASSUME DS: DGROUP endif ; mov ax,WORD PTR [bp+4+LCOD_OFS] ;crc mov dx,WORD PTR [bp+6+LCOD_OFS] not ax not dx if @DataSize les di,DWORD PTR [bp+8+LCOD_OFS] ;buf mov cx,WORD PTR [bp+12+LCOD_OFS] ;len else mov di,WORD PTR [bp+8+LCOD_OFS] ;buf mov cx,WORD PTR [bp+10+LCOD_OFS] ;len endif ; ifndef NO_UNROLLED_LOOPS ifndef NO_16_BIT_LOADS test cx,cx jnz start jmp done start: test di,1 jz is_wordaligned dec cx Do_1 mov WORD PTR [bp+10+LDAT_OFS+LCOD_OFS],cx is_wordaligned: endif ; !NO_16_BIT_LOADS if Have_80x86 shr cx,2 else shr cx,1 shr cx,1 endif jz No_Fours ; align Align_Size ; align destination of branch Next_Four: Do_4 ifndef OPTIMIZE_286_88 dec cx ; on 286, "loop Next_Four" needs 11 jnz Next_Four ; clocks, one less than this code else loop Next_Four endif ; No_Fours: if @DataSize mov cx,WORD PTR [bp+12+LCOD_OFS] ;len else mov cx,WORD PTR [bp+10+LCOD_OFS] ;len endif and cx,00003H endif ; !NO_UNROLLED_LOOPS jz done ; align Align_Size ; align destination of branch Next_Byte: Do_1 ifndef OPTIMIZE_286_88 dec cx ; on 286, "loop Next_Four" needs 11 jnz Next_Byte ; clocks, one less than this code else loop Next_Four endif ; done: if @DataSize pop ds ; ASSUME DS: DGROUP ASSUME DS: nothing endif not ax not dx ; fine: pop si pop di if Have_80x86 leave else mov sp,bp pop bp endif ret _crc32 ENDP if @CodeSize CRC32_TEXT ENDS else _TEXT ENDS endif ; endif ;!CRC_TABLE_ONLY endif ;!USE_ZLIB ; END zip30/msdos/makebz2.dj20100644000076400000060000001027411031355364013047 0ustar edisk# Makefile for Zip, ZipCloak, ZipNote and ZipSplit for # djgpp 2.x # # This simple modified version of makefile.dj2 adds bzip2 support # to Zip for djgpp 2.x and was donated by Robert Riebisch. # # Given standard djgpp 2.x and bzip2 installations, this should create a # version of Zip 3.0 with bzip2 support. Additional information is in # bzip2/install.txt. # # 27 June 2008 VPATH=.;msdos # ------------- djgpp ------------- CPPFLAGS=-I. -DDOS -DASM_CRC -DBZIP2_SUPPORT $(LOCAL_ZIP) ASFLAGS=$(CPPFLAGS) CFLAGS=-Wall -O2 $(CPPFLAGS) UTILFLAGS=-c -DUTIL $(CFLAGS) -o CC=gcc LD=gcc LDFLAGS=-s # ------------- file packer -------- # Laszlo Molnar who wrote DJ Packer and Markus F. X. J. Oberhumer who wrote # the compression library used by the DJ Packer have collaborated on the # Ultimate Packer for eXecutables, which has recently been released. Look # for upx???d.zip at http://upx.sourceforge.net # As an alternative, look for "djp.exe", now two years old, in the archive # mlp107[b,s].zip, found in the same location as csdpmi?[b,s].zip (see below). # If you have got an executable packer in your PATH, you may reduce the # size of the disk image of the zip*.exe's by uncommenting the lines # containing $(DJP) below where the exe's are built. #DJP=djp -q DJP=upx -qq --best # variables #set CRC32 to crc_gcc.o or nothing, depending on whether ASM_CRC is defined: CRCA_O = crc_gcc.o OBJZ = zip.o crypt.o ttyio.o zipfile.o zipup.o fileio.o util.o \ crc32.o $(CRCA_O) globals.o OBJI = deflate.o trees.o match.o msdos.o OBJU = zipfile_.o fileio_.o util_.o globals.o msdos_.o OBJN = zipnote.o $(OBJU) OBJC = zipcloak.o crc32_.o crypt_.o ttyio.o $(OBJU) OBJS = zipsplit.o $(OBJU) LIBS = -lbz2 ZIP_H = zip.h ziperr.h tailor.h msdos/osdep.h # rules .SUFFIXES: # Delete make's default suffix list .SUFFIXES: .exe .out .a .ln .o .c .cc .C .p .f .F .y .l .s .S .h .c.o: $(CC) -c $(CFLAGS) $< -o $@ zips: zip.exe zipnote.exe zipsplit.exe zipcloak.exe zip.o: zip.c $(ZIP_H) revision.h crc32.h crypt.h ttyio.h zipfile.o: zipfile.c $(ZIP_H) crc32.h zipup.o: zipup.c $(ZIP_H) revision.h crc32.h crypt.h msdos/zipup.h fileio.o: fileio.c $(ZIP_H) crc32.h util.o: util.c $(ZIP_H) globals.o: globals.c $(ZIP_H) deflate.o: deflate.c $(ZIP_H) trees.o: trees.c $(ZIP_H) crc_gcc.o: crc_i386.S $(CC) $(ASFLAGS) -x assembler-with-cpp -c -o $@ crc_i386.S crc32.o: crc32.c $(ZIP_H) crc32.h crypt.o: crypt.c $(ZIP_H) crypt.h crc32.h ttyio.h ttyio.o: ttyio.c $(ZIP_H) crypt.h ttyio.h msdos.o: msdos/msdos.c $(ZIP_H) zipcloak.o: zipcloak.c $(ZIP_H) revision.h crc32.h crypt.h ttyio.h zipnote.o: zipnote.c $(ZIP_H) revision.h zipsplit.o: zipsplit.c $(ZIP_H) revision.h zipfile_.o: zipfile.c $(ZIP_H) crc32.h $(CC) $(UTILFLAGS) $@ zipfile.c fileio_.o: fileio.c $(ZIP_H) crc32.h $(CC) $(UTILFLAGS) $@ fileio.c util_.o: util.c $(ZIP_H) $(CC) $(UTILFLAGS) $@ util.c crc32_.o: crc32.c $(ZIP_H) crc32.h $(CC) $(UTILFLAGS) $@ crc32.c crypt_.o: crypt.c $(ZIP_H) crypt.h crc32.h ttyio.h $(CC) $(UTILFLAGS) $@ crypt.c msdos_.o: msdos/msdos.c $(ZIP_H) $(CC) $(UTILFLAGS) $@ msdos/msdos.c match.o: match.S $(CC) $(ASFLAGS) -x assembler-with-cpp -c -o $@ match.S zip.exe: $(OBJZ) $(OBJI) echo $(OBJZ) > zip.rsp echo $(OBJI) >> zip.rsp echo $(LIBS) >> zip.rsp $(LD) $(LDFLAGS) -o $@ @zip.rsp del zip.rsp # stubedit $@ dpmi=cwsdpmi.exe # $(DJP) $@ zipcloak.exe: $(OBJC) $(LD) $(LDFLAGS) $(OBJC) -o $@ # stubedit $@ dpmi=cwsdpmi.exe # $(DJP) $@ zipnote.exe: $(OBJN) $(LD) $(LDFLAGS) $(OBJN) -o $@ # stubedit $@ dpmi=cwsdpmi.exe # $(DJP) $@ zipsplit.exe: $(OBJS) $(LD) $(LDFLAGS) $(OBJS) -o $@ # stubedit $@ dpmi=cwsdpmi.exe # $(DJP) $@ # These stand alone executables require dpmi services to run. When # running in a DOS window under windows 3.1 or later, the dpmi server # is automatically present. Under DOS, if a dpmi server is not installed, # by default the program will look for "cwsdpmi.exe." If found, it will # be loaded for the duration of the program. # cwsdpmi is a "free" dpmi server written by Charles W. Sandmann # (sandman@clio.rice.edu). It may be found, among other sites, on SimTel # and its mirrors in the .../vendors/djgpp/v2misc directory. zip30/msdos/makefile.bor0100644000076400000060000001167710550047612013403 0ustar edisk# Makefile for Zip, ZipCloak, ZipNote and ZipSplit for # Borland (Turbo) C++ 1.0 or 2.0. # Warning: this file is not suitable for Turbo C 2.0. Use makefile.tc instead. # To use, do "make -fmakefile.bor" # WARNING: the small model is not supported. # Add -DSMALL_MEM or -DMEDIUM_MEM to the LOC macro if you wish to reduce # the memory requirements. # Add -DNO_ASM to CFLAGS and comment out the ASMOBJS definition if # you do not have tasm. # Optional nonstandard preprocessor flags (as -DMEDIUM_MEM or -DNO_ASM) # should be added to the environment via "set LOCAL_ZIP=-DFOO" or added # to the declaration of LOC here: LOC = -DDOS -DNO_SECURE_TESTS $(LOCAL_ZIP) # Zip requires compact or large memory model. # with 2.1, compact model exceeds 64k code segment; use large model ZIPMODEL=l # large model for Zip and ZipUtils # name of Flag to select memory model for assembler compiles, supported # values are __SMALL__ , __MEDIUM__ , __COMPACT__ , __LARGE__ : ASMODEL=__LARGE__ # keep in sync with ZIPMODEL definition !! # Type for CPU required: 0: 8086, 1: 80186, 2: 80286, 3: 80386, etc. CPU_TYP = 0 # Uncomment the following macro to use the optimized assembler # routines in Zip: CRCA_O = crc_i86.obj ASMOBJS = match.obj $(CRCA_O) ASCPUFLAG = __$(CPU_TYP)86 !if $(CPU_TYP) != 0 CC_CPUFLG = -$(CPU_TYP) !endif VPATH=.;msdos # ------------- Turbo C++, Borland C++ ------------- !if $(CC_REV) == 1 CC = tcc !else ! if !$(CC_REV) CC_REV = 3 ! endif CC = bcc !endif MODEL=-m$(ZIPMODEL) !if $(CC_REV) == 1 CFLAGS=-w -w-eff -w-def -w-sig -w-cln -a -d -G -O -Z $(CC_CPUFLG) $(MODEL) $(LOC) !else CFLAGS=-w -w-cln -O2 -Z $(CC_CPUFLG) $(MODEL) $(LOC) !endif UTILFLAGS=-DUTIL $(CFLAGS) -o # for Turbo C++ 1.0, replace bcc with tcc and use the upper version of CFLAGS AS=tasm ASFLAGS=-ml -t -m2 -DDYN_ALLOC -DSS_NEQ_DS -D$(ASCPUFLAG) -D$(ASMODEL) $(LOC) LD=$(CC) LDFLAGS=$(MODEL) # ------------- Common declarations: STRIP=@rem # If you don't have UPX, LZEXE, or PKLITE, get one of them. Then define: # (NOTE: upx needs a 386 or higher system to run the exe compressor) #STRIP=upx --8086 --best # or #STRIP=lzexe # or (if you've registered PKLITE) #STRIP=pklite # This makes a big difference in .exe size (and possibly load time) # ------------- Used by install rule # set BIN to the directory you want to install the executables to BIN = c:\util # variables OBJZ = zip.obj crypt.obj ttyio.obj zipfile.obj zipup.obj fileio.obj util.obj \ crc32.obj globals.obj OBJI = deflate.obj trees.obj $(ASMOBJS) msdos.obj OBJU = zipfile_.obj fileio_.obj util_.obj globals.obj msdos_.obj OBJN = zipnote.obj $(OBJU) OBJC = zipcloak.obj crc32_.obj crypt_.obj ttyio.obj $(OBJU) OBJS = zipsplit.obj $(OBJU) ZIP_H = zip.h ziperr.h tailor.h msdos/osdep.h ZIPS = zip.exe zipnote.exe zipsplit.exe zipcloak.exe zips: $(ZIPS) zip.obj: zip.c $(ZIP_H) revision.h crc32.h crypt.h ttyio.h $(CC) -c $(CFLAGS) $*.c zipfile.obj: zipfile.c $(ZIP_H) crc32.h $(CC) -c $(CFLAGS) $*.c zipup.obj: zipup.c $(ZIP_H) revision.h crc32.h crypt.h msdos/zipup.h $(CC) -c $(CFLAGS) $*.c fileio.obj: fileio.c $(ZIP_H) crc32.h $(CC) -c $(CFLAGS) $*.c util.obj: util.c $(ZIP_H) $(CC) -c $(CFLAGS) $*.c globals.obj: globals.c $(ZIP_H) $(CC) -c $(CFLAGS) $*.c deflate.obj: deflate.c $(ZIP_H) $(CC) -c $(CFLAGS) $*.c trees.obj: trees.c $(ZIP_H) $(CC) -c $(CFLAGS) $*.c crc32.obj: crc32.c $(ZIP_H) crc32.h $(CC) -c $(CFLAGS) $*.c crypt.obj: crypt.c $(ZIP_H) crypt.h crc32.h ttyio.h $(CC) -c $(CFLAGS) $*.c ttyio.obj: ttyio.c $(ZIP_H) crypt.h ttyio.h $(CC) -c $(CFLAGS) $*.c msdos.obj: msdos/msdos.c $(ZIP_H) $(CC) -c $(CFLAGS) msdos/$*.c zipcloak.obj: zipcloak.c $(ZIP_H) revision.h crc32.h crypt.h ttyio.h $(CC) -c $(CFLAGS) $*.c zipnote.obj: zipnote.c $(ZIP_H) revision.h $(CC) -c $(CFLAGS) $*.c zipsplit.obj: zipsplit.c $(ZIP_H) revision.h $(CC) -c $(CFLAGS) $*.c zipfile_.obj: zipfile.c $(ZIP_H) crc32.h $(CC) -c $(UTILFLAGS)$* zipfile.c fileio_.obj: fileio.c $(ZIP_H) crc32.h $(CC) -c $(UTILFLAGS)$* fileio.c util_.obj: util.c $(ZIP_H) $(CC) -c $(UTILFLAGS)$* util.c crc32_.obj: crc32.c $(ZIP_H) crc32.h $(CC) -c $(UTILFLAGS) crc32.c crypt_.obj: crypt.c $(ZIP_H) crypt.h crc32.h ttyio.h $(CC) -c $(UTILFLAGS)$* crypt.c msdos_.obj: msdos/msdos.c $(ZIP_H) $(CC) -c $(UTILFLAGS)$* msdos/msdos.c crc_i86.obj: msdos/crc_i86.asm $(AS) $(ASFLAGS) msdos\crc_i86.asm ; match.obj: msdos/match.asm $(AS) $(ASFLAGS) msdos\match.asm ; # we must cut the command line to fit in the MS/DOS 128 byte limit: zip.exe: $(OBJZ) $(OBJI) echo $(OBJZ) > zip.rsp echo $(OBJI) >> zip.rsp $(LD) $(LDFLAGS) @zip.rsp del zip.rsp $(STRIP) zip.exe zipcloak.exe: $(OBJC) echo $(OBJC) > zipc.rsp $(LD) $(LDFLAGS) @zipc.rsp del zipc.rsp $(STRIP) zipcloak.exe zipnote.exe: $(OBJN) echo $(OBJN) > zipn.rsp $(LD) $(LDFLAGS) @zipn.rsp del zipn.rsp $(STRIP) zipnote.exe zipsplit.exe: $(OBJS) echo $(OBJS) > zips.rsp $(LD) $(LDFLAGS) @zips.rsp del zips.rsp $(STRIP) zipsplit.exe install: $(ZIPS) copy /b *.exe $(BIN) clean: del *.obj del *.exe zip30/msdos/makefile.dj10100644000076400000060000000601710550051704013264 0ustar edisk# Makefile for Zip, ZipCloak, ZipNote and ZipSplit for # djgpp 1.x VPATH=.;msdos # ------------- djgpp ------------- CPPFLAGS=-I. -DDOS -DASM_CRC $(LOCAL_ZIP) ASFLAGS=$(CPPFLAGS) CFLAGS=-Wall -O2 -m486 $(CPPFLAGS) UTILFLAGS=-c -DUTIL $(CFLAGS) -o CC=gcc LD=gcc LDFLAGS=-s STRIP=strip # Change the STUBIFY definition to the upper version if you want to create # executables which can be used without any external extender file. # >>> NOTE: Either copy the go32 extender into your build directory, or # >>> edit the STUBIFY macro and add the correct path to "go32.exe". #STUBIFY=coff2exe -s go32.exe STUBIFY=coff2exe # variables #set CRCA_O to crc_gcc.o or nothing, depending on whether ASM_CRC is defined: CRCA_O = crc_gcc.o OBJZ = zip.o crypt.o ttyio.o zipfile.o zipup.o fileio.o util.o \ crc32.o $(CRCA_O) globals.o OBJI = deflate.o trees.o match.o msdos.o OBJU = zipfile_.o fileio_.o util_.o globals.o msdos_.o OBJN = zipnote.o $(OBJU) OBJC = zipcloak.o crc32_.o crypt_.o ttyio.o $(OBJU) OBJS = zipsplit.o $(OBJU) ZIP_H = zip.h ziperr.h tailor.h msdos/osdep.h # rules .SUFFIXES: # Delete make's default suffix list .SUFFIXES: .exe .out .a .ln .o .c .cc .C .p .f .F .y .l .s .S .h .c.o: $(CC) -c $(CFLAGS) $< -o $@ zips: zip.exe zipnote.exe zipsplit.exe zipcloak.exe zip.o: zip.c $(ZIP_H) revision.h crc32.h crypt.h ttyio.h zipfile.o: zipfile.c $(ZIP_H) crc32.h zipup.o: zipup.c $(ZIP_H) revision.h crc32.h crypt.h msdos/zipup.h fileio.o: fileio.c $(ZIP_H) util.o: util.c $(ZIP_H) globals.o: globals.c $(ZIP_H) deflate.o: deflate.c $(ZIP_H) trees.o: trees.c $(ZIP_H) crc_gcc.o: crc_i386.S $(CC) $(ASFLAGS) -x assembler-with-cpp -c -o $@ crc_i386.S crc32.o: crc32.c $(ZIP_H) crc32.h crypt.o: crypt.c $(ZIP_H) crypt.h crc32.h ttyio.h ttyio.o: ttyio.c $(ZIP_H) crypt.h ttyio.h msdos.o: msdos/msdos.c $(ZIP_H) zipcloak.o: zipcloak.c $(ZIP_H) revision.h crc32.h crypt.h ttyio.h zipnote.o: zipnote.c $(ZIP_H) revision.h zipsplit.o: zipsplit.c $(ZIP_H) revision.h zipfile_.o: zipfile.c $(ZIP_H) crc32.h $(CC) $(UTILFLAGS) $@ zipfile.c fileio_.o: fileio.c $(ZIP_H) crc32.h $(CC) $(UTILFLAGS) $@ fileio.c util_.o: util.c $(ZIP_H) $(CC) $(UTILFLAGS) $@ util.c crc32_.o: crc32.c $(ZIP_H) crc32.h $(CC) $(UTILFLAGS) $@ crc32.c crypt_.o: crypt.c $(ZIP_H) crypt.h crc32.h ttyio.h $(CC) $(UTILFLAGS) $@ crypt.c msdos_.o: msdos/msdos.c $(ZIP_H) $(CC) $(UTILFLAGS) $@ msdos/msdos.c match.o: match.S $(CC) $(ASFLAGS) -x assembler-with-cpp -c -o $@ match.S zip.exe: $(OBJZ) $(OBJI) echo $(OBJZ) > zip.rsp echo $(OBJI) >> zip.rsp $(LD) $(LDFLAGS) -o zip @zip.rsp del zip.rsp $(STRIP) zip $(STUBIFY) zip del zip zipcloak.exe: $(OBJC) $(LD) $(LDFLAGS) $(OBJC) -o zipcloak $(STRIP) zipcloak $(STUBIFY) zipcloak del zipcloak zipnote.exe: $(OBJN) $(LD) $(LDFLAGS) $(OBJN) -o zipnote $(STRIP) zipnote $(STUBIFY) zipnote del zipnote zipsplit.exe: $(OBJS) $(LD) $(LDFLAGS) $(OBJS) -o zipsplit $(STRIP) zipsplit $(STUBIFY) zipsplit del zipsplit zip30/msdos/makefile.dj20100644000076400000060000000751610550047560013277 0ustar edisk# Makefile for Zip, ZipCloak, ZipNote and ZipSplit for # djgpp 2.x VPATH=.;msdos # ------------- djgpp ------------- CPPFLAGS=-I. -DDOS -DASM_CRC $(LOCAL_ZIP) ASFLAGS=$(CPPFLAGS) CFLAGS=-Wall -O2 $(CPPFLAGS) UTILFLAGS=-c -DUTIL $(CFLAGS) -o CC=gcc LD=gcc LDFLAGS=-s # ------------- file packer -------- # Laszlo Molnar who wrote DJ Packer and Markus F. X. J. Oberhumer who wrote # the compression library used by the DJ Packer have collaborated on the # Ultimate Packer for eXecutables, which has recently been released. Look # for upx???d.zip at http://upx.sourceforge.net # As an alternative, look for "djp.exe", now two years old, in the archive # mlp107[b,s].zip, found in the same location as csdpmi?[b,s].zip (see below). # If you have got an executable packer in your PATH, you may reduce the # size of the disk image of the zip*.exe's by uncommenting the lines # containing $(DJP) below where the exe's are built. #DJP=djp -q DJP=upx -qq --best # variables #set CRC32 to crc_gcc.o or nothing, depending on whether ASM_CRC is defined: CRCA_O = crc_gcc.o OBJZ = zip.o crypt.o ttyio.o zipfile.o zipup.o fileio.o util.o \ crc32.o $(CRCA_O) globals.o OBJI = deflate.o trees.o match.o msdos.o OBJU = zipfile_.o fileio_.o util_.o globals.o msdos_.o OBJN = zipnote.o $(OBJU) OBJC = zipcloak.o crc32_.o crypt_.o ttyio.o $(OBJU) OBJS = zipsplit.o $(OBJU) ZIP_H = zip.h ziperr.h tailor.h msdos/osdep.h # rules .SUFFIXES: # Delete make's default suffix list .SUFFIXES: .exe .out .a .ln .o .c .cc .C .p .f .F .y .l .s .S .h .c.o: $(CC) -c $(CFLAGS) $< -o $@ zips: zip.exe zipnote.exe zipsplit.exe zipcloak.exe zip.o: zip.c $(ZIP_H) revision.h crc32.h crypt.h ttyio.h zipfile.o: zipfile.c $(ZIP_H) crc32.h zipup.o: zipup.c $(ZIP_H) revision.h crc32.h crypt.h msdos/zipup.h fileio.o: fileio.c $(ZIP_H) crc32.h util.o: util.c $(ZIP_H) globals.o: globals.c $(ZIP_H) deflate.o: deflate.c $(ZIP_H) trees.o: trees.c $(ZIP_H) crc_gcc.o: crc_i386.S $(CC) $(ASFLAGS) -x assembler-with-cpp -c -o $@ crc_i386.S crc32.o: crc32.c $(ZIP_H) crc32.h crypt.o: crypt.c $(ZIP_H) crypt.h crc32.h ttyio.h ttyio.o: ttyio.c $(ZIP_H) crypt.h ttyio.h msdos.o: msdos/msdos.c $(ZIP_H) zipcloak.o: zipcloak.c $(ZIP_H) revision.h crc32.h crypt.h ttyio.h zipnote.o: zipnote.c $(ZIP_H) revision.h zipsplit.o: zipsplit.c $(ZIP_H) revision.h zipfile_.o: zipfile.c $(ZIP_H) crc32.h $(CC) $(UTILFLAGS) $@ zipfile.c fileio_.o: fileio.c $(ZIP_H) crc32.h $(CC) $(UTILFLAGS) $@ fileio.c util_.o: util.c $(ZIP_H) $(CC) $(UTILFLAGS) $@ util.c crc32_.o: crc32.c $(ZIP_H) crc32.h $(CC) $(UTILFLAGS) $@ crc32.c crypt_.o: crypt.c $(ZIP_H) crypt.h crc32.h ttyio.h $(CC) $(UTILFLAGS) $@ crypt.c msdos_.o: msdos/msdos.c $(ZIP_H) $(CC) $(UTILFLAGS) $@ msdos/msdos.c match.o: match.S $(CC) $(ASFLAGS) -x assembler-with-cpp -c -o $@ match.S zip.exe: $(OBJZ) $(OBJI) echo $(OBJZ) > zip.rsp echo $(OBJI) >> zip.rsp $(LD) $(LDFLAGS) -o $@ @zip.rsp del zip.rsp # stubedit $@ dpmi=cwsdpmi.exe # $(DJP) $@ zipcloak.exe: $(OBJC) $(LD) $(LDFLAGS) $(OBJC) -o $@ # stubedit $@ dpmi=cwsdpmi.exe # $(DJP) $@ zipnote.exe: $(OBJN) $(LD) $(LDFLAGS) $(OBJN) -o $@ # stubedit $@ dpmi=cwsdpmi.exe # $(DJP) $@ zipsplit.exe: $(OBJS) $(LD) $(LDFLAGS) $(OBJS) -o $@ # stubedit $@ dpmi=cwsdpmi.exe # $(DJP) $@ # These stand alone executables require dpmi services to run. When # running in a DOS window under windows 3.1 or later, the dpmi server # is automatically present. Under DOS, if a dpmi server is not installed, # by default the program will look for "cwsdpmi.exe." If found, it will # be loaded for the duration of the program. # cwsdpmi is a "free" dpmi server written by Charles W. Sandmann # (sandman@clio.rice.edu). It may be found, among other sites, on SimTel # and its mirrors in the .../vendors/djgpp/v2misc directory. zip30/msdos/makefile.emx0100644000076400000060000001256010550051542013377 0ustar edisk# Makefile for Zip, ZipCloak, ZipNote and ZipSplit # using emx 0.9c for DOS. # By Kai-Uwe Rommel, Chr. Spieler, E-Yen Tan (and others). # Last updated 7th January 2007. # # This Makefile is a stripped down version of win32/Makefile.emx that # builds executables applying the default MSDOS emx setup. For variant # targets (using zlib), and cross-compilation for WIN32 or OS/2, take a # look into "win32/makefile.emx" resp. "os2/makefile.os2". # # Supported Make utilities: # - Microsoft/IBM nmake (e.g. from MSC 6.0 or newer) # - dmake 3.8 or higher # - GNU make, at least version 3.68 (GNUish 16-bit port, RSXNT Make 3.75 in a # Win95/WinNT DOS box, DJGPP v1.12 Make 3.71, some versions of DJGPP v2.x # 32-bit Make; current DJGPP v2.01 Make 3.76.1 does NOT work) # - NOT watcom make # The "smart" Make utilities mentioned below are Christian Spieler's # enhanced version of GNUish 16-bit Make (3.74) and his adaption of these # GNU Make sources to EMX (32-bit). # Supported 32-bit C Compilers for MSDOS: # - GNU gcc (emx kit 0.9c or newer, 32-bit) # Supported Assemblers: # - GNU as with GNU gcc # To use, enter "make/nmake/dmake -f msdos/makefile.emx" # (this makefile depends on its name being "msdos/makefile.emx"). # emx 0.9c, gcc, a.out format, for MS-DOS CC=gcc -O2 -m486 -Wall CFLAGS=-DDOS -DMSDOS -DASM_CRC AS=gcc ASFLAGS=-Di386 LDFLAGS=-o ./ LDFLAGS2=-s -Zsmall-conv OUT=-o OBJ=.o CRCA_O=crc_gcc.o OBJA=matchgcc.o OBJZS=msdos.o OBJUS=msdos_.o OSDEP_H=msdos/osdep.h ZIPUP_H=msdos/zipup.h #default settings for target dependent macros: DIRSEP = / AS_DIRSEP = / RM = del LOCAL_OPTS = $(LOCAL_ZIP) CCFLAGS = $(CFLAGS) $(LOCAL_OPTS) OBJZ1 = zip$(OBJ) zipfile$(OBJ) zipup$(OBJ) fileio$(OBJ) util$(OBJ) \ crc32$(OBJ) $(CRCA_O) OBJZ2 = globals$(OBJ) deflate$(OBJ) trees$(OBJ) crypt$(OBJ) \ ttyio$(OBJ) OBJZ = $(OBJZ1) $(OBJZ2) $(OBJZS) $(OBJA) OBJU1 = zipfile_$(OBJ) fileio_$(OBJ) util_$(OBJ) globals$(OBJ) OBJU = $(OBJU1) $(OBJUS) OBJN = zipnote$(OBJ) $(OBJU) OBJS = zipsplit$(OBJ) $(OBJU) OBJC1 = zipcloak$(OBJ) crc32_$(OBJ) crypt_$(OBJ) ttyio$(OBJ) OBJC = $(OBJC1) $(OBJU) ZIP_H = zip.h ziperr.h tailor.h $(OSDEP_H) # rules .SUFFIXES: .c $(OBJ) .c$(OBJ): $(CC) -c -I. $(CCFLAGS) $(OUT)$@ $< # targets all: zip.exe zipnote.exe zipsplit.exe zipcloak.exe zip$(OBJ): zip.c $(ZIP_H) revision.h crc32.h crypt.h ttyio.h zipfile$(OBJ): zipfile.c $(ZIP_H) crc32.h zipup$(OBJ): zipup.c $(ZIP_H) revision.h crc32.h crypt.h $(ZIPUP_H) fileio$(OBJ): fileio.c $(ZIP_H) crc32.h util$(OBJ): util.c $(ZIP_H) globals$(OBJ): globals.c $(ZIP_H) deflate$(OBJ): deflate.c $(ZIP_H) trees$(OBJ): trees.c $(ZIP_H) crc32$(OBJ): crc32.c $(ZIP_H) crc32.h crypt$(OBJ): crypt.c $(ZIP_H) crypt.h crc32.h ttyio.h ttyio$(OBJ): ttyio.c $(ZIP_H) crypt.h ttyio.h msdos$(OBJ): msdos/msdos.c $(ZIP_H) $(CC) -c -I. $(CCFLAGS) msdos$(DIRSEP)msdos.c win32zip$(OBJ): win32/win32zip.c $(ZIP_H) win32/win32zip.h win32/nt.h $(CC) -c -I. $(CCFLAGS) win32$(DIRSEP)win32zip.c win32$(OBJ): win32/win32.c $(ZIP_H) win32/win32zip.h $(CC) -c -I. $(CCFLAGS) win32$(DIRSEP)win32.c nt$(OBJ): win32/nt.c $(ZIP_H) win32/nt.h $(CC) -c -I. $(CCFLAGS) win32$(DIRSEP)nt.c crc_gcc$(OBJ): crc_i386.S # 32bit, GNU AS $(AS) $(ASFLAGS) -x assembler-with-cpp -c -o $@ crc_i386.S matchgcc$(OBJ): match.S $(AS) $(ASFLAGS) -x assembler-with-cpp -c -o $@ match.S zipcloak$(OBJ): zipcloak.c $(ZIP_H) revision.h crc32.h crypt.h ttyio.h zipnote$(OBJ): zipnote.c $(ZIP_H) revision.h zipsplit$(OBJ): zipsplit.c $(ZIP_H) revision.h zipfile_$(OBJ): zipfile.c $(ZIP_H) crc32.h $(CC) -c -I. $(CCFLAGS) -DUTIL $(OUT)$@ zipfile.c fileio_$(OBJ): fileio.c $(ZIP_H) crc32.h $(CC) -c -I. $(CCFLAGS) -DUTIL $(OUT)$@ fileio.c util_$(OBJ): util.c $(ZIP_H) $(CC) -c -I. $(CCFLAGS) -DUTIL $(OUT)$@ util.c crc32_$(OBJ): crc32.c $(ZIP_H) crc32.h $(CC) -c -I. $(CCFLAGS) -DUTIL $(OUT)$@ crc32.c crypt_$(OBJ): crypt.c $(ZIP_H) crypt.h crc32.h ttyio.h $(CC) -c -I. $(CCFLAGS) -DUTIL $(OUT)$@ crypt.c msdos_$(OBJ): msdos/msdos.c $(ZIP_H) $(CC) -c -I. $(CCFLAGS) -DUTIL $(OUT)$@ msdos$(DIRSEP)msdos.c win32_$(OBJ): win32/win32.c $(ZIP_H) win32/win32zip.h $(CC) -c -I. $(CCFLAGS) -DUTIL $(OUT)$@ win32$(DIRSEP)win32.c # This next bit is nasty, but is needed to overcome the MS-DOS command # line limit as response files for emx's gcc seem to only work if each # file is on a different line. DJGPP doesn't do this (if you are at all # interested). zip.exe: $(OBJZ) # for DUMB make utilities, uncomment the following commands: -@$(RM) zip.rsp @for %%f in ($(OBJZ1)) do echo %%f >> zip.rsp @for %%f in ($(OBJZ2)) do echo %%f >> zip.rsp @for %%f in ($(OBJZS) $(OBJA)) do echo %%f >> zip.rsp $(CC) $(LDFLAGS)$@ @zip.rsp $(LDFLAGS2) @$(RM) zip.rsp # smart make utilities (like well done ports of GNU Make) can use this: # $(CC) $(LDFLAGS)$@ $(OBJZ) $(LDFLAGS2) zipcloak.exe: $(OBJC) # for DUMB make utilities, uncomment the following commands: -@$(RM) zipcloak.rsp @for %%f in ($(OBJC1)) do echo %%f >> zipcloak.rsp @for %%f in ($(OBJU1)) do echo %%f >> zipcloak.rsp @for %%f in ($(OBJUS)) do echo %%f >> zipcloak.rsp $(CC) $(LDFLAGS)$@ @zipcloak.rsp $(LDFLAGS2) @$(RM) zipcloak.rsp # smart make utilities (like well done ports of GNU Make) can use this: # $(CC) $(LDFLAGS)$@ $(OBJC) $(LDFLAGS2) zipnote.exe: $(OBJN) $(CC) $(LDFLAGS)$@ $(OBJN) $(LDFLAGS2) zipsplit.exe: $(OBJS) $(CC) $(LDFLAGS)$@ $(OBJS) $(LDFLAGS2) zip30/msdos/makefile.msc0100644000076400000060000001420511027060616013370 0ustar edisk# Makefile for Zip, ZipCloak, ZipNote and ZipSplit for # Microsoft C 5.1 and above. # To use, do "make makefile.msc" # Add -DSMALL_MEM or -DMEDIUM_MEM to the LOC macro if you wish to reduce # the memory requirements. # Add -DNO_ASM to CFLAGS and comment out the ASMOBJS definition if # you do not have masm. # # If you want link Zip against zlib to replace the built-in deflate routines, # the following changes are required: # - in the definition of "LOC", add "-DUSE_ZLIB" and remove "-DNO_SECURE_TESTS" # - comment out the "ASMOBJS" symbol definition # - modify the linking command blocks for zip and zipcloak according to # the following scheme: # add a command line "echo ,,,zlib_$(ZIPMODEL); >> zip[c].rsp" just # before the "$(LD)..." line; and remove the semicolon character from the # "echo ..." line immediately preceding the just inserted command # Optional nonstandard preprocessor flags (as -DMEDIUM_MEM or -DNO_ASM) # should be added to the environment via "set LOCAL_ZIP=-DFOO" or added # to the declaration of LOC here: LOC = -DDOS -DDYN_ALLOC -DNO_SECURE_TESTS $(LOCAL_ZIP) # Zip requires compact or large memory model. # with 2.1, compact model exceeds 64k code segment; use large model ZIPMODEL=L # large model for Zip and ZipUtils # name of Flag to select memory model for assembler compiles, supported # values are __SMALL__ , __MEDIUM__ , __COMPACT__ , __LARGE__ : ASMODEL=__LARGE__ # keep in sync with ZIPMODEL definition !! # Type for CPU required: 0: 8086, 1: 80186, 2: 80286, 3: 80386, etc. CPU_TYP = 0 # Uncomment the following macro to use the optimized assembler # routines in Zip: ASMOBJS = match.obj crc_i86.obj ASCPUFLAG = __$(CPU_TYP)86 # ------------- Microsoft C 5.1, 6.0, 7.0 and VC++ Pro 1.0 ------------- CC=cl MODEL=-A$(ZIPMODEL) FP= # With the feature additions of Zip 3, the default data segment gets occupied # with too much initialized data to fit into 64k. As a workaround, for some # source files with large amount of message strings, -Gt is used to # force data items of size or larger into their own data segments. COMMON_CFLAGS=-nologo -I. $(MODEL) $(FP) -DMSC $(LOC) -W3 -G$(CPU_TYP) CFLAGS=$(COMMON_CFLAGS) -Ox SPECFLAGS=$(COMMON_CFLAGS) -Oaict -Gs # For MSC/C++ 7.0 and VC++ no special flags are needed: # SPECFLAGS=$(CFLAGS) UTILFLAGS=-DUTIL $(CFLAGS) -Fo AS=masm ASFLAGS=-ml -t -D$(ASCPUFLAG) -D$(ASMODEL) $(LOC) # For MSC 6.0, use: #AS=ml #ASFLAGS=-c -D$(ASCPUFLAG) -D$(ASMODEL) $(LOC) # Supress -DDYN_ALLOC in ASFLAGS if you have suppressed it in CFLAGS LD=link LDFLAGS=/noi/farcall/packcode/e/st:0x1400/m # If you use an exe packer as recommended below, remove /e from LDFLAGS # ------------- Common declarations: STRIP=rem # If you don't have UPX, LZEXE, or PKLITE, get one of them. Then define: # (NOTE: upx needs a 386 or higher system to run the exe compressor) #STRIP=upx --8086 --best # or #STRIP=lzexe # or (if you've registered PKLITE) #STRIP=pklite # and remove /e from LDFLAGS. # This makes a big difference in .exe size (and possibly load time) # ------------- Used by install rule # set BIN to the directory you want to install the executables to BIN = c:\util # variables OBJZ = zip.obj crypt.obj ttyio.obj zipfile.obj zipup.obj fileio.obj util.obj \ crc32.obj globals.obj OBJI = deflate.obj trees.obj $(ASMOBJS) msdos.obj OBJU = zipfile_.obj fileio_.obj util_.obj globals.obj msdos_.obj OBJN = zipnote.obj $(OBJU) OBJC = zipcloak.obj crc32_.obj crypt_.obj ttyio.obj $(OBJU) OBJS = zipsplit.obj $(OBJU) ZIP_H = zip.h ziperr.h tailor.h msdos/osdep.h ZIPS = zip.exe zipnote.exe zipsplit.exe zipcloak.exe zips: $(ZIPS) zip.obj: zip.c $(ZIP_H) revision.h crc32.h crypt.h ttyio.h $(CC) -c $(CFLAGS) -Gt65 $*.c # MSC 5.1 generates bad code on zipfile with -Ox zipfile.obj: zipfile.c $(ZIP_H) crc32.h $(CC) -c $(SPECFLAGS) $*.c zipup.obj: zipup.c $(ZIP_H) revision.h crc32.h crypt.h msdos/zipup.h $(CC) -c $(CFLAGS) $*.c fileio.obj: fileio.c $(ZIP_H) crc32.h $(CC) -c $(CFLAGS) $*.c util.obj: util.c $(ZIP_H) $(CC) -c $(CFLAGS) $*.c globals.obj: globals.c $(ZIP_H) $(CC) -c $(CFLAGS) $*.c deflate.obj: deflate.c $(ZIP_H) $(CC) -c $(CFLAGS) $*.c trees.obj: trees.c $(ZIP_H) $(CC) -c $(CFLAGS) $*.c crc32.obj: crc32.c $(ZIP_H) crc32.h $(CC) -c $(CFLAGS) $*.c crypt.obj: crypt.c $(ZIP_H) crypt.h crc32.h ttyio.h $(CC) -c $(CFLAGS) $*.c ttyio.obj: ttyio.c $(ZIP_H) crypt.h ttyio.h $(CC) -c $(CFLAGS) $*.c msdos.obj: msdos/msdos.c $(ZIP_H) $(CC) -c $(CFLAGS) msdos/$*.c zipcloak.obj: zipcloak.c $(ZIP_H) revision.h crc32.h crypt.h ttyio.h $(CC) -c $(CFLAGS) $*.c zipnote.obj: zipnote.c $(ZIP_H) revision.h $(CC) -c $(CFLAGS) $*.c # MSC 5.1 dies on zipsplit with -Ox zipsplit.obj: zipsplit.c $(ZIP_H) revision.h $(CC) -c $(SPECFLAGS) $*.c # MSC 5.1 generates bad code on zipfile with -Ox zipfile_.obj: zipfile.c $(ZIP_H) crc32.h $(CC) -c $(SPECFLAGS) -DUTIL -Fo$@ zipfile.c fileio_.obj: fileio.c $(ZIP_H) crc32.h $(CC) -c $(UTILFLAGS)$@ fileio.c util_.obj: util.c $(ZIP_H) $(CC) -c $(UTILFLAGS)$@ util.c crc32_.obj: crc32.c $(ZIP_H) crc32.h $(CC) -c $(UTILFLAGS)$@ crc32.c crypt_.obj: crypt.c $(ZIP_H) crypt.h crc32.h ttyio.h $(CC) -c $(UTILFLAGS)$@ crypt.c msdos_.obj: msdos/msdos.c $(ZIP_H) $(CC) -c $(UTILFLAGS)$@ msdos/msdos.c crc_i86.obj: msdos/crc_i86.asm $(AS) $(ASFLAGS) msdos\crc_i86.asm ; match.obj: msdos/match.asm $(AS) $(ASFLAGS) msdos\match.asm ; # we must cut the command line to fit in the MS/DOS 128 byte limit: zip.exe: $(OBJZ) $(OBJI) echo $(OBJZ)+ > zip.rsp echo $(OBJI); >> zip.rsp $(LD) $(LDFLAGS) @zip.rsp del zip.rsp $(STRIP) zip.exe zipcloak.exe: $(OBJC) echo $(OBJC); > zipc.rsp $(LD) $(LDFLAGS) @zipc.rsp del zipc.rsp $(STRIP) zipcloak.exe zipnote.exe: $(OBJN) echo $(OBJN); > zipn.rsp $(LD) $(LDFLAGS) @zipn.rsp del zipn.rsp $(STRIP) zipnote.exe zipsplit.exe: $(OBJS) echo $(OBJS); > zips.rsp $(LD) $(LDFLAGS) @zips.rsp del zips.rsp $(STRIP) zipsplit.exe # No `install' and `clean' target possible as long as MSC's old MAKE utility # is supported (MSC 5.1 Make always tries to update ALL targets. The result # is that install and clean are always executed, unless an error occured.) #install: $(ZIPS) # copy /b *.exe $(BIN) # #clean: # del *.obj # del *.exe zip30/msdos/makefile.tc0100644000076400000060000001133710550051100013203 0ustar edisk# Makefile for Zip, ZipCloak, ZipNote and ZipSplit for # Turbo C 2.0. (Thanks to Andrew Cadach ) # To use, do "make -fmakefile.tc" # WARNING: the small model is not supported. You must use the large model. # Add -DSMALL_MEM or -DMEDIUM_MEM to the LOC macro if you wish to reduce # the memory requirements. # Add -DNO_ASM to CFLAGS and comment out the ASMOBJS definition if # you do not have tasm. # Optional nonstandard preprocessor flags (as -DMEDIUM_MEM or -DNO_ASM) # should be added to the environment via "set LOCAL_ZIP=-DFOO" or added # to the declaration of LOC here: LOC = -DDOS -DNO_SECURE_TESTS $(LOCAL_ZIP) # Zip requires compact or large memory model. # with 2.1, compact model exceeds 64k code segment; use large model ZIPMODEL=l # large model for Zip and ZipUtils # name of Flag to select memory model for assembler compiles, supported # values are __SMALL__ , __MEDIUM__ , __COMPACT__ , __LARGE__ : ASMODEL=__LARGE__ # keep in sync with ZIPMODEL definition !! # Type for CPU required: 0: 8086, 1: 80186, 2: 80286, 3: 80386, etc. CPU_TYP = 0 # Uncomment the following macro to use the optimized assembler # routines in Zip: ASMOBJS = match.obj crc_i86.obj ASCPUFLAG = __$(CPU_TYP)86 # ------------- Turbo C 2.0 ------------- MODEL=-m$(ZIPMODEL) CFLAGS=-w -w-eff -w-def -w-sig -w-cln -a -d -G -O -Z $(MODEL) $(LOC) UTILFLAGS=-DUTIL $(CFLAGS) -o CC=tcc # Old versions of tasm (prior to 2.01) may not like the "-m2" option... AS=tasm ASFLAGS=-ml -t -m2 -DDYN_ALLOC -DSS_NEQ_DS -D$(ASCPUFLAG) -D$(ASMODEL) $(LOC) LD=tcc LDFLAGS=$(MODEL) # ------------- Common declarations: STRIP=rem # If you don't have UPX, LZEXE, or PKLITE, get one of them. Then define: # (NOTE: upx needs a 386 or higher system to run the exe compressor) #STRIP=upx --8086 --best # or #STRIP=lzexe # or (if you've registered PKLITE) #STRIP=pklite # This makes a big difference in .exe size (and possibly load time) # ------------- Used by install rule # set BIN to the directory you want to install the executables to BIN = c:\util # variables OBJZ = zip.obj crypt.obj ttyio.obj zipfile.obj zipup.obj fileio.obj util.obj \ crc32.obj globals.obj OBJI = deflate.obj trees.obj $(ASMOBJS) msdos.obj OBJU = _zipfile.obj _fileio.obj _util.obj globals.obj _msdos.obj OBJN = zipnote.obj $(OBJU) OBJC = zipcloak.obj _crc32.obj _crypt.obj ttyio.obj $(OBJU) OBJS = zipsplit.obj $(OBJU) ZIP_H = zip.h ziperr.h tailor.h msdos/osdep.h ZIPS = zip.exe zipnote.exe zipsplit.exe zipcloak.exe zips: $(ZIPS) zip.obj: zip.c $(ZIP_H) revision.h crc32.h crypt.h ttyio.h $(CC) -c $(CFLAGS) $*.c zipfile.obj: zipfile.c $(ZIP_H) crc32.h $(CC) -c $(CFLAGS) $*.c zipup.obj: zipup.c $(ZIP_H) revision.h crc32.h crypt.h msdos/zipup.h $(CC) -c $(CFLAGS) $*.c fileio.obj: fileio.c $(ZIP_H) crc32.h $(CC) -c $(CFLAGS) $*.c util.obj: util.c $(ZIP_H) $(CC) -c $(CFLAGS) $*.c globals.obj: globals.c $(ZIP_H) $(CC) -c $(CFLAGS) $*.c deflate.obj: deflate.c $(ZIP_H) $(CC) -c $(CFLAGS) $*.c trees.obj: trees.c $(ZIP_H) $(CC) -c $(CFLAGS) $*.c crc32.obj: crc32.c $(ZIP_H) crc32.h $(CC) -c $(CFLAGS) $*.c crypt.obj: crypt.c $(ZIP_H) crypt.h crc32.h ttyio.h $(CC) -c $(CFLAGS) $*.c ttyio.obj: ttyio.c $(ZIP_H) crypt.h ttyio.h $(CC) -c $(CFLAGS) $*.c msdos.obj: msdos/msdos.c $(ZIP_H) $(CC) -c $(CFLAGS) msdos/$*.c zipcloak.obj: zipcloak.c $(ZIP_H) revision.h crc32.h crypt.h ttyio.h $(CC) -c $(CFLAGS) -o$* $*.c zipnote.obj: zipnote.c $(ZIP_H) revision.h $(CC) -c $(CFLAGS) -o$* $*.c zipsplit.obj: zipsplit.c $(ZIP_H) revision.h $(CC) -c $(CFLAGS) -o$* $*.c _zipfile.obj: zipfile.c $(ZIP_H) crc32.h $(CC) -c $(UTILFLAGS)$* zipfile.c _fileio.obj: fileio.c $(ZIP_H) crc32.h $(CC) -c $(UTILFLAGS)$* fileio.c _util.obj: util.c $(ZIP_H) $(CC) -c $(UTILFLAGS)$* util.c _crc32.obj: crc32.c $(ZIP_H) crc32.h $(CC) -c $(UTILFLAGS)$* crc32.c _crypt.obj: crypt.c $(ZIP_H) crypt.h crc32.h ttyio.h $(CC) -c $(UTILFLAGS)$* crypt.c _msdos.obj: msdos/msdos.c $(ZIP_H) $(CC) -c $(UTILFLAGS)$* msdos/msdos.c crc_i86.obj: msdos/crc_i86.asm $(AS) $(ASFLAGS) msdos\crc_i86.asm ; match.obj: msdos/match.asm $(AS) $(ASFLAGS) msdos\match.asm ; # make sure the command line fits in the MS/DOS 128 byte limit: zip.exe: $(OBJZ) $(OBJI) rem ignore any warnings in the following renaming commands: ren _*.obj _*.ob ren zipcloak.obj *.ob ren zipnote.obj *.ob ren zipsplit.obj *.ob $(LD) $(LDFLAGS) -ezip.exe *.obj ren _*.ob _*.obj ren zip???*.ob *.obj $(STRIP) zip.exe zipcloak.exe: $(OBJC) $(LD) $(LDFLAGS) -ezipcloak.exe $(OBJC) $(STRIP) zipcloak.exe zipnote.exe: $(OBJN) $(LD) $(LDFLAGS) -ezipnote.exe $(OBJN) $(STRIP) zipnote.exe zipsplit.exe: $(OBJS) $(LD) $(LDFLAGS) -ezipsplit.exe $(OBJS) $(STRIP) zipsplit.exe install: $(ZIPS) copy /b *.exe $(BIN) clean: del *.obj del *.exe zip30/msdos/makefile.wat0100644000076400000060000001721210550051406013377 0ustar edisk# WMAKE makefile for 16 bit MSDOS or 32 bit DOS extender (PMODE/W or DOS/4GW) # using Watcom C/C++ v11.0+, by Paul Kienitz, last revised 07 Aug 2005. # Makes Zip.exe, ZipNote.exe, ZipCloak.exe, and ZipSplit.exe. # # Invoke from Zip source dir with "WMAKE -F MSDOS\MAKEFILE.WAT [targets]" # To build with debug info use "WMAKE DEBUG=1 ..." # To build with no assembly modules use "WMAKE NOASM=1 ..." # To make the PMODE/W version use "WMAKE PM=1 ..." # To make the DOS/4GW version use "WMAKE GW=1 ..." (overrides PM=1) # Note: specifying PM or GW without NOASM requires that the win32 source # directory be present, so it can access the 32 bit assembly sources. # PMODE/W is recommended over DOS/4GW for best performance. # To create a low memory usage version of Zip, use "WMAKE WSIZE=8192 ..." # (or whatever power of two less than 32768 you wish) -- this also causes # SMALL_MEM to be defined. Compression performance will be reduced. # This currently is not supported with PM=1 or GW=1. # # Other options to be fed to the compiler and assembler can be specified in # an environment variable called LOCAL_ZIP. variation = $(%LOCAL_ZIP) # Stifle annoying "Delete this file?" questions when errors occur: .ERASE .EXTENSIONS: .EXTENSIONS: .exe .obj .c .h .asm # We maintain multiple sets of object files in different directories so that # we can compile msdos, dos/4gw or pmode/w, and win32 versions of Zip without # their object files interacting. The following var must be a directory name # ending with a backslash. All object file names must include this macro # at the beginning, for example "$(O)foo.obj". !ifdef GW PM = 1 # both protected mode formats use the same object files !endif !ifdef DEBUG ! ifdef PM OBDIR = od32d ! else ! ifdef WSIZE OBDIR = od16l size = -DWSIZE=$(WSIZE) -DSMALL_MEM ! else OBDIR = od16d size = -DMEDIUM_MEM ! endif ! endif !else ! ifdef PM OBDIR = ob32d ! else ! ifdef WSIZE OBDIR = ob16l size = -DWSIZE=$(WSIZE) -DSMALL_MEM ! else OBDIR = ob16d size = -DMEDIUM_MEM ! endif ! endif !endif O = $(OBDIR)\ # comment here so backslash won't continue the line # The assembly hot-spot code in crc_i[3]86.asm and match[32].asm is # optional. This section controls its usage. !ifdef NOASM # C source asmob = cvars = $+$(cvars)$- -DDYN_ALLOC -DNO_ASM # or ASM_CRC might default on! # "$+$(foo)$-" means expand foo as it has been defined up to now; normally, # this make defers inner expansion until the outer macro is expanded. !else # !NOASM asmob = $(O)crc.obj $(O)match.obj ! ifdef PM cvars = $+$(cvars)$- -DASM_CRC -DASMV # no DYN_ALLOC with match32.asm crc_s = win32\crc_i386.asm # requires that the win32 directory be present mat_s = win32\match32.asm # ditto ! else cvars = $+$(cvars)$- -DDYN_ALLOC -DASM_CRC -DASMV avars = $+$(avars)$- -DDYN_ALLOC crc_s = msdos\crc_i86.asm mat_s = msdos\match.asm ! endif !endif # Now we have to pick out the proper compiler and options for it. This gets # pretty complicated with the PM, GW, DEBUG, and NOASM options... link = wlink asm = wasm !ifdef PM cc = wcc386 # Use Pentium Pro timings, register args, static strings in code: cflags = -bt=DOS -mf -6r -zt -zq aflags = -bt=DOS -mf -3 -zq cvars = $+$(cvars)$- -DDOS $(variation) avars = $+$(avars)$- -DWATCOM_DSEG $(variation) ! ifdef GW lflags = sys DOS4G ! else # THIS REQUIRES THAT PMODEW.EXE BE FINDABLE IN THE COMMAND PATH. # It does NOT require you to add a pmodew entry to wlink.lnk or wlsystem.lnk. defaultlibs = libpath %WATCOM%\lib386 libpath %WATCOM%\lib386\dos lflags = format os2 le op osname='PMODE/W' op stub=pmodew.exe $(defaultlibs) ! endif !else # plain 16-bit DOS: cc = wcc # Use plain 8086 instructions, large memory model, static strings in code: cflags = -bt=DOS -ml -0 -zt -zq aflags = -bt=DOS -ml -0 -zq cvars = $+$(cvars)$- -DDOS $(size) $(variation) avars = $+$(avars)$- $(size) $(variation) lflags = sys DOS !endif # !PM # Specify optimizations, or a nonoptimized debugging version: !ifdef DEBUG cdebug = -od -d2 ldebug = d w all op symf !else ! ifdef PM cdebug = -s -obhikl+rt -oe=100 -zp8 # -oa helps slightly but might be dangerous. ! else cdebug = -s -oehiklrt ! endif ldebug = op el !endif # How to compile most sources: .c.obj: $(cc) $(cdebug) $(cflags) $(cvars) $[@ -fo=$@ # Our object files. OBJZ is for Zip, OBJC is for ZipCloak, OBJN is for # ZipNote, and OBJS is for ZipSplit: OBJZ2 = $(O)zip.obj $(O)crypt.obj $(O)ttyio.obj $(O)zipfile.obj $(O)zipup.obj OBJZA = $(OBJZ2) $(O)util.obj $(O)fileio.obj $(O)deflate.obj OBJZB = $(O)trees.obj $(O)globals.obj $(O)crc32.obj $(asmob) $(O)msdos.obj OBJU2 = $(O)zipfile_.obj $(O)fileio_.obj $(O)util_.obj $(O)globals.obj OBJ_U = $(OBJU2) $(O)msdos_.obj OBJC = $(O)zipcloak.obj $(O)crc32_.obj $(O)crypt_.obj $(O)ttyio.obj $(OBJ_U) OBJN = $(O)zipnote.obj $(OBJ_U) OBJS = $(O)zipsplit.obj $(OBJ_U) # Common header files included by all C sources: ZIP_H = zip.h ziperr.h tailor.h msdos\osdep.h # HERE WE GO! By default, make all targets: all: Zip.exe ZipNote.exe ZipCloak.exe ZipSplit.exe # Convenient shorthand options for single targets: z: Zip.exe .SYMBOLIC n: ZipNote.exe .SYMBOLIC c: ZipCloak.exe .SYMBOLIC s: ZipSplit.exe .SYMBOLIC Zip.exe: $(OBDIR) $(OBJZA) $(OBJZB) $(OBJV) set WLK_VA=file {$(OBJZA)} set WLK_VB=file {$(OBJZB) $(OBJV)} $(link) $(lflags) $(ldebug) name $@ @WLK_VA @WLK_VB set WLK_VA= set WLK_VB= # We use WLK_VA and WLK_VB to keep the size of each command under 256 chars. ZipNote.exe: $(OBDIR) $(OBJN) set WLK_VAR=file {$(OBJN)} $(link) $(lflags) $(ldebug) name $@ @WLK_VAR set WLK_VAR= ZipCloak.exe: $(OBDIR) $(OBJC) set WLK_VAR=file {$(OBJC)} $(link) $(lflags) $(ldebug) name $@ @WLK_VAR set WLK_VAR= ZipSplit.exe: $(OBDIR) $(OBJS) set WLK_VAR=file {$(OBJS)} $(link) $(lflags) $(ldebug) name $@ @WLK_VAR set WLK_VAR= # Source dependencies: $(O)crc32.obj: crc32.c $(ZIP_H) crc32.h $(O)crypt.obj: crypt.c $(ZIP_H) crypt.h crc32.h ttyio.h $(O)deflate.obj: deflate.c $(ZIP_H) $(O)fileio.obj: fileio.c $(ZIP_H) crc32.h $(O)globals.obj: globals.c $(ZIP_H) $(O)trees.obj: trees.c $(ZIP_H) $(O)ttyio.obj: ttyio.c $(ZIP_H) crypt.h ttyio.h $(O)util.obj: util.c $(ZIP_H) $(O)zip.obj: zip.c $(ZIP_H) crc32.h crypt.h revision.h ttyio.h $(O)zipfile.obj: zipfile.c $(ZIP_H) crc32.h $(O)zipup.obj: zipup.c $(ZIP_H) revision.h crc32.h crypt.h msdos\zipup.h $(O)zipnote.obj: zipnote.c $(ZIP_H) revision.h $(O)zipcloak.obj: zipcloak.c $(ZIP_H) revision.h crc32.h crypt.h ttyio.h $(O)zipsplit.obj: zipsplit.c $(ZIP_H) revision.h # Special case object files: $(O)msdos.obj: msdos\msdos.c $(ZIP_H) $(cc) $(cdebug) $(cflags) $(cvars) msdos\msdos.c -fo=$@ $(O)match.obj: $(mat_s) $(asm) $(aflags) $(avars) $(mat_s) -fo=$@ $(O)crc.obj: $(crc_s) $(asm) $(aflags) $(avars) $(crc_s) -fo=$@ # Variant object files for ZipNote, ZipCloak, and ZipSplit: $(O)zipfile_.obj: zipfile.c $(ZIP_H) crc32.h $(cc) $(cdebug) $(cflags) $(cvars) -DUTIL zipfile.c -fo=$@ $(O)fileio_.obj: fileio.c $(ZIP_H) crc32.h $(cc) $(cdebug) $(cflags) $(cvars) -DUTIL fileio.c -fo=$@ $(O)util_.obj: util.c $(ZIP_H) $(cc) $(cdebug) $(cflags) $(cvars) -DUTIL util.c -fo=$@ $(O)crc32_.obj: crc32.c $(ZIP_H) crc32.h $(cc) $(cdebug) $(cflags) $(cvars) -DUTIL crc32.c -fo=$@ $(O)crypt_.obj: crypt.c $(ZIP_H) crc32.h crypt.h ttyio.h $(cc) $(cdebug) $(cflags) $(cvars) -DUTIL crypt.c -fo=$@ $(O)msdos_.obj: msdos\msdos.c $(ZIP_H) $(cc) $(cdebug) $(cflags) $(cvars) -DUTIL msdos\msdos.c -fo=$@ # Creation of subdirectory for intermediate files $(OBDIR): -mkdir $@ # Unwanted file removal: clean: .SYMBOLIC del $(O)*.obj cleaner: clean .SYMBOLIC del Zip.exe del ZipNote.exe del ZipCloak.exe del ZipSplit.exe zip30/msdos/match.asm0100644000076400000060000003535711027062000012705 0ustar edisk;=========================================================================== ; Copyright (c) 1990-2008 Info-ZIP. All rights reserved. ; ; See the accompanying file LICENSE, version 2007-Mar-04 or later ; (the contents of which are also included in zip.h) for terms of use. ; If, for some reason, all these files are missing, the Info-ZIP license ; also may be found at: ftp://ftp.info-zip.org/pub/infozip/license.html ;=========================================================================== ; ; match.asm by Jean-loup Gailly. ; match.asm, optimized version of longest_match() in deflate.c ; Must be assembled with masm -ml. To be used only with C compact model ; or large model. (For large model, assemble with -D__LARGE__). ; This file is only optional. If you don't have masm or tasm, use the ; C version (add -DNO_ASM to CFLAGS in makefile.msc and remove match.obj ; from OBJI). If you have reduced WSIZE in zip.h, then make sure this is ; assembled with an equivalent -DWSIZE=. ; ; The code has been prepared for two different C compiler calling conventions ; and contains some support for dynamically allocated working space. ; The different environments are selected by two conditional flags: ; DYN_ALLOC : select support for malloc'ed working space ; SS_NEQ_DS : relaxes assumption that stack and default data segments ; are identical ; When SS_NEQ_DS is defined, the code segment is used to store some ; local variables. This (bad) coding practice is very likely to break any ; `segment protection scheme', it will most probably only work for real ; mode programs. ; ; Turbo C 2.0 does not support static allocation of more than 64K bytes per ; file, and does not have SS == DS. So TC and BC++ users must use: ; tasm -ml -DDYN_ALLOC -DSS_NEQ_DS match; ; ; To simplify the code, the option -DDYN_ALLOC is supported for OS/2 ; only if the arrays are guaranteed to have zero offset (allocated by ; halloc). We also require SS==DS. This is satisfied for MSC but not Turbo C. ; ; Per default, test code is included to check if the above requirements are ; fulfilled. This test code can be disabled by defining the compile time ; option flag NO_SECURE_TESTS when compiling for a production executable. ; This shortens the code size (but the performance gain is neglectable). ; The security tests should remain enabled, when a new C compiler ; and/or a new set of compilation options is tried. name match ; Do NOT assemble this source if external crc32 routine from zlib gets used. ; ifndef USE_ZLIB ifdef DEBUG VERBOSE_INFO EQU 1 else ifdef _AS_MSG_ VERBOSE_INFO EQU 1 else VERBOSE_INFO EQU 0 endif endif ifndef __SMALL__ ifndef __COMPACT__ ifndef __MEDIUM__ ifndef __LARGE__ ifndef __HUGE__ ; __SMALL__ EQU 1 endif endif endif endif endif ifdef __HUGE__ ; .MODEL Huge ifndef @CodeSize @CodeSize EQU 1 endif ifndef @DataSize @DataSize EQU 1 endif Save_DS EQU 1 if VERBOSE_INFO if1 %out Assembling for C, Huge memory model endif endif else ifdef __LARGE__ ; .MODEL Large ifndef @CodeSize @CodeSize EQU 1 endif ifndef @DataSize @DataSize EQU 1 endif if VERBOSE_INFO if1 %out Assembling for C, Large memory model endif endif else ifdef __COMPACT__ ; .MODEL Compact ifndef @CodeSize @CodeSize EQU 0 endif ifndef @DataSize @DataSize EQU 1 endif if VERBOSE_INFO if1 %out Assembling for C, Compact memory model endif endif else ifdef __MEDIUM__ ; .MODEL Medium ifndef @CodeSize @CodeSize EQU 1 endif ifndef @DataSize @DataSize EQU 0 endif if VERBOSE_INFO if1 %out Assembling for C, Medium memory model endif endif else ; .MODEL Small ifndef @CodeSize @CodeSize EQU 0 endif ifndef @DataSize @DataSize EQU 0 endif if VERBOSE_INFO if1 %out Assembling for C, Small memory model endif endif endif endif endif endif if @CodeSize LCOD_OFS EQU 2 else LCOD_OFS EQU 0 endif IF @DataSize LDAT_OFS EQU 2 else LDAT_OFS EQU 0 endif ifdef Save_DS ; (di,si,ds)+(size, return address) SAVE_REGS EQU 6+(4+LCOD_OFS) else ; (di,si)+(size, return address) SAVE_REGS EQU 4+(4+LCOD_OFS) endif ; ; Selection of the supported CPU instruction set and initialization ; of CPU type related macros: ; ifdef __586 Use_286_code EQU 1 Align_Size EQU 16 ; paragraph alignment on Pentium Alig_PARA EQU 1 ; paragraph aligned code segment else ifdef __486 Use_286_code EQU 1 Align_Size EQU 4 ; dword alignment on 32 bit processors Alig_PARA EQU 1 ; paragraph aligned code segment else ifdef __386 Use_286_code EQU 1 Align_Size EQU 4 ; dword alignment on 32 bit processors Alig_PARA EQU 1 ; paragraph aligned code segment else ifdef __286 Use_286_code EQU 1 Align_Size EQU 2 ; word alignment on 16 bit processors Alig_PARA EQU 0 ; word aligned code segment else ifdef __186 Use_186_code EQU 1 Align_Size EQU 2 ; word alignment on 16 bit processors Alig_PARA EQU 0 ; word aligned code segment else Align_Size EQU 2 ; word alignment on 16 bit processors Alig_PARA EQU 0 ; word aligned code segment endif ;?__186 endif ;?__286 endif ;?__386 endif ;?__486 endif ;?__586 ifdef Use_286_code .286 Have_80x86 EQU 1 else ifdef Use_186_code .186 Have_80x86 EQU 1 else .8086 Have_80x86 EQU 0 endif ;?Use_186_code endif ;?Use_286_code ifndef DYN_ALLOC extrn _prev : word extrn _window : byte prev equ _prev ; offset part window equ _window endif _DATA segment word public 'DATA' extrn _nice_match : word extrn _match_start : word extrn _prev_length : word extrn _good_match : word extrn _strstart : word extrn _max_chain_length : word ifdef DYN_ALLOC extrn _prev : word extrn _window : word prev equ 0 ; offset forced to zero window equ 0 window_seg equ _window[2] window_off equ 0 else wseg dw seg _window window_seg equ wseg window_off equ offset _window endif _DATA ends DGROUP group _DATA if @CodeSize if Alig_PARA MATCH_TEXT SEGMENT PARA PUBLIC 'CODE' else MATCH_TEXT SEGMENT WORD PUBLIC 'CODE' endif assume cs: MATCH_TEXT, ds: DGROUP else ;!@CodeSize if Alig_PARA _TEXT segment para public 'CODE' else _TEXT segment word public 'CODE' endif assume cs: _TEXT, ds: DGROUP endif ;?@CodeSize public _match_init public _longest_match ifndef WSIZE WSIZE equ 32768 ; keep in sync with zip.h ! endif MIN_MATCH equ 3 MAX_MATCH equ 258 MIN_LOOKAHEAD equ (MAX_MATCH+MIN_MATCH+1) MAX_DIST equ (WSIZE-MIN_LOOKAHEAD) ifdef DYN_ALLOC ifdef SS_NEQ_DS prev_ptr dw seg _prev ; pointer to the prev array endif else prev_ptr dw seg _prev ; pointer to the prev array endif ifdef SS_NEQ_DS match_start dw 0 ; copy of _match_start if SS != DS nice_match dw 0 ; copy of _nice_match if SS != DS endif ; initialize or check the variables used in match.asm. if @CodeSize _match_init proc far ; 'proc far' for large model else _match_init proc near ; 'proc near' for compact model endif ifdef SS_NEQ_DS ma_start equ cs:match_start ; does not work on OS/2 nice equ cs:nice_match else assume ss: DGROUP ma_start equ ss:_match_start nice equ ss:_nice_match ifndef NO_SECURE_TESTS mov ax,ds mov bx,ss cmp ax,bx ; SS == DS? jne fatal_err endif endif ifdef DYN_ALLOC ifndef NO_SECURE_TESTS cmp _prev[0],0 ; verify zero offset jne fatal_err cmp _window[0],0 jne fatal_err endif ifdef SS_NEQ_DS mov ax,_prev[2] ; segment value mov cs:prev_ptr,ax ; ugly write to code, crash on OS/2 prev_seg equ cs:prev_ptr else prev_seg equ ss:_prev[2] ; works on OS/2 if SS == DS endif else prev_seg equ cs:prev_ptr endif ret ifndef NO_SECURE_TESTS if @CodeSize extrn _exit : far ; 'far' for large model else extrn _exit : near ; 'near' for compact model endif fatal_err: ; (quiet) emergency stop: call _exit ; incompatible "global vars interface" endif _match_init endp ; ----------------------------------------------------------------------- ; Set match_start to the longest match starting at the given string and ; return its length. Matches shorter or equal to prev_length are discarded, ; in which case the result is equal to prev_length and match_start is ; garbage. ; IN assertions: cur_match is the head of the hash chain for the current ; string (strstart) and its distance is <= MAX_DIST, and prev_length >= 1 ; int longest_match(cur_match) align Align_Size if @CodeSize _longest_match proc far ; 'proc far' for large model else _longest_match proc near ; 'proc near' for compact model endif push bp mov bp,sp push di push si push ds if @CodeSize cur_match equ word ptr [bp+6] ; [bp+6] for large model else cur_match equ word ptr [bp+4] ; [bp+4] for compact model endif ; window equ es:window (es:0 for DYN_ALLOC) ; prev equ ds:prev ; match equ es:si ; scan equ es:di ; chain_length equ bp ; best_len equ bx ; limit equ dx mov si,cur_match ; use bp before it is destroyed ifdef SS_NEQ_DS mov ax,_nice_match mov nice,ax ; ugly write to code, crash on OS/2 endif mov dx,_strstart mov bp,_max_chain_length ; chain_length = max_chain_length mov di,dx sub dx,MAX_DIST ; limit = strstart-MAX_DIST cld ; string ops increment si and di jae limit_ok sub dx,dx ; limit = NIL limit_ok: add di,2+window_off ; di = offset(window + strstart + 2) mov bx,_prev_length ; best_len = prev_length mov es,window_seg mov ax,es:[bx+di-3] ; ax = scan[best_len-1..best_len] mov cx,es:[di-2] ; cx = scan[0..1] cmp bx,_good_match ; do we have a good match already? mov ds,prev_seg ; (does not destroy the flags) assume ds: nothing jb do_scan ; good match? if Have_80x86 shr bp,2 ; chain_length >>= 2 else shr bp,1 ; chain_length >>= 2 shr bp,1 endif jmp short do_scan align Align_Size ; align destination of branch long_loop: ; at this point, ds:di == scan+2, ds:si == cur_match mov ax,[bx+di-3] ; ax = scan[best_len-1..best_len] mov cx,[di-2] ; cx = scan[0..1] mov ds,prev_seg ; reset ds to address the prev array short_loop: ; at this point, di == scan+2, si = cur_match, ; ax = scan[best_len-1..best_len] and cx = scan[0..1] if (WSIZE-32768) and si,WSIZE-1 ; not needed if WSIZE=32768 endif shl si,1 ; cur_match as word index dec bp ; --chain_length mov si,prev[si] ; cur_match = prev[cur_match] jz the_end cmp si,dx ; cur_match <= limit ? jbe the_end do_scan: cmp ax,word ptr es:window[bx+si-1] ; check match at best_len-1 jne short_loop cmp cx,word ptr es:window[si] ; check min_match_length match jne short_loop mov cx,es add si,2+window_off ; si = match mov ds,cx ; ds = es = window mov cx,(MAX_MATCH-2)/2 ; scan for at most MAX_MATCH bytes mov ax,di ; ax = scan+2 repe cmpsw ; loop until mismatch je maxmatch ; match of length MAX_MATCH? mismatch: mov cl,[di-2] ; mismatch on first or second byte? xchg ax,di ; di = scan+2, ax = end of scan sub cl,[si-2] ; cl = 0 if first bytes equal sub ax,di ; ax = len sub si,2+window_off ; si = cur_match + len sub si,ax ; si = cur_match sub cl,1 ; set carry if cl == 0 (can't use DEC) adc ax,0 ; ax = carry ? len+1 : len cmp ax,bx ; len > best_len ? jle long_loop mov ma_start,si ; match_start = cur_match mov bx,ax ; bx = best_len = len cmp ax,nice ; len >= nice_match ? jl long_loop the_end: pop ds assume ds: DGROUP ifdef SS_NEQ_DS mov ax,ma_start ; garbage if no match found mov ds:_match_start,ax endif pop si pop di pop bp mov ax,bx ; result = ax = best_len ret maxmatch: ; come here if maximum match cmpsb ; increment si and di jmp mismatch ; force match_length = MAX_LENGTH _longest_match endp if @CodeSize MATCH_TEXT ENDS else _TEXT ENDS endif ; endif ;!USE_ZLIB ; end zip30/msdos/msdos.c0100644000076400000060000010173310274065322012405 0ustar edisk/* Copyright (c) 1990-2005 Info-ZIP. All rights reserved. See the accompanying file LICENSE, version 2005-Feb-10 or later (the contents of which are also included in zip.h) for terms of use. If, for some reason, all these files are missing, the Info-ZIP license also may be found at: ftp://ftp.info-zip.org/pub/infozip/license.html */ #include "zip.h" #ifndef UTIL /* little or no material in this file is used by UTIL */ #include #include #if defined(__GO32__) || defined(__TURBOC__) # include /* prototypes of find*() */ typedef struct ffblk ff_dir; # define FATTR (hidden_files ? FA_HIDDEN+FA_SYSTEM+FA_DIREC : FA_DIREC) # define FFIRST(n,d,a) findfirst(n,(struct ffblk *)d,a) # define FNEXT(d) findnext((struct ffblk *)d) # if (defined(__TURBOC__) || (defined(__DJGPP__) && (__DJGPP__ >=2))) # if (defined(__DJGPP__) && (__DJGPP__ == 2) && (__DJGPP_MINOR__ == 0)) # include # endif # define GetFileMode(name) _chmod(name, 0) # define SetFileMode(name, attr) _chmod(name, 1, attr) # else /* DJGPP v1.x */ # define GetFileMode(name) bdosptr(0x43, (name), 0) # endif #endif /* __GO32__ || __TURBOC__ */ #if defined(MSC) || defined(__WATCOMC__) typedef struct find_t ff_dir; # define FATTR (hidden_files ? _A_HIDDEN+_A_SYSTEM+_A_SUBDIR : _A_SUBDIR) # ifndef FA_LABEL # define FA_LABEL _A_VOLID # endif # define FFIRST(n,d,a) _dos_findfirst(n,a,(struct find_t *)d) # define FNEXT(d) _dos_findnext((struct find_t *)d) # define ff_name name # define ff_fdate wr_date # define ff_ftime wr_time # define ff_attrib attrib #endif /* MSC || __WATCOMC__ */ #ifdef __EMX__ # ifdef EMX_OBSOLETE /* emx 0.9b or earlier */ # define size_t xxx_size_t # define wchar_t xxx_wchar_t # define tm xxx_tm # include # undef size_t # undef wchar_t # undef tm # else /* !EMX_OBSOLETE */ /* emx 0.9c or newer */ # include # endif /* ?EMX_OBSOLETE */ typedef struct _find ff_dir; # define FATTR (hidden_files ? _A_HIDDEN+_A_SYSTEM+_A_SUBDIR : _A_SUBDIR) # define FA_LABEL _A_VOLID # define FFIRST(n,d,a) __findfirst(n,a,d) # define FNEXT(d) __findnext(d) # define ff_name name # define ff_fdate date # define ff_ftime time # define ff_attrib attr # define GetFileMode(name) __chmod(name, 0, 0) # define SetFileMode(name, attr) __chmod(name, 1, attr) #endif /* __EMX__ */ #ifndef SetFileMode # define SetFileMode(name, attr) _dos_setfileattr(name, attr) #endif #define PAD 0 #define PATH_END '/' /* Library functions not in (most) header files */ int rmdir OF((const char *)); int utime OF((char *, ztimbuf *)); /* Local functions */ #ifndef GetFileMode int GetFileMode OF((char *name)); #endif /* !GetFileMode */ local int initDirSearch OF((char *name, ff_dir *ff_context_p)); local char *getVolumeLabel OF((int, ulg *, ulg *, time_t *)); local int wild_recurse OF((char *, char *)); local int procname_dos OF((char *n, int caseflag, unsigned attribs)); local int is_running_on_windows OF((void)); #define MSDOS_INVALID_ATTR 0xFF #define getDirEntryAttr(d) ((d)->ff_attrib) /* Module level variables */ extern char *label; local ulg label_time = 0; local ulg label_mode = 0; local time_t label_utim = 0; /* Module level constants */ local ZCONST char wild_match_all[] = "*.*"; #ifndef GetFileMode int GetFileMode(char *name) { unsigned int attr = 0; return (_dos_getfileattr(name, &attr) ? -1 : attr); } #endif /* !GetFileMode */ local int initDirSearch(name, ff_context_p) char *name; /* name of directory to scan */ ff_dir *ff_context_p; /* pointer to FFIRST/FNEXT context structure */ { int r; /* FFIRST return value */ char *p, *q; /* temporary copy of name, and aux pointer */ if ((p = malloc(strlen(name) + (2 + sizeof(wild_match_all)))) == NULL) return ZE_MEM; strcpy(p, name); q = p + strlen(p); if (q[-1] == ':') *q++ = '.'; if ((q - p) > 0 && *(q - 1) != '/') *q++ = '/'; strcpy(q, wild_match_all); r = FFIRST(p, ff_context_p, FATTR); free((zvoid *)p); return (r ? ZE_MISS : ZE_OK); } local char *getVolumeLabel(drive, vtime, vmode, vutim) int drive; /* drive name: 'A' .. 'Z' or '\0' for current drive */ ulg *vtime; /* volume label creation time (DOS format) */ ulg *vmode; /* volume label file mode */ time_t *vutim;/* volume label creation time (UNIX format) */ /* If a volume label exists for the given drive, return its name and set its time and mode. The returned name must be static data. */ { static char vol[14]; ff_dir d; char *p; if (drive) { vol[0] = (char)drive; strcpy(vol+1, ":/"); } else { strcpy(vol, "/"); } strcat(vol, wild_match_all); if (FFIRST(vol, &d, FA_LABEL) == 0) { strncpy(vol, d.ff_name, sizeof(vol)-1); vol[sizeof(vol)-1] = '\0'; /* just in case */ if ((p = strchr(vol, '.')) != NULL) /* remove dot, though PKZIP doesn't */ strcpy(p, p + 1); *vtime = ((ulg)d.ff_fdate << 16) | ((ulg)d.ff_ftime & 0xffff); *vmode = (ulg)d.ff_attrib; *vutim = dos2unixtime(*vtime); return vol; } return NULL; } #ifdef MSDOS16 #define ONENAMELEN 12 /* no 16-bit compilers supports LFN */ #else #define ONENAMELEN 255 #endif /* whole is a pathname with wildcards, wildtail points somewhere in the */ /* middle of it. All wildcards to be expanded must come AFTER wildtail. */ local int wild_recurse(whole, wildtail) char *whole; char *wildtail; { ff_dir dir; char *subwild, *name, *newwhole = NULL, *glue = NULL, plug = 0, plug2; ush newlen, amatch = 0; int e = ZE_MISS; if (!isshexp(wildtail)) { struct stat s; /* dummy buffer for stat() */ if (!LSSTAT(whole, &s)) /* file exists ? */ return procname(whole, 0); else return ZE_MISS; /* woops, no wildcards! */ } /* back up thru path components till existing dir found */ do { name = wildtail + strlen(wildtail) - 1; for (;;) if (name-- <= wildtail || *name == PATH_END) { subwild = name + 1; plug2 = *subwild; *subwild = 0; break; } if (glue) *glue = plug; glue = subwild; plug = plug2; e = initDirSearch(whole, &dir); } while (e == ZE_MISS && subwild > wildtail); wildtail = subwild; /* skip past non-wild components */ if (e != ZE_OK) { if (glue) *glue = plug; goto ohforgetit; } subwild = strchr(wildtail + 1, PATH_END); /* this "+ 1" dodges the ^^^ hole left by *glue == 0 */ if (subwild != NULL) { *(subwild++) = 0; /* wildtail = one component pattern */ newlen = strlen(whole) + strlen(subwild) + (ONENAMELEN + 2); } else newlen = strlen(whole) + (ONENAMELEN + 1); if ((newwhole = malloc(newlen)) == NULL) { if (glue) *glue = plug; e = ZE_MEM; goto ohforgetit; } strcpy(newwhole, whole); newlen = strlen(newwhole); if (glue) *glue = plug; /* repair damage to whole */ if (!isshexp(wildtail)) { e = ZE_MISS; /* non-wild name not found */ goto ohforgetit; } do { if (strcmp(dir.ff_name, ".") && strcmp(dir.ff_name, "..") && MATCH(wildtail, dir.ff_name, 0)) { strcpy(newwhole + newlen, dir.ff_name); if (subwild) { name = newwhole + strlen(newwhole); *(name++) = PATH_END; strcpy(name, subwild); e = wild_recurse(newwhole, name); } else e = procname_dos(newwhole, 0, getDirEntryAttr(&dir)); newwhole[newlen] = 0; if (e == ZE_OK) amatch = 1; else if (e != ZE_MISS) break; } } while (FNEXT(&dir) == 0); ohforgetit: if (subwild) *--subwild = PATH_END; if (newwhole) free(newwhole); if (e == ZE_MISS && amatch) e = ZE_OK; return e; } int wild(w) char *w; /* path/pattern to match */ /* If not in exclude mode, expand the pattern based on the contents of the file system. Return an error code in the ZE_ class. */ { char *p; /* path */ char *q; /* diskless path */ int e; /* result */ if (volume_label == 1) { volume_label = 2; label = getVolumeLabel((w != NULL && w[1] == ':') ? to_up(w[0]) : '\0', &label_time, &label_mode, &label_utim); if (label != NULL) (void)newname(label, 0, 0); if (w == NULL || (w[1] == ':' && w[2] == '\0')) return ZE_OK; /* "zip -$ foo a:" can be used to force drive name */ } /* special handling of stdin request */ if (strcmp(w, "-") == 0) /* if compressing stdin */ return newname(w, 0, 0); /* Allocate and copy pattern, leaving room to add "." if needed */ if ((p = malloc(strlen(w) + 2)) == NULL) return ZE_MEM; strcpy(p, w); /* Normalize path delimiter as '/' */ for (q = p; *q; q++) /* use / consistently */ if (*q == '\\') *q = '/'; /* Separate the disk part of the path */ q = strchr(p, ':'); if (q != NULL) { if (strchr(++q, ':')) /* sanity check for safety of wild_recurse */ return ZE_MISS; } else q = p; /* Normalize bare disk names */ if (q > p && !*q) strcpy(q, "."); /* Here we go */ e = wild_recurse(p, q); free((zvoid *)p); return e; } local int procname_dos(n, caseflag, attribs) char *n; /* name to process */ int caseflag; /* true to force case-sensitive match */ unsigned attribs; /* file attributes, if available */ /* Process a name or sh expression to operate on (or exclude). Return an error code in the ZE_ class. */ { char *a; /* path and name for recursion */ ff_dir *d; /* control structure for FFIRST/FNEXT */ char *e; /* pointer to name from readd() */ int m; /* matched flag */ int ff_status; /* return value of FFIRST/FNEXT */ char *p; /* path for recursion */ struct stat s; /* result of stat() */ struct zlist far *z; /* steps through zfiles list */ if (n == NULL) /* volume_label request in freshen|delete mode ?? */ return ZE_OK; if (strcmp(n, "-") == 0) /* if compressing stdin */ return newname(n, 0, caseflag); else if (*n == '\0') return ZE_MISS; else if (attribs != MSDOS_INVALID_ATTR) { /* Avoid calling stat() for performance reasons when it is already known (from a previous directory scan) that the passed name corresponds to a "real existing" file. The only information needed further down in this function is the distinction between directory entries and other (typically normal file) entries. This distinction can be derived from the file's attributes that the directory lookup has already provided "for free". */ s.st_mode = ((attribs & MSDOS_DIR_ATTR) ? S_IFDIR : S_IFREG); } else if (LSSTAT(n, &s) #ifdef __TURBOC__ /* For this compiler, stat() succeeds on wild card names! */ || isshexp(n) #endif ) { /* Not a file or directory--search for shell expression in zip file */ if (caseflag) { p = malloc(strlen(n) + 1); if (p != NULL) strcpy(p, n); } else p = ex2in(n, 0, (int *)NULL); /* shouldn't affect matching chars */ m = 1; for (z = zfiles; z != NULL; z = z->nxt) { if (MATCH(p, z->iname, caseflag)) { z->mark = pcount ? filter(z->zname, caseflag) : 1; if (z->mark) z->dosflag = 1; /* force DOS attribs for incl. names */ if (verbose) fprintf(mesg, "zip diagnostic: %scluding %s\n", z->mark ? "in" : "ex", z->name); m = 0; } } free((zvoid *)p); return m ? ZE_MISS : ZE_OK; } /* Live name--use if file, recurse if directory */ for (p = n; *p; p++) /* use / consistently */ if (*p == '\\') *p = '/'; if ((s.st_mode & S_IFDIR) == 0) { /* add or remove name of file */ if ((m = newname(n, 0, caseflag)) != ZE_OK) return m; } else { /* Add trailing / to the directory name */ if ((p = malloc(strlen(n)+2)) == NULL) return ZE_MEM; if (strcmp(n, ".") == 0 || strcmp(n, "/.") == 0) { *p = '\0'; /* avoid "./" prefix and do not create zip entry */ } else { strcpy(p, n); a = p + strlen(p); if (a[-1] != '/') strcpy(a, "/"); if (dirnames && (m = newname(p, 1, caseflag)) != ZE_OK) { free((zvoid *)p); return m; } } /* recurse into directory */ if (recurse) { if ((d = malloc(sizeof(ff_dir))) == NULL || (m = initDirSearch(n, d)) == ZE_MEM) { if (d != NULL) free((zvoid *)d); free((zvoid *)p); return ZE_MEM; } for (e = d->ff_name, ff_status = m; ff_status == 0; ff_status = FNEXT(d)) { if (strcmp(e, ".") && strcmp(e, "..")) { if ((a = malloc(strlen(p) + strlen(e) + 1)) == NULL) { free((zvoid *)d); free((zvoid *)p); return ZE_MEM; } strcat(strcpy(a, p), e); if ((m = procname_dos(a, caseflag, getDirEntryAttr(d))) != ZE_OK) /* recurse on name */ { if (m == ZE_MISS) zipwarn("name not matched: ", a); else ziperr(m, a); } free((zvoid *)a); } } free((zvoid *)d); } free((zvoid *)p); } /* (s.st_mode & S_IFDIR) == 0) */ return ZE_OK; } int procname(n, caseflag) char *n; /* name to process */ int caseflag; /* true to force case-sensitive match */ { return procname_dos(n, caseflag, MSDOS_INVALID_ATTR); } char *ex2in(x, isdir, pdosflag) char *x; /* external file name */ int isdir; /* input: x is a directory */ int *pdosflag; /* output: force MSDOS file attributes? */ /* Convert the external file name to a zip file name, returning the malloc'ed string or NULL if not enough memory. */ { char *n; /* internal file name (malloc'ed) */ char *t; /* shortened name */ int dosflag; dosflag = 1; /* Find starting point in name before doing malloc */ /* Strip drive specification */ t = *x && *(x + 1) == ':' ? x + 2 : x; /* Strip "//host/share/" part of a UNC name */ if ((!strncmp(x,"//",2) || !strncmp(x,"\\\\",2)) && (x[2] != '\0' && x[2] != '/' && x[2] != '\\')) { n = x + 2; while (*n != '\0' && *n != '/' && *n != '\\') n++; /* strip host name */ if (*n != '\0') { n++; while (*n != '\0' && *n != '/' && *n != '\\') n++; /* strip `share' name */ } if (*n != '\0') t = n + 1; } /* Strip leading "/" to convert an absolute path into a relative path */ while (*t == '/' || *t == '\\') t++; /* Skip leading "./" as well */ while (*t == '.' && (t[1] == '/' || t[1] == '\\')) t += 2; /* Make changes, if any, to the copied name (leave original intact) */ for (n = t; *n; n++) if (*n == '\\') *n = '/'; if (!pathput) t = last(t, PATH_END); /* Malloc space for internal name and copy it */ if ((n = malloc(strlen(t) + 1)) == NULL) return NULL; strcpy(n, t); if (isdir == 42) return n; /* avoid warning on unused variable */ if (dosify) msname(n); else #if defined(__DJGPP__) && __DJGPP__ >= 2 if (_USE_LFN == 0) #endif strlwr(n); if (pdosflag) *pdosflag = dosflag; return n; } char *in2ex(n) char *n; /* internal file name */ /* Convert the zip file name to an external file name, returning the malloc'ed string or NULL if not enough memory. */ { char *x; /* external file name */ if ((x = malloc(strlen(n) + 1 + PAD)) == NULL) return NULL; strcpy(x, n); return x; } void stamp(f, d) char *f; /* name of file to change */ ulg d; /* dos-style time to change it to */ /* Set last updated and accessed time of file f to the DOS time d. */ { #if defined(__TURBOC__) || defined(__GO32__) int h; /* file handle */ if ((h = open(f, 0)) != -1) { setftime(h, (struct ftime *)(void *)&d); close(h); } #else /* !__TURBOC__ && !__GO32__ */ ztimbuf u; /* argument for utime() */ /* Convert DOS time to time_t format in u.actime and u.modtime */ u.actime = u.modtime = dos2unixtime(d); /* Set updated and accessed times of f */ utime(f, &u); #endif /* ?(__TURBOC__ || __GO32__) */ } ulg filetime(f, a, n, t) char *f; /* name of file to get info on */ ulg *a; /* return value: file attributes */ long *n; /* return value: file size */ iztimes *t; /* return value: access, modific. and creation times */ /* If file *f does not exist, return 0. Else, return the file's last modified date and time as an MSDOS date and time. The date and time is returned in a long with the date most significant to allow unsigned integer comparison of absolute times. Also, if a is not a NULL pointer, store the file attributes there, with the high two bytes being the Unix attributes, and the low byte being a mapping of that to DOS attributes. If n is not NULL, store the file size there. If t is not NULL, the file's access, modification and creation times are stored there as UNIX time_t values. If f is "-", use standard input as the file. If f is a device, return a file size of -1 */ { struct stat s; /* results of stat() */ /* convert FNMAX to malloc - 11/8/04 EG */ char *name; int len = strlen(f); int isstdin = !strcmp(f, "-"); if (f == label) { if (a != NULL) *a = label_mode; if (n != NULL) *n = -2L; /* convention for a label name */ if (t != NULL) t->atime = t->mtime = t->ctime = label_utim; return label_time; } if ((name = malloc(len + 1)) == NULL) { ZIPERR(ZE_MEM, "filetime"); } strcpy(name, f); if (name[len - 1] == '/') name[len - 1] = '\0'; /* not all systems allow stat'ing a file with / appended */ if (isstdin) { if (fstat(fileno(stdin), &s) != 0) { free(name); error("fstat(stdin)"); } time((time_t *)&s.st_mtime); /* some fstat()s return time zero */ } else if (LSSTAT(name, &s) != 0) { /* Accept about any file kind including directories * (stored with trailing / with -r option) */ free(name); return 0; } if (a != NULL) { *a = ((ulg)s.st_mode << 16) | (isstdin ? 0L : (ulg)GetFileMode(name)); #if (S_IFREG != 0x8000) /* kludge to work around non-standard S_IFREG flag used in DJGPP V2.x */ if ((s.st_mode & S_IFMT) == S_IFREG) *a |= 0x80000000L; #endif } free(name); if (n != NULL) *n = (s.st_mode & S_IFMT) == S_IFREG ? s.st_size : -1L; if (t != NULL) { t->atime = s.st_atime; t->mtime = s.st_mtime; t->ctime = s.st_ctime; } return unix2dostime((time_t *)&s.st_mtime); } int deletedir(d) char *d; /* directory to delete */ /* Delete the directory *d if it is empty, do nothing otherwise. Return the result of rmdir(), delete(), or system(). */ { return rmdir(d); } int set_extra_field(z, z_utim) struct zlist far *z; iztimes *z_utim; /* create extra field and change z->att if desired */ { #ifdef USE_EF_UT_TIME #ifdef IZ_CHECK_TZ if (!zp_tz_is_valid) return ZE_OK; /* skip silently if no valid TZ info */ #endif if ((z->extra = (char *)malloc(EB_HEADSIZE+EB_UT_LEN(1))) == NULL) return ZE_MEM; z->extra[0] = 'U'; z->extra[1] = 'T'; z->extra[2] = EB_UT_LEN(1); /* length of data part of e.f. */ z->extra[3] = 0; z->extra[4] = EB_UT_FL_MTIME; z->extra[5] = (char)(z_utim->mtime); z->extra[6] = (char)(z_utim->mtime >> 8); z->extra[7] = (char)(z_utim->mtime >> 16); z->extra[8] = (char)(z_utim->mtime >> 24); z->cext = z->ext = (EB_HEADSIZE+EB_UT_LEN(1)); z->cextra = z->extra; return ZE_OK; #else /* !USE_EF_UT_TIME */ return (int)(z-z); #endif /* ?USE_EF_UT_TIME */ } #ifdef MY_ZCALLOC /* Special zcalloc function for MEMORY16 (MSDOS/OS2) */ #if defined(__TURBOC__) && !defined(OS2) /* Small and medium model are for now limited to near allocation with * reduced MAX_WBITS and MAX_MEM_LEVEL */ /* Turbo C malloc() does not allow dynamic allocation of 64K bytes * and farmalloc(64K) returns a pointer with an offset of 8, so we * must fix the pointer. Warning: the pointer must be put back to its * original form in order to free it, use zcfree(). */ #define MAX_PTR 10 /* 10*64K = 640K */ local int next_ptr = 0; typedef struct ptr_table_s { zvoid far *org_ptr; zvoid far *new_ptr; } ptr_table; local ptr_table table[MAX_PTR]; /* This table is used to remember the original form of pointers * to large buffers (64K). Such pointers are normalized with a zero offset. * Since MSDOS is not a preemptive multitasking OS, this table is not * protected from concurrent access. This hack doesn't work anyway on * a protected system like OS/2. Use Microsoft C instead. */ zvoid far *zcalloc (unsigned items, unsigned size) { zvoid far *buf; ulg bsize = (ulg)items*size; if (bsize < (65536L-16L)) { buf = farmalloc(bsize); if (*(ush*)&buf != 0) return buf; } else { buf = farmalloc(bsize + 16L); } if (buf == NULL || next_ptr >= MAX_PTR) return NULL; table[next_ptr].org_ptr = buf; /* Normalize the pointer to seg:0 */ *((ush*)&buf+1) += ((ush)((uch*)buf-NULL) + 15) >> 4; *(ush*)&buf = 0; table[next_ptr++].new_ptr = buf; return buf; } zvoid zcfree (zvoid far *ptr) { int n; if (*(ush*)&ptr != 0) { /* object < 64K */ farfree(ptr); return; } /* Find the original pointer */ for (n = next_ptr - 1; n >= 0; n--) { if (ptr != table[n].new_ptr) continue; farfree(table[n].org_ptr); while (++n < next_ptr) { table[n-1] = table[n]; } next_ptr--; return; } ziperr(ZE_MEM, "zcfree: ptr not found"); } #endif /* __TURBOC__ */ #if defined(MSC) || defined(__WATCOMC__) #if (!defined(_MSC_VER) || (_MSC_VER < 700)) # define _halloc halloc # define _hfree hfree #endif zvoid far *zcalloc (unsigned items, unsigned size) { return (zvoid far *)_halloc((long)items, size); } zvoid zcfree (zvoid far *ptr) { _hfree((void huge *)ptr); } #endif /* MSC || __WATCOMC__ */ #endif /* MY_ZCALLOC */ #if (defined(__WATCOMC__) && defined(ASMV) && !defined(__386__)) /* This is a hack to connect "call _exit" in match.asm to exit() */ #pragma aux xit "_exit" parm caller [] void xit(void) { exit(20); } #endif local int is_running_on_windows(void) { char * var = getenv("OS"); /* if the OS env.var says 'Windows_NT' then */ /* we're likely running on a variant of WinNT */ if ((NULL != var) && (0 == strcmp("Windows_NT", var))) { return 1; } /* if the windir env.var is non-null then */ /* we're likely running on a variant of Win9x */ /* DOS mode of Win9x doesn't define windir, only winbootdir */ /* NT's command.com can't see lowercase env. vars */ var = getenv("windir"); if ((NULL != var) && (0 != var[0])) { return 1; } return 0; } void check_for_windows(char *app) { /* Print a warning for users running under Windows */ /* to reduce bug reports due to running DOS version */ /* under Windows, when Windows version usually works correctly */ /* This is only called from the DOS version */ if (is_running_on_windows()) { printf("\nzip warning: You are running MSDOS %s on Windows.\n" "Try the Windows version before reporting any problems.\n", app); } } #endif /* !UTIL */ #ifndef WINDLL /******************************/ /* Function version_local() */ /******************************/ static ZCONST char CompiledWith[] = "Compiled with %s%s for %s%s%s.\n\n"; /* At module level to keep Turbo C++ 1.0 happy !! */ void version_local() { #if defined(__DJGPP__) || defined(__WATCOMC__) || \ (defined(_MSC_VER) && (_MSC_VER != 800)) char buf[80]; #endif /* Define the compiler name and version strings */ #if defined(__GNUC__) # if defined(__DJGPP__) sprintf(buf, "djgpp v%d.%02d / gcc ", __DJGPP__, __DJGPP_MINOR__); # define COMPILER_NAME1 buf # elif defined(__GO32__) /* __GO32__ is defined as "1" only (sigh) */ # define COMPILER_NAME1 "djgpp v1.x / gcc " # elif defined(__EMX__) /* ...so is __EMX__ (double sigh) */ # define COMPILER_NAME1 "emx+gcc " # else # define COMPILER_NAME1 "gcc " # endif # define COMPILER_NAME2 __VERSION__ #elif defined(__WATCOMC__) # if (__WATCOMC__ % 10 > 0) /* We do this silly test because __WATCOMC__ gives two digits for the */ /* minor version, but Watcom packaging prefers to show only one digit. */ sprintf(buf, "Watcom C/C++ %d.%02d", __WATCOMC__ / 100, __WATCOMC__ % 100); # else sprintf(buf, "Watcom C/C++ %d.%d", __WATCOMC__ / 100, (__WATCOMC__ % 100) / 10); # endif # define COMPILER_NAME1 buf # define COMPILER_NAME2 "" #elif defined(__TURBOC__) # ifdef __BORLANDC__ # define COMPILER_NAME1 "Borland C++" # if (__BORLANDC__ < 0x0200) # define COMPILER_NAME2 " 1.0" # elif (__BORLANDC__ == 0x0200) /* James: __TURBOC__ = 0x0297 */ # define COMPILER_NAME2 " 2.0" # elif (__BORLANDC__ == 0x0400) # define COMPILER_NAME2 " 3.0" # elif (__BORLANDC__ == 0x0410) /* __BCPLUSPLUS__ = 0x0310 */ # define COMPILER_NAME2 " 3.1" # elif (__BORLANDC__ == 0x0452) /* __BCPLUSPLUS__ = 0x0320 */ # define COMPILER_NAME2 " 4.0 or 4.02" # elif (__BORLANDC__ == 0x0460) /* __BCPLUSPLUS__ = 0x0340 */ # define COMPILER_NAME2 " 4.5" # elif (__BORLANDC__ == 0x0500) /* __TURBOC__ = 0x0500 */ # define COMPILER_NAME2 " 5.0" # else # define COMPILER_NAME2 " later than 5.0" # endif # else # define COMPILER_NAME1 "Turbo C" # if (__TURBOC__ > 0x0401) # define COMPILER_NAME2 "++ later than 3.0" # elif (__TURBOC__ == 0x0401) /* Kevin: 3.0 -> 0x0401 */ # define COMPILER_NAME2 "++ 3.0" # elif (__TURBOC__ == 0x0296) /* [662] checked by SPC */ # define COMPILER_NAME2 "++ 1.01" # elif (__TURBOC__ == 0x0295) /* [661] vfy'd by Kevin */ # define COMPILER_NAME2 "++ 1.0" # elif (__TURBOC__ == 0x0201) /* Brian: 2.01 -> 0x0201 */ # define COMPILER_NAME2 " 2.01" # elif ((__TURBOC__ >= 0x018d) && (__TURBOC__ <= 0x0200)) /* James: 0x0200 */ # define COMPILER_NAME2 " 2.0" # elif (__TURBOC__ > 0x0100) # define COMPILER_NAME2 " 1.5" /* James: 0x0105? */ # else # define COMPILER_NAME2 " 1.0" /* James: 0x0100 */ # endif # endif #elif defined(MSC) # if defined(_QC) && !defined(_MSC_VER) # define COMPILER_NAME1 "Microsoft Quick C" # define COMPILER_NAME2 "" /* _QC is defined as 1 */ # else # define COMPILER_NAME1 "Microsoft C " # ifdef _MSC_VER # if (_MSC_VER == 800) # define COMPILER_NAME2 "8.0/8.0c (Visual C++ 1.0/1.5)" # else # define COMPILER_NAME2 \ (sprintf(buf, "%d.%02d", _MSC_VER/100, _MSC_VER%100), buf) # endif # else # define COMPILER_NAME2 "5.1 or earlier" # endif # endif #else # define COMPILER_NAME1 "unknown compiler" # define COMPILER_NAME2 "" #endif /* Define the OS name and memory environment strings */ #if defined(__WATCOMC__) || defined(__TURBOC__) || defined(MSC) || \ defined(__GNUC__) # define OS_NAME1 "\nMS-DOS" #else # define OS_NAME1 "MS-DOS" #endif #if (defined(__GNUC__) || (defined(__WATCOMC__) && defined(__386__))) # define OS_NAME2 " (32-bit)" #elif defined(M_I86HM) || defined(__HUGE__) # define OS_NAME2 " (16-bit, huge)" #elif defined(M_I86LM) || defined(__LARGE__) # define OS_NAME2 " (16-bit, large)" #elif defined(M_I86MM) || defined(__MEDIUM__) # define OS_NAME2 " (16-bit, medium)" #elif defined(M_I86CM) || defined(__COMPACT__) # define OS_NAME2 " (16-bit, compact)" #elif defined(M_I86SM) || defined(__SMALL__) # define OS_NAME2 " (16-bit, small)" #elif defined(M_I86TM) || defined(__TINY__) # define OS_NAME2 " (16-bit, tiny)" #else # define OS_NAME2 " (16-bit)" #endif /* Define the compile date string */ #ifdef __DATE__ # define COMPILE_DATE " on " __DATE__ #else # define COMPILE_DATE "" #endif printf(CompiledWith, COMPILER_NAME1, COMPILER_NAME2, OS_NAME1, OS_NAME2, COMPILE_DATE); } /* end function version_local() */ #endif /* !WINDLL */ #if 0 /* inserted here for future use (clearing of archive bits) */ #if (defined(__GO32__) && (!defined(__DJGPP__) || (__DJGPP__ < 2))) #include int volatile _doserrno; unsigned _dos_setfileattr(char *name, unsigned attr) { #if 0 /* stripping of trailing '/' is not needed for zip-internal use */ unsigned namlen = strlen(name); char *i_name = alloca(namlen + 1); strcpy(i_name, name); if (namlen > 1 && i_name[namlen-1] == '/' && i_name[namlen-2] != ':') i_name[namlen-1] = '\0'; asm("movl %0, %%edx": : "g" (i_name)); #else asm("movl %0, %%edx": : "g" (name)); #endif asm("movl %0, %%ecx": : "g" (attr)); asm("movl $0x4301, %eax"); asm("int $0x21": : : "%eax", "%ebx", "%ecx", "%edx", "%esi", "%edi"); _doserrno = 0; asm("jnc 1f"); asm("movl %%eax, %0": "=m" (_doserrno)); switch (_doserrno) { case 2: case 3: errno = ENOENT; break; case 5: errno = EACCES; break; } asm("1:"); return (unsigned)_doserrno; } #endif /* DJGPP v1.x */ #endif /* never (not yet used) */ #if (defined(__DJGPP__) && (__DJGPP__ >= 2)) /* Disable determination of "x" bit in st_mode field for [f]stat() calls. */ int _is_executable (const char *path, int fhandle, const char *ext) { return 0; } /* Prevent globbing of filenames. This gives the same functionality as * "stubedit globbing=no" did with DJGPP v1. */ #ifndef USE_DJGPP_GLOB char **__crt0_glob_function(char *_arg) { return NULL; } #endif /* Reduce the size of the executable and remove the functionality to read * the program's environment from whatever $DJGPP points to. */ #if !defined(USE_DJGPP_ENV) || defined(UTIL) void __crt0_load_environment_file(char *_app_name) { } #endif #endif /* __DJGPP__ >= 2 */ #if defined(_MSC_VER) && _MSC_VER == 700 /* * ARGH. MSC 7.0 libraries think times are based on 1899 Dec 31 00:00, not * 1970 Jan 1 00:00. So we have to diddle time_t's appropriately: add * 70 years' worth of seconds for localtime() wrapper function; * (70*365 regular days + 17 leap days + 1 1899 day) * 86400 == * (25550 + 17 + 1) * 86400 == 2209075200 seconds. * Let time() and stat() return seconds since 1970 by using our own * _dtoxtime() which is the routine that is called by these two functions. */ #ifdef UTIL # include #endif #ifndef UTIL #undef localtime struct tm *localtime(const time_t *); struct tm *msc7_localtime(const time_t *clock) { time_t t = *clock; t += 2209075200L; return localtime(&t); } #endif /* !UTIL */ void __tzset(void); int _isindst(struct tm *); extern int _days[]; /* Nonzero if `y' is a leap year, else zero. */ #define leap(y) (((y) % 4 == 0 && (y) % 100 != 0) || (y) % 400 == 0) /* Number of leap years from 1970 to `y' (not including `y' itself). */ #define nleap(y) (((y) - 1969) / 4 - ((y) - 1901) / 100 + ((y) - 1601) / 400) time_t _dtoxtime(year, month, mday, hour, min, sec) int year, month, mday, year, hour, min, sec; { struct tm tm; time_t t; int days; days = _days[month - 1] + mday; year += 1980; if (leap(year) && month > 2) ++days; tm.tm_yday = days; tm.tm_mon = month - 1; tm.tm_year = year - 1900; tm.tm_hour = hour; __tzset(); days += 365 * (year - 1970) + nleap (year); t = 86400L * days + 3600L * hour + 60 * min + sec + _timezone; if (_daylight && _isindst(&tm)) t -= 3600; return t; } #endif /* _MSC_VER && _MSC_VER == 700 */ #ifdef __WATCOMC__ /* This papers over a bug in Watcom 10.6's standard library... sigh */ /* Apparently it applies to both the DOS and Win32 stat()s. */ int stat_bandaid(const char *path, struct stat *buf) { char newname[4]; if (!stat(path, buf)) return 0; else if (!strcmp(path, ".") || (path[0] && !strcmp(path + 1, ":."))) { strcpy(newname, path); newname[strlen(path) - 1] = '\\'; /* stat(".") fails for root! */ return stat(newname, buf); } else return -1; } #endif zip30/msdos/osdep.h0100644000076400000060000001400111027613506012366 0ustar edisk/* Copyright (c) 1990-2008 Info-ZIP. All rights reserved. See the accompanying file LICENSE, version 2007-Mar-4 or later (the contents of which are also included in zip.h) for terms of use. If, for some reason, all these files are missing, the Info-ZIP license also may be found at: ftp://ftp.info-zip.org/pub/infozip/license.html */ /* The symbol DOS is used throughout the Zip source to identify code portions * specific to the MSDOS port. * Just to make sure, we check that it is set. * (Currently, this should should not be neccessary, since currently it has * to be set on the compiler command line to get this file read in.) */ #ifndef DOS # define DOS #endif /* The symbol MSDOS is consistently used in the generic source files * to identify code to support for MSDOS (and MSDOS related) stuff. * e.g: FAT or (FAT like) file systems, * '\\' as directory separator in paths, * "\r\n" as record (line) terminator in text files, ... * * IMPORTANT Note: * This symbol is not unique for the MSDOS port !!!!!! * It is also defined by ports to some other OS which are (to some extend) * considered DOS compatible. * Examples are: OS/2 (OS2), Windows NT and Windows 95 (WIN32). * */ #ifndef MSDOS # define MSDOS #endif /* Power C is similar to Turbo C */ #ifdef __POWERC # define __TURBOC__ #endif /* __POWERC */ /* Automatic setting of the common Microsoft C idenfifier MSC. * NOTE: Watcom also defines M_I*86 ! */ #if defined(_MSC_VER) || (defined(M_I86) && !defined(__WATCOMC__)) # ifndef MSC # define MSC /* This should work for older MSC, too! */ # endif #endif #if !defined(__GO32__) && !defined(__EMX__) # define NO_UNISTD_H #endif #if defined(__WATCOMC__) && defined(__386__) # define WATCOMC_386 #endif #ifdef WINDLL # define MSWIN # define MEMORY16 #endif #if !defined(__EMX__) && !defined(__GO32__) && !defined(WATCOMC_386) #if !defined(WINDLL) # define MSDOS16 /* 16 bit MSDOS only */ # define MEMORY16 #endif #endif #if !defined(NO_ASM) && !defined(ASMV) # define ASMV #endif /* enable creation of UTC time fields unless explicitely suppressed */ #if !defined(NO_EF_UT_TIME) && !defined(USE_EF_UT_TIME) # define USE_EF_UT_TIME #endif /* check that TZ environment variable is defined before using UTC times */ #if (!defined(NO_IZ_CHECK_TZ) && !defined(IZ_CHECK_TZ)) # define IZ_CHECK_TZ #endif #ifdef MEMORY16 # ifndef NO_ASM # define ASM_CRC 1 # endif /* ?NO_ASM */ # ifdef __TURBOC__ # include # if defined(__COMPACT__) || defined(__LARGE__) || defined(__HUGE__) # if defined(DYNAMIC_CRC_TABLE) && defined(DYNALLOC_CRCTAB) error: No dynamic CRC table allocation with Borland C far data models. # endif /* DYNAMIC_CRC_TABLE */ # endif /* Turbo/Borland C far data memory models */ # define nearmalloc malloc # define nearfree free # define DYN_ALLOC # else /* !__TURBOC__ */ # include # define nearmalloc _nmalloc # define nearfree _nfree # define farmalloc _fmalloc # define farfree _ffree # endif /* ?__TURBOC__ */ # define MY_ZCALLOC 1 # ifdef SMALL_MEM # define CBSZ 2048 # define ZBSZ 2048 # endif # ifdef MEDIUM_MEM # define CBSZ 4096 # define ZBSZ 4096 # endif # ifndef CBSZ # define CBSZ 8192 # define ZBSZ 8192 # endif #endif /* MEMORY16 */ /* Symbolic links are not supported, but some compilers may define S_IFLNK. */ #ifndef NO_SYMLINKS # define NO_SYMLINKS #endif #ifdef MATCH # undef MATCH #endif #define MATCH dosmatch /* use DOS style wildcard matching */ #define USE_CASE_MAP #define ROUNDED_TIME(time) (((time) + 1) & (~1)) #define PROCNAME(n) (action == ADD || action == UPDATE ? wild(n) : \ procname(n, 1)) #define FOPR "rb" #define FOPM "r+b" #define FOPW "wb" #include #include #include #ifdef ZCRYPT_INTERNAL # ifdef WINDLL # define ZCR_SEED2 (unsigned)3141592654L /* use PI as seed pattern */ # else # ifndef __GO32__ # include /* getpid() declaration for srand seed */ # endif # endif #endif /* * djgpp 1.x did not declare these */ #if defined(__GO32__) && !defined(__DJGPP__) char *strlwr(char *); int setmode(int, int); #endif #ifdef __WATCOMC__ # define NO_MKTEMP # define HAS_OPENDIR # define SSTAT stat_bandaid int stat_bandaid(const char *path, struct stat *buf); /* Get asm routines to link properly without using "__cdecl": */ # ifdef __386__ # ifdef ASMV # pragma aux match_init "_*" parm caller [] modify [] # pragma aux longest_match "_*" parm caller [] value [eax] \ modify [eax ecx edx] # endif # ifndef USE_ZLIB # pragma aux crc32 "_*" parm caller [] value [eax] modify [eax] # pragma aux get_crc_table "_*" parm caller [] value [eax] \ modify [eax ecx edx] # endif /* !USE_ZLIB */ # else /* !__386__ */ # ifdef ASMV # pragma aux match_init "_*" parm caller [] loadds modify [ax bx] # pragma aux longest_match "_*" parm caller [] loadds value [ax] \ modify [ax bx cx dx es] # endif /* ASMV */ # ifndef USE_ZLIB # pragma aux crc32 "_*" parm caller [] value [ax dx] \ modify [ax bx cx dx es] # pragma aux get_crc_table "_*" parm caller [] value [ax] \ modify [ax bx cx dx] # endif /* !USE_ZLIB */ # endif /* ?__386__ */ #endif /* __WATCOMC__ */ /* * Wrapper function to get around the MSC7 00:00:00 31 Dec 1899 time base, * see msdos.c for more info */ #if defined(_MSC_VER) && _MSC_VER == 700 # define localtime(t) msc7_localtime(t) #endif #ifdef __TURBOC__ # ifdef __FILEIO_C # include /* supplies mktemp() prototype */ # endif #endif #if (defined(__TURBOC__) && !defined(__BORLANDC__) && __TURBOC__ <= 0x0201) # ifndef NO_MKTIME # define NO_MKTIME /* TC 2.01 and earlier do not supply mktime() */ # endif #endif void check_for_windows(char *app); zip30/msdos/README.DOS0100644000076400000060000001466207420230360012417 0ustar ediskREADME.DOS Some notes about the supplied MSDOS executables and their compilers: A) The 32-bit DOS executables "zip.exe" and the auxilary utilities "zipnote.exe", "zipsplit.exe", "zipcloak.exe" (crypt-enabled distribution only) were compiled with DJGPP v 2.03, using gcc 2.95.3 as compiler. They require a DPMI server to run, e.g.: a DOS command prompt window under WINDOWS 3.x or Windows 9x. To use this program under plain DOS, you should install the free (GPL'ed) DPMI server CWSDPMI.EXE. Look for "csdpmi5b.zip" under "simtelnet/gnu/djgpp/v2misc/" on the SimTelNet home site "ftp.cdrom.com" or any mirror site of the SimtelNet archive. We have decided to provide 32-bit rather than 16-bit executables of the auxilary tools for the following reasons: - Nowadays, it has become quite unlikely to find PC computers "in action" that do not at least have an i386 CPU. - the 32-bit versions do not impose additional archive handling limits beyond those defined by the Zip archive format - the 32-bit DJGPP executables can handle long filenames on systems running Windows 95/98/Me and Windows 2K/XP. B) There are two 16-bit MSDOS executables provided in zcr2?x.zip: zip16.exe regular Zip program, requires ca. 455 KBytes of contiguous free DOS memory or more. zip16-sm.exe a variant that was compiled with the SMALL_MEM option for minimal memory consumption; requires at minimum 322 KBytes of contiguous free DOS memory. The SMALL_MEM variant requires much less space for the compression buffers, but at the cost of some compression efficiency. Therefore, we recommend to use the "SMALL_MEM" 16-bit "zip16-sm.exe" only in case of "out of memory" problems (DOS memory is low and/or very large number of archive entries), when the 32-bit program cannot be used for some reason (286 or older; no DPMI server; ...). C) Hard limits of the Zip archive format: Number of entries in Zip archive: 64 k (2^16 - 1 entries) Compressed size of archive entry: 4 GByte (2^32 - 1 Bytes) Uncompressed size of entry: 4 GByte (2^32 - 1 Bytes) Size of single-volume Zip archive: 4 GByte (2^32 - 1 Bytes) Per-volume size of multi-volume archives: 4 GByte (2^32 - 1 Bytes) Number of parts for multi-volume archives: 64 k (1^16 - 1 parts) Total size of multi-volume archive: 256 TByte (4G * 64k) The number of archive entries and of multivolume parts are limited by the structure of the "end-of-central-directory" record, where the these numbers are stored in 2-Byte fields. Some Zip and/or UnZip implementations (for example Info-ZIP's) allow handling of archives with more than 64k entries. (The information from "number of entries" field in the "end-of-central-directory" record is not really neccessary to retrieve the contents of a Zip archive; it should rather be used for consistency checks.) Length of an archive entry name: 64 kByte (2^16 - 1) Length of archive member comment: 64 kByte (2^16 - 1) Total length of "extra field": 64 kByte (2^16 - 1) Length of a single e.f. block: 64 kByte (2^16 - 1) Length of archive comment: 64 KByte (2^16 - 1) Additional limitation claimed by PKWARE: Size of local-header structure (fixed fields of 30 Bytes + filename local extra field): < 64 kByte Size of central-directory structure (46 Bytes + filename + central extra field + member comment): < 64 kByte D) Implementation limits of the Zip executables: 1. Size limits caused by file I/O and compression handling: Size of Zip archive: 2 GByte (2^31 - 1 Bytes) Compressed size of archive entry: 2 GByte (2^31 - 1 Bytes) Uncompressed size of entry: 2 GByte (2^31 - 1 Bytes), (could/should be 4 GBytes...) Multi-volume archive creation is not supported. 2. Limits caused by handling of archive contents lists 2.1. Number of archive entries (freshen, update, delete) a) 16-bit executable: 64k (2^16 -1) or 32k (2^15 - 1), (unsigned vs. signed type of size_t) a1) 16-bit executable: <16k ((2^16)/4) (The smaller limit a1) results from the array size limit of the "qsort()" function.) 32-bit executables <1G ((2^32)/4) (usual system limit of the "qsort()" function on 32-bit systems) b) stack space needed by qsort to sort list of archive entries NOTE: In the current executables, overflows of limits a) and b) are NOT checked! c) amount of free memory to hold "central directory information" of all archive entries; one entry needs: 96 bytes (32-bit) resp. 80 bytes (16-bit) + 3 * length of entry name + length of zip entry comment (when present) + length of extra field(s) (when present, e.g.: UT needs 9 bytes) + some bytes for book-keeping of memory allocation Conclusion: For systems with limited memory space (MSDOS, small AMIGAs, other environments without virtual memory), the number of archive entries is most often limited by condition c). For example, with approx. 100 kBytes of free memory after loading and initializing the program, a 16-bit DOS Zip cannot process more than 600 to 1000 (+) archive entries. (For the 16-bit Windows DLL or the 16-bit OS/2 port, limit c) is less important because Windows or OS/2 executables are not restricted to the 1024k area of real mode memory. These 16-bit ports are limited by conditions a1) and b), say: at maximum approx. 16000 entries!) 2.2. Number of "new" entries (add operation) In addition to the restrictions above (2.1.), the following limits caused by the handling of the "new files" list apply: a) 16-bit executable: <16k ((2^64)/4) b) stack size required for "qsort" operation on "new entries" list. NOTE: In the current executables, the overflow checks for these limits are missing! c) amount of free memory to hold the directory info list for new entries; one entry needs: 24 bytes (32-bit) resp. 22 bytes (16-bit) + 3 * length of filename Please report any problems to: Zip-Bugs@lists.wku.edu Last updated: 07 July 2001 zip30/msdos/zipup.h0100644000076400000060000000113307011111540012412 0ustar edisk/* Copyright (c) 1990-1999 Info-ZIP. All rights reserved. See the accompanying file LICENSE, version 1999-Oct-05 or later (the contents of which are also included in zip.h) for terms of use. If, for some reason, both of these files are missing, the Info-ZIP license also may be found at: ftp://ftp.cdrom.com/pub/infozip/license.html */ #define fhow (O_RDONLY|O_BINARY) #define fbad (-1) typedef int ftype; #define zopen(n,p) open(n,p) #define zread(f,b,n) read(f,b,n) #define zclose(f) close(f) #define zerr(f) (k == (extent)(-1L)) #define zstdin 0 zip30/novell/0040755000076400000060000000000011033727766011277 5ustar ediskzip30/novell/m.cmd0100644000076400000060000000016707240705152012207 0ustar ediskwmake copy zip.nlm f: attrib -r -h -s g:\hho\*.* /s del g:\hho\Attrib\*.* del g:\hho\Attrib\*.* rmdir g:\hho\Attrib zip30/novell/Makefile0100644000076400000060000000702310550051756012726 0ustar edisk# # This makefile was generated by QMK386 v2.14 # # Program: unzip.NLM # This makefile rebuilds the zip NetWare Loadable Module # # Created: Sun Jan 03 03:54:03 1999 # # MAKEINIT defines many of the macros used herein # The following macros can be set via your environment: # CCF386 : Set compile options # QMKVER : Set to 'd' or 'p' to define VERSION # SILENT : If defined, .SILENT will be set # # The following macros are defined for your program: # vMAJ : Major version number # vMIN : Minor version number # vREV : Revision number !ifdef %SILENT .silent !endif program = zip pvmaj = 1 # major version number pvmin = 00 # minor version number pvrev = 3 # revision number e.g. 0,1,2, ... !ifndef %qmkver ! define version p # use 'd' or 'p' here !else ! define version $(%qmkver) !endif !ifeq version d ! define lversion DEBUG ! define debug /dDEBUG !else ! define lversion PRODUCTION ! define debug !endif nlm_TYPE = Form Novell NLM '$(program)' nlm_NAME = Name $^& nlm_SCREEN = Op ScreenName '$(program)' nlm_THREAD = Op ThreadName '$^&__P ' nlm_STACK = Op Stack = 8k nlm_NLMVER = Op Version = $(pvmaj).$(pvmin).$(pvrev) nlm_COPYRIGHT = Op Copyright '$(copyright)' linkop = $+$(linkop)$- Caseexact linkop = $+$(linkop)$- Nod !ifeq version d ! define linkop $+$(linkop)$- Map ! define linkop $+$(linkop)$- Verbose ! define ldebug debug all debug novell !endif objlst = BITS.OBJ objlst = $+$(objlst)$- CRC32.OBJ objlst = $+$(objlst)$- CRYPT.OBJ objlst = $+$(objlst)$- DEFLATE.OBJ objlst = $+$(objlst)$- FILEIO.OBJ objlst = $+$(objlst)$- GLOBALS.OBJ objlst = $+$(objlst)$- MKTIME.OBJ objlst = $+$(objlst)$- NETWARE.OBJ objlst = $+$(objlst)$- SIGNAL.OBJ objlst = $+$(objlst)$- TREES.OBJ objlst = $+$(objlst)$- TTYIO.OBJ objlst = $+$(objlst)$- UTIL.OBJ objlst = $+$(objlst)$- ZIP.OBJ objlst = $+$(objlst)$- ZIPFILE.OBJ objlst = $+$(objlst)$- ZIPUP.OBJ objlst = $+$(objlst)$- $(startup) import = $(allimp) module = CLib build_msg = Building a $(lversion) version of $(program) pgm_ver = /dvMAJ="$(pvmaj)" /dvMIN="$(pvmin)" /dvREV="$(pvrev)" !ifndef %ccf386 ! define d_wcc386opt /ms /w4 /e99 /zp1 /3s /ot /d2 /dN_PLAT_NLM /d_FIND_OLD_HEADERS -dNO_ASM -dNLM $(debug) ! define p_wcc386opt /ms /w4 /s /zp1 /3s /oaxt /dN_PLAT_NLM /d_FIND_OLD_HEADERS -dNO_ASM -dNLM ! define x_wcc386opt $($(version)_wcc386opt) $(pgm_ver) !else ! define x_wcc386opt $(%ccf386) !endif compiler_cmd = $(wcc386) $(x_wcc386opt) $[*.c .BEFORE echo $(build_msg) set inc386=$(inc_386) set lib386=$(lib_386) set wcg386=$(code_386) .c.obj: $(compiler_cmd) zip.nlm : $(objlst) zip.LNK $(linker) @zip zip.LNK : MAKEFILE if exist $^&.LNK del $^&.LNK %append $^&.LNK $(nlm_TYPE) %append $^&.LNK $(nlm_NAME) %append $^&.LNK $(nlm_SCREEN) %append $^&.LNK $(nlm_THREAD) %append $^&.LNK $(nlm_STACK) %append $^&.LNK $(nlm_NLMVER) !ifdef copyright %append $^&.LNK $(nlm_COPYRIGHT) !endif !ifdef ldebug %append $^&.LNK $(ldebug) !endif for %i in ($(linkop)) do %append $^&.LNK Op %i for %i in ($(objlst)) do %append $^&.LNK File %i for %i in ($(import)) do %append $^&.LNK Import @%i for %i in ($(export)) do %append $^&.LNK Export @%i for %i in ($(module)) do %append $^&.LNK Module %i for %i in ($(library)) do %append $^&.LNK Library %i clean : .symbolic del *.MAP del *.OBJ del *.ERR del *.LNK del *.NLM zip : .symbolic -pkzip -u zip MAKEFILE *.c *.h unzip : .symbolic -pkunzip -n -d zip save : .symbolic %make zip %make clean zip30/novell/MAKEINIT0100644000076400000060000000713507240704776012427 0ustar edisk# # makeinit file for makefiles created with QMK386 # # Novell's NetWare SDK - Release 15 # # Directories for both the WATCOM and NOVELL tools # wat386loc = e:\watcom\ nlm386loc = c:\novell\ndk\nwsdk\ nlm386hdr = $(nlm386loc)INCLUDE\NLM;$(nlm386loc)INCLUDE;. nlm386imp = $(nlm386loc)IMPORTS nlm386lib = $(wat386loc)LIB386;$(wat386loc)LIB386\NETWARE # # Define this macro with your copyright statement # #copyright = (C) Copyright 199x NONAME, INC. All Rights Reserved # # Macros that point to various tools we'll need to compile # wcc386r = WCC386 # location of 386 real mode compiler wcc386p = WCC386P # protected compiler (last avail on Watcom v9.5 wcc386 = $(wcc386r) # version we want to use linkr = WLINK # location of real mode linker linkp = WLINKP # protected linker (last avail on Watcom v9.5 linker = $(linkr) # version we want to use nlmlinkr = $(nlm386loc)TOOLS\NLMLINKR # location of real mode Novell linker nlmlinkp = $(nlm386loc)TOOLS\NLMLINKX # location of protected Novell linker nlmlinker = $(nlmlinkr) # version we want to use nlmpackr = $(nlm386loc)TOOLS\NLMPACK # location of real mode NLM compression utility nlmpackp = $(nlm386loc)TOOLS\NLMPACKP # location of protected NLM compression utility nlmpack = $(nlmpackr) # location of NLM compression utility inc_386 = $(nlm386hdr) lib_386 = $(nlm386lib) code_386 = $(wat386loc)BIN\386WCGL.EXE # code generator (last avail on Watcom v9.01 librarian = $(wat386loc)BINB\WLIB # location of librarian # # NLM Import Files # startup = $(nlm386imp)\PRELUDE.OBJ # other option is nwpre.obj allimp = $(nlm386imp)\ALL.IMP # import to include all imports clibimp = $(nlm386imp)\CLIB.IMP # the clib import file tliimp = $(nlm386imp)\TLI.IMP # the tli import file aioimp = $(nlm386imp)\AIO.IMP # the aio import file socklibimp = $(nlm386imp)\SOCKLIB.IMP # the socket import file mathlibimp = $(nlm386imp)\MATHLIB.IMP # the math library import file dsapiimp = $(nlm386imp)\DSAPI.IMP # the NDS import file nutimp = $(nlm386imp)\NWSNUT.IMP # the NWSNUT import file appleimp = $(nlm386imp)\APPLTLK.IMP # the AppleTalk import file nitimp = $(nlm386imp)\NIT.IMP # the legacy NLM import file nlmlibimp = $(nlm386imp)\NLMLIB.IMP # the NLM-specific import file requesterimp = $(nlm386imp)\REQUESTR.IMP # the Requester import file fpsmimp = $(nlm386imp)\FPSM.IMP # floating point support import file threadsimp = $(nlm386imp)\THREADS.IMP # the threads import file dseventimp = $(nlm386imp)\DSEVENT.IMP # DS Events import file psrvimp = $(nlm386imp)\NWPSRV.IMP # print services import file psrv3ximp = $(nlm386imp)\NWPSRV3X.IMP # 3.x print services import file streamsimp = $(nlm386imp)\STREAMS.IMP # streams import file unicodeimp = $(nlm386imp)\UNICODE.IMP # unicode import file agentimp = $(nlm386imp)\agent.imp # SNMP Agent import file smileimp = $(nlm386imp)\smile.imp # SMILE (SNMP) import file # # Cross-platform Import Files # audnlm32imp = $(nlm386imp)\AUDNLM32.IMP # auditing import file calnlm32imp = $(nlm386imp)\CALNLM32.IMP # NWCALLS import file clxnlm32imp = $(nlm386imp)\CLXNLM32.IMP # NWCLIENT import file locnlm32imp = $(nlm386imp)\LOCNLM32.IMP # NWLOCALE import file netnlm32imp = $(nlm386imp)\NETNLM32.IMP # NWNET import file zip30/novell/Netware.c0100644000076400000060000006137610143650000013033 0ustar edisk#include #include #include #include #include #include #include #include #include #include #include #include #include extern void UseAccurateCaseForPaths(int); #include "zip.h" /*------------------------------------------------------------------ ** Global Variables */ #define skipspace( x ) while( isspace( *x ) ) ++x #define nextspace( x ) while( *x && !isspace( *x ) ) ++x #define CWS 0 #define CWV 1 #define CWP 2 #define ALL 99 /* Globals */ extern char *GetWorkArea(void); extern char *next_arg(char *); extern int NLM_exiting; char fid[100]; static breakkey = FALSE; #define MATCH shmatch extern char *label; local ulg label_time = 0; local ulg label_mode = 0; local time_t label_utim = 0; #define PAD 0 #define PATH_END '/' local char *readd(d) DIR *d; /* directory stream to read from */ /* Return a pointer to the next name in the directory stream d, or NULL if no more entries or an error occurs. */ { struct dirent *e; e = readdir(d); return e == NULL ? (char *) NULL : e->d_name; } void findzip(char *s) { dowhereis(s); } void dowhereis(char *s) { char dir[_MAX_PATH]; char fsv[_MAX_SERVER+_MAX_VOLUME+1]; char fdir[_MAX_PATH]; char fname[_MAX_FNAME],fext[_MAX_EXT], both[_MAX_FNAME+_MAX_EXT]; char *p = next_arg(s); /* point at argument */ if(!*p) { printf("No filename specified!"); return; } //setlocale (LC_ALL, "NORWAY"); NWLsetlocale (LC_ALL, "NORWAY"); strcpy(dir,GetWorkArea()); /* get the file name specification */ _splitpath(p,fsv,fdir,fname,fext); //printf ("p %s, fsv %s, fdir %s, fname %s, fext %s\n", p,fsv,fdir,fname,fext); //getch(); sprintf(both,"%s%s",strupr(fname),strupr(fext)); breakkey = FALSE; /* startup the recursive file find operation */ chdir(fsv); UseAccurateCaseForPaths(1); SetCurrentNameSpace (NW_NS_LONG); chdir(fdir); findit(both); } char *GetWorkArea(void) { static char cwd[_MAX_PATH]; static char serverName[_MAX_SERVER]; static char volumeName[_MAX_VOLUME + 1]; static char dirName[_MAX_DIR]; if(getcwd(cwd,_MAX_PATH) == NULL) return NULL; ParsePath(cwd,serverName,volumeName,dirName); /* shouldn't fail! */ return cwd; } char *next_arg(char *s) { char *p; skipspace(s); /* ignore white */ p = s; nextspace(s); /* find next blank */ *s = NULL; return(p); } static void findit(char *what) { char dir[_MAX_PATH]; char zipdir[_MAX_PATH]; char szzipfile[_MAX_PATH]; char *psz; DIR *dirStructPtr; DIR *dirStructPtrSave; int r; getcwd(dir,_MAX_PATH); psz = dir; while (*psz) { if (*psz == ':') { strcpy (zipdir, psz + 1); break; } psz++; } dirStructPtrSave = dirStructPtr = opendir(what); /* _A_NORMAL Normal file; read/write permitted _A_RDONLY Read-only file _A_HIDDEN Hidden file _A_SYSTEM System file _A_VOLID Volume ID entry _A_SUBDIR Subdirectory _A_ARCH Archive file */ if (hidden_files) SetReaddirAttribute (dirStructPtr, _A_NORMAL | _A_RDONLY | _A_HIDDEN | _A_SYSTEM | _A_ARCH); else SetReaddirAttribute (dirStructPtr, _A_NORMAL | _A_ARCH); //while(dirStructPtr && !breakkey) while(dirStructPtr && !NLM_exiting) { //printf ("\n NLM_exiting test Line 167.... \n"); dirStructPtr = readdir(dirStructPtr); if((dirStructPtr == NULL) || (dirStructPtr == -1)) break; /* Filen er funnet */ if(dirStructPtr->d_attr & _A_SUBDIR) continue; strcpy (szzipfile, zipdir); strcat (szzipfile, "/"); strcat (szzipfile, dirStructPtr->d_name); procnamehho (szzipfile); //ThreadSwitchWithDelay(); //if(kbhit() && getch() == 3) // printf("^C\n",breakkey = TRUE); } if(dirStructPtrSave) closedir(dirStructPtrSave); if (!recurse) return; /* Now traverse the directories in this path */ dirStructPtrSave = dirStructPtr = opendir("*.*"); if(dirStructPtr == NULL) return; if (hidden_files) SetReaddirAttribute (dirStructPtr, _A_NORMAL | _A_RDONLY | _A_HIDDEN | _A_SYSTEM | _A_ARCH | _A_SUBDIR); else SetReaddirAttribute (dirStructPtr, _A_NORMAL | _A_ARCH | _A_SUBDIR); //ThreadSwitchWithDelay(); while(!NLM_exiting) { //printf ("\n NLM_exiting test Line 204.... \n"); getch (); dirStructPtr = readdir(dirStructPtr); if((dirStructPtr == NULL) || (dirStructPtr == -1)) break; if(dirStructPtr->d_attr & _A_SUBDIR) { strcpy (szzipfile, zipdir); strcat (szzipfile, "/"); strcat (szzipfile, dirStructPtr->d_name); procnamehho (szzipfile); chdir(dirStructPtr->d_name); findit(what); chdir(".."); } //if(kbhit() && getch() == 3) // printf("^C\n",breakkey = TRUE); } if(dirStructPtrSave) closedir(dirStructPtrSave); } int wild(w) char *w; /* path/pattern to match */ /* If not in exclude mode, expand the pattern based on the contents of the file system. Return an error code in the ZE_ class. */ { DIR *d; /* stream for reading directory */ char *e; /* name found in directory */ int r; /* temporary variable */ char *n; /* constructed name from directory */ int f; /* true if there was a match */ char *a; /* alloc'ed space for name */ //char *p; /* path */ char *q; /* name */ char v[5]; /* space for device current directory */ char dir[_MAX_PATH]; char fsv[_MAX_SERVER+_MAX_VOLUME+1]; char fdir[_MAX_PATH]; char fname[_MAX_FNAME],fext[_MAX_EXT], both[_MAX_FNAME+_MAX_EXT]; char *p; /* point at argument */ p = w; /* Test HHO */ findzip(p); return ZE_OK; strcpy(dir,GetWorkArea()); /* get the file name specification */ _splitpath(p,fsv,fdir,fname,fext); sprintf(both,"%s%s",strupr(fname),strupr(fext)); /* startup the recursive file find operation */ chdir(fsv); /* Search that level for matching names */ if ((d = opendir(both)) == NULL) { free((zvoid *)a); return ZE_MISS; } f = 0; while ((e = readd(d)) != NULL) { if (strcmp(e, ".") && strcmp(e, "..") && MATCH(q, e)) { f = 1; if (strcmp(p, ".") == 0) { /* path is . */ r = procname(e); /* name is name */ if (r) { f = 0; break; } } else { if ((n = malloc(strlen(p) + strlen(e) + 2)) == NULL) { free((zvoid *)a); closedir(d); return ZE_MEM; } n = strcpy(n, p); if (n[r = strlen(n) - 1] != '/' && n[r] != ':') strcat(n, "/"); r = procname(strcat(n, e)); /* name is path/name */ free((zvoid *)n); if (r) { f = 0; break; } } } } closedir(d); /* Done */ free((zvoid *)a); return f ? ZE_OK : ZE_MISS; } int procnamehho (char *n) { int m; /* matched flag */ char *p; /* path for recursion */ struct stat s; /* result of stat() */ struct zlist far *z; /* steps through zfiles list */ char *a; if (n == NULL) /* volume_label request in freshen|delete mode ?? */ return ZE_OK; if (strcmp(n, "-") == 0) /* if compressing stdin */ return newname(n, 0); else if (stat(n, &s) #if defined(__TURBOC__) || defined(__WATCOMC__) /* For these 2 compilers, stat() succeeds on wild card names! */ || isshexp(n) #endif ) { /* Not a file or directory--search for shell expression in zip file */ p = ex2in(n, 0, (int *)NULL); /* shouldn't affect matching chars */ m = 1; for (z = zfiles; z != NULL; z = z->nxt) { if (MATCH(p, z->iname)) { z->mark = pcount ? filter(z->zname) : 1; if (verbose) fprintf(mesg, "zip diagnostic: %scluding %s\n", z->mark ? "in" : "ex", z->name); m = 0; } } free((zvoid *)p); return m ? ZE_MISS : ZE_OK; } /* Live name--use if file, recurse if directory */ for (p = n; *p; p++) /* use / consistently */ if (*p == '\\') *p = '/'; //printf ("\nHHO %s\n", n); if ((s.st_mode & S_IFDIR) == 0) { //printf ("\nHHO1 %s\n", n); /* add or remove name of file */ //printf ("\nAdding name %s to list.\n", n); if ((m = newname(n, 0)) != ZE_OK) return m; } else { /* Add trailing / to the directory name */ if ((p = malloc(strlen(n)+2)) == NULL) return ZE_MEM; if (strcmp(n, ".") == 0 || strcmp(n, "/.") == 0) { *p = '\0'; /* avoid "./" prefix and do not create zip entry */ } else { strcpy(p, n); a = p + strlen(p); if (a[-1] != '/') strcpy(a, "/"); //if (dirnames && (m = newname(p, 1)) != ZE_OK) { if ((m = newname(p, 1)) != ZE_OK) { free((zvoid *)p); return m; } free ((zvoid *)p); } return ZE_OK; } return ZE_OK; } int procname(n) char *n; /* name to process */ /* Process a name or sh expression to operate on (or exclude). Return an error code in the ZE_ class. */ { char *a; /* path and name for recursion */ DIR *d; /* directory stream from opendir() */ char *e; /* pointer to name from readd() */ int m; /* matched flag */ char *p; /* path for recursion */ struct stat s; /* result of stat() */ struct zlist far *z; /* steps through zfiles list */ if (n == NULL) /* volume_label request in freshen|delete mode ?? */ return ZE_OK; if (strcmp(n, "-") == 0) /* if compressing stdin */ return newname(n, 0); else if (stat(n, &s) #if defined(__TURBOC__) || defined(__WATCOMC__) /* For these 2 compilers, stat() succeeds on wild card names! */ || isshexp(n) #endif ) { /* Not a file or directory--search for shell expression in zip file */ p = ex2in(n, 0, (int *)NULL); /* shouldn't affect matching chars */ m = 1; for (z = zfiles; z != NULL; z = z->nxt) { if (MATCH(p, z->iname)) { z->mark = pcount ? filter(z->zname) : 1; if (verbose) fprintf(mesg, "zip diagnostic: %scluding %s\n", z->mark ? "in" : "ex", z->name); m = 0; } } free((zvoid *)p); return m ? ZE_MISS : ZE_OK; } /* Live name--use if file, recurse if directory */ for (p = n; *p; p++) /* use / consistently */ if (*p == '\\') *p = '/'; if ((s.st_mode & S_IFDIR) == 0) { /* add or remove name of file */ if ((m = newname(n, 0)) != ZE_OK) return m; } else { /* Add trailing / to the directory name */ if ((p = malloc(strlen(n)+2)) == NULL) return ZE_MEM; if (strcmp(n, ".") == 0 || strcmp(n, "/.") == 0) { *p = '\0'; /* avoid "./" prefix and do not create zip entry */ } else { strcpy(p, n); a = p + strlen(p); if (a[-1] != '/') strcpy(a, "/"); if (dirnames && (m = newname(p, 1)) != ZE_OK) { free((zvoid *)p); return m; } } /* recurse into directory */ if (recurse && (d = opendir(n)) != NULL) { while ((e = readd(d)) != NULL) { if (strcmp(e, ".") && strcmp(e, "..")) { if ((a = malloc(strlen(p) + strlen(e) + 1)) == NULL) { closedir(d); free((zvoid *)p); return ZE_MEM; } strcat(strcpy(a, p), e); if ((m = procname(a)) != ZE_OK) /* recurse on name */ { if (m == ZE_MISS) zipwarn("name not matched: ", a); else ziperr(m, a); } free((zvoid *)a); } } closedir(d); } free((zvoid *)p); } /* (s.st_mode & S_IFDIR) == 0) */ return ZE_OK; } char *szRelativParameter; char szRelativ[512]; int iRelativOK = FALSE; int iRelativPakking = FALSE; int fixRelativpath () { char *szp; szp = szRelativParameter; if (szRelativParameter[0] == '/' || szRelativParameter[0] == '\\') szp++; while (*szp) { if (*szp == '\\') *szp = '/'; szp++; } szp = szRelativParameter; if (szRelativParameter[0] == '/') szp++; strcpy (szRelativ, szp); if (strlen(szp) == 0) { szRelativ[0] = '\0'; return FALSE; } return TRUE; } char *ex2in(x, isdir, pdosflag) char *x; /* external file name */ int isdir; /* input: x is a directory */ int *pdosflag; /* output: force MSDOS file attributes? */ /* Convert the external file name to a zip file name, returning the malloc'ed string or NULL if not enough memory. */ { char *n; /* internal file name (malloc'ed) */ char *t; /* shortened name */ int dosflag; char *sztUpper; /* Find starting point in name before doing malloc */ t = *x && *(x + 1) == ':' ? x + 2 : x; while (*t == '/' || *t == '\\') t++; /* Make changes, if any, to the copied name (leave original intact) */ for (n = t; *n; n++) if (*n == '\\') *n = '/'; if (iRelativPakking) { //printf ("\n LINE 516 *ex2ex Internt navn %s external name %s.\n", t, x); getch (); if (!iRelativOK) { if (!fixRelativpath()) { iRelativOK = FALSE; iRelativPakking = FALSE; } else { sztUpper = malloc (strlen(t) + 10); strcpy (sztUpper, t); NWLstrupr (sztUpper); NWLstrupr (szRelativ); if (strncmp (sztUpper, szRelativ, strlen(szRelativ)) == 0) { t = t + strlen(szRelativ); iRelativPakking = TRUE; iRelativOK = TRUE; } else { iRelativOK = FALSE; iRelativPakking = FALSE; } free (sztUpper); } } else { t = t + strlen(szRelativ); } } if (!pathput) t = last(t, PATH_END); /* Malloc space for internal name and copy it */ if ((n = malloc(strlen(t) + 1)) == NULL) return NULL; strcpy(n, t); if (dosify) msname(n); /* Returned malloc'ed name */ if (pdosflag) *pdosflag = dosflag; return n; } char *in2ex(n) char *n; /* internal file name */ /* Convert the zip file name to an external file name, returning the malloc'ed string or NULL if not enough memory. */ { char *x; /* external file name */ if ((x = malloc(strlen(n) + 1 + PAD)) == NULL) return NULL; strcpy(x, n); //if ( !IsFileNameValid(x) ) //ChangeNameForFAT(x); //printf ("\n *in2ex Internt navn %s external name %s.\n", n, x); getch (); return x; } void stamp(f, d) char *f; /* name of file to change */ ulg d; /* dos-style time to change it to */ /* Set last updated and accessed time of file f to the DOS time d. */ { //SetFileTime(f, d); } ulg filetime(f, a, n, t) char *f; /* name of file to get info on */ ulg *a; /* return value: file attributes */ long *n; /* return value: file size */ iztimes *t; /* return value: access, modific. and creation times */ /* If file *f does not exist, return 0. Else, return the file's last modified date and time as an MSDOS date and time. The date and time is returned in a long with the date most significant to allow unsigned integer comparison of absolute times. Also, if a is not a NULL pointer, store the file attributes there, with the high two bytes being the Unix attributes, and the low byte being a mapping of that to DOS attributes. If n is not NULL, store the file size there. If t is not NULL, the file's access, modification and creation times are stored there as UNIX time_t values. If f is "-", use standard input as the file. If f is a device, return a file size of -1 */ { struct stat s; /* results of stat() */ /* convert FNMAX to malloc - 11/8/04 EG */ char *name; int len = strlen(f); if (f == label) { if (a != NULL) *a = label_mode; if (n != NULL) *n = -2L; /* convention for a label name */ if (t != NULL) t->atime = t->mtime = t->ctime = label_utim; return label_time; } if ((name = malloc(len + 1)) == NULL) { ZIPERR(ZE_MEM, "filetime"); } strcpy(name, f); if (name[len - 1] == '/') name[len - 1] = '\0'; /* not all systems allow stat'ing a file with / appended */ if (strcmp(f, "-") == 0) { if (fstat(fileno(stdin), &s) != 0) error("fstat(stdin)"); } else if (stat(name, &s) != 0) { /* Accept about any file kind including directories * (stored with trailing / with -r option) */ free(name); return 0; } free(name); if (a != NULL) { *a = s.st_attr; // << 16) | !(s.st_mode & S_IWRITE); //*a = ((ulg)s.st_mode << 16) | !(s.st_mode & S_IWRITE); //if ((s.st_mode & S_IFMT) == S_IFDIR) { //*a |= MSDOS_DIR_ATTR; //} } if (n != NULL) *n = (s.st_mode & S_IFMT) == S_IFREG ? s.st_size : -1L; if (t != NULL) { t->atime = s.st_atime; t->mtime = s.st_mtime; t->ctime = t->mtime; /* best guess, (s.st_ctime: last status change!!) */ } return unix2dostime(&s.st_mtime); } ulg filetimeHHO(f, a, n, t) char *f; /* name of file to get info on */ ulg *a; /* return value: file attributes */ long *n; /* return value: file size */ iztimes *t; /* return value: access, modific. and creation times */ /* If file *f does not exist, return 0. Else, return the file's last modified date and time as an MSDOS date and time. The date and time is returned in a long with the date most significant to allow unsigned integer comparison of absolute times. Also, if a is not a NULL pointer, store the file attributes there, with the high two bytes being the Unix attributes, and the low byte being a mapping of that to DOS attributes. If n is not NULL, store the file size there. If t is not NULL, the file's access, modification and creation times are stored there as UNIX time_t values. If f is "-", use standard input as the file. If f is a device, return a file size of -1 */ { struct stat s; /* results of stat() */ char *name; int len = strlen(f), isstdin = !strcmp(f, "-"); if (f == label) { if (a != NULL) *a = label_mode; if (n != NULL) *n = -2L; /* convention for a label name */ if (t != NULL) t->atime = t->mtime = t->ctime = label_utim; return label_time; } if ((name = malloc(len + 1)) == NULL) { ZIPERR(ZE_MEM, "filetimeHHO"); } strcpy(name, f); if (name[len - 1] == '/') name[len - 1] = '\0'; /* not all systems allow stat'ing a file with / appended */ if (isstdin) { /* it is common for some PC based compilers to fail with fstat() on devices or pipes */ if (fstat(fileno(stdin), &s) != 0) { s.st_mode = S_IFREG; s.st_size = -1L; } time(&s.st_ctime); s.st_atime = s.st_mtime = s.st_ctime; } else if (stat(name, &s) != 0) { /* Accept about any file kind including directories * (stored with trailing / with -r option) */ free(name); return 0; } if (a != NULL) { //*a = ((ulg)s.st_mode << 16) | (isstdin ? 0L : (ulg)GetFileMode(name)); //*a = (ulg)s.st_mode; *a = s.st_attr; } printf ("\nDette er en test LINE : 721 \n"); getch(); if (n != NULL) *n = (s.st_mode & S_IFMT) == S_IFREG ? s.st_size : -1L; #ifdef __WATCOMC__ /* of course, Watcom always has to make an exception */ if (s.st_atime == 312764400) s.st_atime = s.st_mtime; if (s.st_ctime == 312764400) s.st_ctime = s.st_mtime; #endif if (t != NULL) { t->atime = s.st_atime; t->mtime = s.st_mtime; t->ctime = s.st_ctime; } printf ("\nDette er en test LINE : 735 \n"); getch(); //return GetFileTime(name); free(name); return t->atime; } int deletedir(d) char *d; /* directory to delete */ /* Delete the directory *d if it is empty, do nothing otherwise. Return the result of rmdir(), delete(), or system(). */ { return rmdir(d); } int set_extra_field(z, z_utim) struct zlist far *z; iztimes *z_utim; /* create extra field and change z->att if desired */ { #ifdef USE_EF_UT_TIME if ((z->extra = (char *)malloc(EB_HEADSIZE+EB_UT_LEN(1))) == NULL) return ZE_MEM; z->extra[0] = 'U'; z->extra[1] = 'T'; z->extra[2] = EB_UT_LEN(1); /* length of data part of e.f. */ z->extra[3] = 0; z->extra[4] = EB_UT_FL_MTIME; z->extra[5] = (char)(z_utim->mtime); z->extra[6] = (char)(z_utim->mtime >> 8); z->extra[7] = (char)(z_utim->mtime >> 16); z->extra[8] = (char)(z_utim->mtime >> 24); z->cext = z->ext = (EB_HEADSIZE+EB_UT_LEN(1)); z->cextra = z->extra; return ZE_OK; #else /* !USE_EF_UT_TIME */ return (int)(z-z); #endif /* ?USE_EF_UT_TIME */ } /******************************/ /* Function version_local() */ /******************************/ static ZCONST char CompiledWith[] = "Compiled with %s%s for %s%s%s%s.\n\n"; /* At module level to keep Turbo C++ 1.0 happy !! */ void version_local() { #if defined(__DJGPP__) || defined(__WATCOMC__) || \ (defined(_MSC_VER) && (_MSC_VER != 800)) char buf[80]; #endif printf(CompiledWith, #ifdef __GNUC__ # if defined(__DJGPP__) (sprintf(buf, "djgpp v%d / gcc ", __DJGPP__), buf), # elif defined(__GO32__) "djgpp v1.x / gcc ", # elif defined(__EMX__) /* ...so is __EMX__ (double sigh) */ "emx+gcc ", # else "gcc ", # endif __VERSION__, #elif defined(__WATCOMC__) # if (__WATCOMC__ % 10 > 0) /* We do this silly test because __WATCOMC__ gives two digits for the */ /* minor version, but Watcom packaging prefers to show only one digit. */ (sprintf(buf, "Watcom C/C++ %d.%02d", __WATCOMC__ / 100, __WATCOMC__ % 100), buf), "", # else (sprintf(buf, "Watcom C/C++ %d.%d", __WATCOMC__ / 100, (__WATCOMC__ % 100) / 10), buf), "", # endif #elif defined(__TURBOC__) # ifdef __BORLANDC__ "Borland C++", # if (__BORLANDC__ < 0x0200) " 1.0", # elif (__BORLANDC__ == 0x0200) /* James: __TURBOC__ = 0x0297 */ " 2.0", # elif (__BORLANDC__ == 0x0400) " 3.0", # elif (__BORLANDC__ == 0x0410) /* __BCPLUSPLUS__ = 0x0310 */ " 3.1", # elif (__BORLANDC__ == 0x0452) /* __BCPLUSPLUS__ = 0x0320 */ " 4.0 or 4.02", # elif (__BORLANDC__ == 0x0460) /* __BCPLUSPLUS__ = 0x0340 */ " 4.5", # elif (__BORLANDC__ == 0x0500) /* __TURBOC__ = 0x0500 */ " 5.0", # else " later than 5.0", # endif # else "Turbo C", # if (__TURBOC__ > 0x0401) "++ later than 3.0" # elif (__TURBOC__ == 0x0401) /* Kevin: 3.0 -> 0x0401 */ "++ 3.0", # elif (__TURBOC__ == 0x0295) /* [661] vfy'd by Kevin */ "++ 1.0", # elif ((__TURBOC__ >= 0x018d) && (__TURBOC__ <= 0x0200)) /* James: 0x0200 */ " 2.0", # elif (__TURBOC__ > 0x0100) " 1.5", /* James: 0x0105? */ # else " 1.0", /* James: 0x0100 */ # endif # endif #elif defined(MSC) "Microsoft C ", # ifdef _MSC_VER # if (_MSC_VER == 800) "(Visual C++ v1.1)", # elif (_MSC_VER == 850) "(Windows NT v3.5 SDK)", # elif (_MSC_VER == 900) "(Visual C++ v2.0/v2.1)", # elif (_MSC_VER > 900) (sprintf(buf2, "(Visual C++ v%d.%d)", _MSC_VER/100 - 6, _MSC_VER%100/10), buf2), # else (sprintf(buf, "%d.%02d", _MSC_VER/100, _MSC_VER%100), buf), # endif # else "5.1 or earlier", # endif #else "unknown compiler", "", #endif "MS-DOS", #if (defined(__GNUC__) || (defined(__WATCOMC__) && defined(__386__))) " (32-bit)", #elif defined(M_I86HM) || defined(__HUGE__) " (16-bit, huge)", #elif defined(M_I86LM) || defined(__LARGE__) " (16-bit, large)", #elif defined(M_I86MM) || defined(__MEDIUM__) " (16-bit, medium)", #elif defined(M_I86CM) || defined(__COMPACT__) " (16-bit, compact)", #elif defined(M_I86SM) || defined(__SMALL__) " (16-bit, small)", #elif defined(M_I86TM) || defined(__TINY__) " (16-bit, tiny)", #else " (16-bit)", #endif #ifdef __DATE__ " on ", __DATE__ #else "", "" #endif ); } /* end function version_local() */ #ifdef __WATCOMC__ /* This papers over a bug in Watcom 10.6's standard library... sigh */ /* Apparently it applies to both the DOS and Win32 stat()s. */ int stat_bandaid(const char *path, struct stat *buf) { char newname[4]; if (!stat(path, buf)) return 0; else if (!strcmp(path, ".") || (path[0] && !strcmp(path + 1, ":."))) { strcpy(newname, path); newname[strlen(path) - 1] = '\\'; /* stat(".") fails for root! */ return stat(newname, buf); } else return -1; } #endif zip30/novell/osdep.h0100644000076400000060000001335607240705162012556 0ustar edisk/* Copyright (c) 1990-1999 Info-ZIP. All rights reserved. See the accompanying file LICENSE, version 1999-Oct-05 or later (the contents of which are also included in zip.h) for terms of use. If, for some reason, both of these files are missing, the Info-ZIP license also may be found at: ftp://ftp.cdrom.com/pub/infozip/license.html */ /* The symbol DOS is used throughout the Zip source to identify code portions * specific to the MSDOS port. * Just to make sure, we check that it is set. * (Currently, this should should not be neccessary, since currently it has * to be set on the compiler command line to get this file read in.) */ #ifndef DOS # define DOS #endif /* The symbol MSDOS is consistently used in the generic source files * to identify code to support for MSDOS (and MSDOS related) stuff. * e.g: FAT or (FAT like) file systems, * '\\' as directory separator in paths, * "\r\n" as record (line) terminator in text files, ... * * IMPORTANT Note: * This symbol is not unique for the MSDOS port !!!!!! * It is also defined by ports to some other OS which are (to some extend) * considered DOS compatible. * Examples are: OS/2 (OS2), Windows NT and Windows 95 (WIN32). * */ #ifndef MSDOS # define MSDOS #endif /* Power C is similar to Turbo C */ #ifdef __POWERC # define __TURBOC__ #endif /* __POWERC */ /* Automatic setting of the common Microsoft C idenfifier MSC. * NOTE: Watcom also defines M_I*86 ! */ #if defined(_MSC_VER) || (defined(M_I86) && !defined(__WATCOMC__)) # ifndef MSC # define MSC /* This should work for older MSC, too! */ # endif #endif #if !defined(__GO32__) && !defined(__EMX__) # define NO_UNISTD_H #endif #if defined(__WATCOMC__) && defined(__386__) # define WATCOMC_386 #endif #ifdef WINDLL # define MSWIN # define MEMORY16 #endif #if !defined(__EMX__) && !defined(__GO32__) && !defined(WATCOMC_386) #if !defined(WINDLL) # define MSDOS16 /* 16 bit MSDOS only */ # define MEMORY16 #endif #endif #if !defined(NO_ASM) && !defined(ASMV) # define ASMV #endif /* enable creation of UTC time fields unless explicitely suppressed */ #if !defined(NO_EF_UT_TIME) && !defined(USE_EF_UT_TIME) # define USE_EF_UT_TIME #endif /* check that TZ environment variable is defined before using UTC times */ #if (!defined(NO_IZ_CHECK_TZ) && !defined(IZ_CHECK_TZ)) # define IZ_CHECK_TZ #endif #ifdef MEMORY16 # ifndef NO_ASM # define ASM_CRC 1 # endif /* ?NO_ASM */ # ifdef __TURBOC__ # include # if defined(__COMPACT__) || defined(__LARGE__) || defined(__HUGE__) # if defined(DYNAMIC_CRC_TABLE) && defined(DYNALLOC_CRCTAB) error: No dynamic CRC table allocation with Borland C far data models. # endif /* DYNAMIC_CRC_TABLE */ # endif /* Turbo/Borland C far data memory models */ # define nearmalloc malloc # define nearfree free # define DYN_ALLOC # else /* !__TURBOC__ */ # include # define nearmalloc _nmalloc # define nearfree _nfree # define farmalloc _fmalloc # define farfree _ffree # endif /* ?__TURBOC__ */ # define MY_ZCALLOC 1 # ifdef SMALL_MEM # define CBSZ 2048 # define ZBSZ 2048 # endif # ifdef MEDIUM_MEM # define CBSZ 4096 # define ZBSZ 4096 # endif # ifndef CBSZ # define CBSZ 8192 # define ZBSZ 8192 # endif #endif /* MEMORY16 */ #ifdef MATCH # undef MATCH #endif #define MATCH dosmatch /* use DOS style wildcard matching */ #define USE_CASE_MAP #define ROUNDED_TIME(time) (((time) + 1) & (~1)) #define PROCNAME(n) (action == ADD || action == UPDATE ? wild(n) : \ procname(n, 1)) #define FOPR "rb" #define FOPM "r+b" #define FOPW "wb" #include #include #include #ifdef ZCRYPT_INTERNAL # ifdef WINDLL # define ZCR_SEED2 (unsigned)3141592654L /* use PI as seed pattern */ # else # ifndef __GO32__ # include /* getpid() declaration for srand seed */ # endif # endif #endif /* * djgpp 1.x did not declare these */ #if defined(__GO32__) && !defined(__DJGPP__) char *strlwr(char *); int setmode(int, int); #endif #ifdef __WATCOMC__ # define NO_MKTEMP # define HAS_OPENDIR # define SSTAT stat_bandaid int stat_bandaid(const char *path, struct stat *buf); /* Get asm routines to link properly without using "__cdecl": */ # ifdef __386__ # ifdef ASMV # pragma aux match_init "_*" parm caller [] modify [] # pragma aux longest_match "_*" parm caller [] value [eax] \ modify [eax ecx edx] # endif # ifndef USE_ZLIB # pragma aux crc32 "_*" parm caller [] value [eax] modify [eax] # pragma aux get_crc_table "_*" parm caller [] value [eax] \ modify [eax ecx edx] # endif /* !USE_ZLIB */ # else /* !__386__ */ # ifdef ASMV # pragma aux match_init "_*" parm caller [] loadds modify [ax bx] # pragma aux longest_match "_*" parm caller [] loadds value [ax] \ modify [ax bx cx dx es] # endif /* ASMV */ # ifndef USE_ZLIB # pragma aux crc32 "_*" parm caller [] value [ax dx] \ modify [ax bx cx dx es] # pragma aux get_crc_table "_*" parm caller [] value [ax] \ modify [ax bx cx dx] # endif /* !USE_ZLIB */ # endif /* ?__386__ */ #endif /* __WATCOMC__ */ /* * Wrapper function to get around the MSC7 00:00:00 31 Dec 1899 time base, * see msdos.c for more info */ #if defined(_MSC_VER) && _MSC_VER == 700 # define localtime(t) msc7_localtime(t) #endif #if (defined(__TURBOC__) && !defined(__BORLANDC__) && __TURBOC__ <= 0x0201) # ifndef NO_MKTIME # define NO_MKTIME /* TC 2.01 and earlier do not supply mktime() */ # endif #endif zip30/novell/README0100644000076400000060000000043607241352256012151 0ustar ediskUnfinished integration into zip 2.4 of novell port to zip 2.2. TODO: Too much novell specific stuff via ifdef into the main sourcecode, use atexit() and setjmp()/longjmp() constructions instead. If a function doesn't exist (e.g. isatty), just write a wrapper and put it in Netware.c zip30/novell/signal.c0100644000076400000060000000163207241342156012707 0ustar edisk#include #include /*******************************/ /* Interupt handler */ /*******************************/ int NLM_mainThreadGroupID; int NLM_threadCnt = 0; int NLM_exiting = FALSE; #pragma off(unreferenced); void NLM_SignalHandler(int sig) #pragma on(unreferenced); { int handlerThreadGroupID; switch(sig) { case SIGTERM: NLM_exiting = TRUE; handlerThreadGroupID = GetThreadGroupID(); SetThreadGroupID(NLM_mainThreadGroupID); /* NLM SDK functions may be called here */ while (NLM_threadCnt != 0) ThreadSwitchWithDelay(); SetThreadGroupID(handlerThreadGroupID); break; case SIGINT: signal(SIGINT, NLM_SignalHandler); break; } return; } void NLMsignals(void) { ++NLM_threadCnt; NLM_mainThreadGroupID = GetThreadGroupID(); signal(SIGTERM, NLM_SignalHandler); signal(SIGINT, NLM_SignalHandler); } void NLMexit(void) { --NLM_threadCnt; } zip30/novell/zip.lnk0100644000076400000060000000070110550051772012570 0ustar ediskForm Novell NLM 'zip' Name zip Op ScreenName 'zip' Op ThreadName 'zip__P ' Op Stack = 8k Op Version = 1.00.3 Op Caseexact Op Nod File BITS.OBJ File CRC_i386.OBJ File CRYPT.OBJ File DEFLATE.OBJ File FILEIO.OBJ File GLOBALS.OBJ File MKTIME.OBJ File NETWARE.OBJ File TREES.OBJ File TTYIO.OBJ File UTIL.OBJ File ZIP.OBJ File ZIPFILE.OBJ File ZIPUP.OBJ File c:\novell\ndk\nwsdk\IMPORTS\PRELUDE.OBJ Import @c:\novell\ndk\nwsdk\IMPORTS\ALL.IMP Module CLib zip30/novell/zipup.h0100644000076400000060000000113307051100040012561 0ustar edisk/* Copyright (c) 1990-1999 Info-ZIP. All rights reserved. See the accompanying file LICENSE, version 1999-Oct-05 or later (the contents of which are also included in zip.h) for terms of use. If, for some reason, both of these files are missing, the Info-ZIP license also may be found at: ftp://ftp.cdrom.com/pub/infozip/license.html */ #define fhow (O_RDONLY|O_BINARY) #define fbad (-1) typedef int ftype; #define zopen(n,p) open(n,p) #define zread(f,b,n) read(f,b,n) #define zclose(f) close(f) #define zerr(f) (k == (extent)(-1L)) #define zstdin 0 zip30/os2/0040755000076400000060000000000011033727766010503 5ustar ediskzip30/os2/makefile.os20100644000076400000060000003537110550052350012672 0ustar edisk# Makefile for Zip, ZipCloak, ZipNote and ZipSplit # Supported Make utilities: # - Microsoft/IBM nmake # - dmake 3.8 or higher # - GNU make, at least version 3.68 # - NOT watcom make # For Microsoft and Watcom C, better use NMAKE, # otherwise it doesn't matter. # Supported 16-bit C Compilers (created programs run under OS/2 1.x and 2.x): # - Microsoft C 6.00A # - Watcom C/C++ 16-bit # Supported 32-bit C Compilers (created programs run under OS/2 2.x only): # - GNU gcc (emx kit 0.9c or newer) # - IBM C Set/2 or C Set++ - does not yet work with ASM code # - Watcom C/C++ 32-bit - does not yet work with ASM code # - Borland C++ - no ASM code yet # - MetaWare High C/C++ - no ASM code yet # Supported Cross-Compilers for MS-DOS: # - Microsoft C 6.00A (16-bit) # - Watcom C/C++ (16- and 32-bit) # - GNU gcc (emx kit 0.9c or newer, 32-bit) # Supported Cross-Compilers for Win32 (WinNT/Win95): # - GNU gcc (emx kit 0.9c or newer, with RSXNT 1.4 or newer) # Supported Assemblers: # - Microsoft MASM 6.00 with Microsoft C, IBM C # - Watcom WASM with Watcom C/C++ # - GNU as with GNU gcc # To use MASM 5.x instead of MASM 6.00: # - set AS="masm -T -Ml" # - set ASEOL=";" # To use, enter "make/nmake/dmake -f os2/makefile.os2" # (this makefile depends on its name being "os2/makefile.os2"). # Add -DNO_ASM to CFLAGS and define OBJA to `nothing' if you do not have # masm or ml. # Add -DDYN_ALLOC to ASFLAGS if you have defined it in tailor.h or CFLAGS # Note: assembly language modules are really only supported for # Microsoft 16-bit and GNU gcc 32-bit compilation. # Notes on 16-bit (Microsoft C 6.00) compilation: # The resulting programs can be used under OS/2 protected mode only. # A larger stack has to be used for OS/2 because system calls # use more stack than under DOS, 8k is recommended by Microsoft. # Note that __STDC__ has to be defined explicitly with C 6.00 when -Ze # is given, because Microsoft disables __STDC__ when their extensions # are enabled. This is different from the C 5.10 behaviour. # Notes on 32-bit OS/2 compilation: # The resulting programs can be used under OS/2 protected # mode of OS/2 2.x only, not under 1.x and not under DOS. # It makes no difference if __STDC__ is defined or not. # Borland C++ works with DYN_ALLOC only. # Special Notes on IBM C/C++ compilation: # The older C compiler (C Set/2) breaks, while optimizing, on deflate.c # and trees.c (generates incorrect code). The newer C++ compiler (C Set++) # doesn't but instead breaks on crypt.c in the initial version and up to # CSD level 003. Starting with CSD level 004, it doesn't break any longer. # Notes on Watcom C/C++ compilation for DOS with the PMODE/W extender: # # You need to add the following section to your \watcom\binb\wlsystem.lnk # file and also need to copy pmodew.exe to the same directory: # # system begin pmodew # option osname='PMODE/W' # libpath %WATCOM%\lib386 # libpath %WATCOM%\lib386\dos # op stub=pmodew.exe # format os2 le # end # # PMODE/W 1.16 or higher is required. default: @echo "Enter $(MAKE) -f os2/makefile.os2 target" @echo "where target is one of:" @echo " msc mscdos ibm ibmdyn ibmdebug ibmprof metaware borland" @echo " gcc gccdyn gcczlib gccdebug gccdos gccwin32 gccw32dyn" @echo " watcom watcom16 watcomdos watcom16dos pmodew" # MS C 6.00 for OS/2, 16-bit msc: $(MAKE) -f os2/makefile.os2 zips \ CC="cl -nologo -AL -Ocegit -Gs $(FP)" \ CFLAGS="-W1 -Zep -J -G2 -D__STDC__ -DOS2 -DASM_CRC" \ AS="ml -nologo -c -Zm -Cp" \ ASFLAGS="-D__LARGE__ -D__286" \ LDFLAGS="-F 2000 -Lp -Fe" \ LDFLAGS2="-link /noe /pm:vio" \ OUT="-Fo" \ OBJ=".obj" \ CRCA_O="crc_i86.obj" \ OBJA="match.obj" \ DEF="os2\zip.def" # MS C 6.00 for OS/2, 16-bit, debug mscdebug: $(MAKE) -f os2/makefile.os2 zips \ CC="cl -nologo -AL -Zi -Od $(FP)" \ CFLAGS="-W1 -Zep -J -G2 -D__STDC__ -DOS2 -DASM_CRC" \ AS="ml -nologo -c -Zim -Cp" \ ASFLAGS="-D__LARGE__ -D__286" \ LDFLAGS="-F 2000 -Lp -Fe" \ LDFLAGS2="-link /noe /pm:vio" \ OUT="-Fo" \ OBJ=".obj" \ CRCA_O="crc_i86.obj" \ OBJA="match.obj" \ DEF="os2\zip.def" # crosscompilation for MS-DOS with MS C 6.00 mscdos: $(MAKE) -f os2/makefile.os2 zips \ CC="cl -nologo -AL -Ocegit -Gs $(FP)" \ CFLAGS="-W1 -Zep -J -D__STDC__ -DDOS -DASM_CRC -DDYN_ALLOC" \ AS="ml -nologo -c -Zm -Cp" \ ASFLAGS="-D__LARGE__ -DDYN_ALLOC" \ LDFLAGS="-F 2000 -Lr -Fe" \ LDFLAGS2="-link /noe /exe" \ OUT="-Fo" \ OBJ=".obj" \ CRCA_O="crc_i86.obj" \ OBJA="match.obj" \ OBJ2="msdos.obj" OBJU2="msdos_.obj" \ OSDEP_H="msdos/osdep.h" ZIPUP_H="msdos/zipup.h" # IBM C Set/2, statically linked runtime ibm: $(MAKE) -f os2/makefile.os2 zips \ CC="icc -Q -O -Gs" \ CFLAGS="-Sm -Sp1 -DOS2 -DNO_ASM" \ AS="ml -nologo -c -Zm -Cp" \ ASFLAGS="" \ LDFLAGS="-B/ST:0x50000 -Fe" \ LDFLAGS2="" \ OUT="-Fo" \ OBJ=".obj" \ OBJA="" \ DEF="os2/zip.def" # IBM C Set/2, dynamically linked runtime ibmdyn: $(MAKE) -f os2/makefile.os2 zips \ CC="icc -Q -O -Gd -Gs" \ CFLAGS="-Sm -Sp1 -DOS2 -DNO_ASM" \ AS="ml -nologo -c -Zm -Cp" \ ASFLAGS="" \ LDFLAGS="-B/ST:0x50000 -Fe" \ LDFLAGS2="" \ OUT="-Fo" \ OBJ=".obj" \ OBJA="" \ DEF="os2/zip.def" # IBM C Set/2, debug version ibmdebug: $(MAKE) -f os2/makefile.os2 zips \ CC="icc -Q -Ti" \ CFLAGS="-Sm -Sp1 -DOS2 -DNO_ASM -Tm" \ AS="ml -nologo -c -Zim -Cp" \ ASFLAGS="" \ LDFLAGS="-B/ST:0x50000 -Fe" \ LDFLAGS2="" \ OUT="-Fo" \ OBJ=".obj" \ OBJA="" \ DEF="os2/zip.def" # IBM C Set/2, profiling version for PROFIT ibmprof: $(MAKE) -f os2/makefile.os2 zips \ CC="icc -Q -O -Gs -Gh -Ti" \ CFLAGS="-Sm -Sp1 -DOS2 -DNO_ASM" \ AS="ml -nologo -c -Zm -Cp" \ ASFLAGS="" \ LDFLAGS="-B/ST:0x50000 -Fe" \ LDFLAGS2="profit.obj" \ OUT="-Fo" \ OBJ=".obj" \ OBJA="" \ DEF="os2/zip.def" # Watcom C/386 9.0 or higher watcom: $(MAKE) -f os2/makefile.os2 zips \ CC="wcl386 -bt=os2v2 -zq -Ox -s" \ CFLAGS="-Zp1 -DOS2 -DNO_ASM" \ AS="wasm -zq -bt=os2v2 -3p" \ ASFLAGS="" \ LDFLAGS="-k0x50000 -x -l=os2v2 -Fe=" \ LDFLAGS2="" \ OUT="-Fo" \ OBJ=".obj" \ OBJA="" \ DIRSEP="\\" \ AS_DIRSEP="\\" # Watcom C/286 9.0 or higher watcom16: $(MAKE) -f os2/makefile.os2 zips \ CC="wcl -bt=os2 -zq -ml -Ox -s" \ CFLAGS="-Zp1 -DOS2 -DNO_ASM" \ AS="wasm -zq -bt=os2 -2p -ml" \ ASFLAGS="" \ LDFLAGS="/\"option newfiles\" -k0x3000 -x -l=os2 -Fe=" \ LDFLAGS2="" \ OUT="-Fo" \ OBJ=".obj" \ OBJA="" \ DIRSEP="\\" \ AS_DIRSEP="\\" # Watcom C/386 9.0 or higher, crosscompilation for DOS, DOS4GW extender watcomdos: $(MAKE) -f os2/makefile.os2 zips \ CC="wcl386 -bt=dos4g -zq -Ox -s" \ CFLAGS="-Zp1 -DDOS -DMSDOS -DASM_CRC" \ AS="wasm -zq -bt=dos4g -3p" \ ASFLAGS="-DWATCOM_DSEG" \ LDFLAGS="-k0x50000 -x -l=dos4g -Fe=" \ LDFLAGS2="" \ OUT="-Fo" \ OBJ=".obj" \ CRCA_O="crc_i386.obj" \ OBJA="match32.obj" \ OBJ2="msdos.obj" \ OBJU2="msdos_.obj" \ OSDEP_H="msdos/osdep.h" \ ZIPUP_H="msdos/zipup.h" \ DIRSEP="\\" \ AS_DIRSEP="\\" # Watcom C/386 9.0 or higher, crosscompilation for DOS, PMODE/W extender pmodew: $(MAKE) -f os2/makefile.os2 zips \ CC="wcl386 -bt=dos4g -zq -Ox -s" \ CFLAGS="-Zp1 -DDOS -DMSDOS -DASM_CRC" \ AS="wasm -zq -bt=dos4g -3p" \ ASFLAGS="-DWATCOM_DSEG" \ LDFLAGS="-k0x50000 -x -l=pmodew -Fe=" \ LDFLAGS2="" \ OUT="-Fo" \ OBJ=".obj" \ CRCA_O="crc_i386.obj" \ OBJA="match32.obj" \ OBJ2="msdos.obj" \ OBJU2="msdos_.obj" \ OSDEP_H="msdos/osdep.h" \ ZIPUP_H="msdos/zipup.h" \ DIRSEP="\\" \ AS_DIRSEP="\\" # Watcom C/286 9.0 or higher, crosscompilation for DOS watcom16dos: $(MAKE) -f os2/makefile.os2 zips \ CC="wcl -bt=dos -zq -ml -Ox -s" \ CFLAGS="-Zp1 -DDOS -DMSDOS -DDYN_ALLOC -DNO_ASM" \ AS="wasm -zq -bt=dos -2 -ml" \ ASFLAGS="-DDYN_ALLOC" \ LDFLAGS="-k0x2000 -x -l=dos -Fe=" \ LDFLAGS2="" \ OUT="-Fo" \ OBJ=".obj" \ OBJA="" \ OBJ2="msdos.obj" \ OBJU2="msdos_.obj" \ OSDEP_H="msdos/osdep.h" \ ZIPUP_H="msdos/zipup.h" \ DIRSEP="\\" \ AS_DIRSEP="\\" # MetaWare High C/C++ 3.2 metaware: $(MAKE) -f os2/makefile.os2 zips \ CC="hc -O2" \ CFLAGS="-D__32BIT__ -DOS2 -DNO_ASM" \ AS="ml -nologo -c -Zm -Cp" \ ASFLAGS="" \ LDFLAGS="-o " \ LDFLAGS2="" \ OUT="-o ./" \ OBJ=".obj" \ DEF="-Hdef=os2/zip.def" # Borland C++ borland: $(MAKE) -f os2/makefile.os2 zips \ CC="bcc -O" \ CFLAGS="-w- -DOS2 -DDYN_ALLOC -DNO_ASM" \ AS="ml -nologo -c -Zm -Cp" \ ASFLAGS="" \ LDFLAGS="-e" \ LDFLAGS2="" \ OUT="-o" \ OBJ=".obj" \ OBJA="" \ DEF="-sDos2/zip.def" # emx 0.9c, gcc, OMF format, statically linked C runtime and emx gcc: $(MAKE) -f os2/makefile.os2 zips \ CC="gcc -Zomf -O -Wimplicit" \ CFLAGS="-DOS2 -DASM_CRC" \ AS="gcc -Zomf" \ ASFLAGS="-Di386" \ LDFLAGS="-o ./" \ LDFLAGS2="-Zsys -Zstack 320 -s -Zsmall-conv" \ OUT="-o" \ OBJ=".obj" \ CRCA_O="crc_gcc.obj" \ OBJA="matchgcc.obj" \ DEF="os2/zip.def" # emx 0.9c, gcc, OMF format, dynamically linked C runtime and emx gccdyn: $(MAKE) -f os2/makefile.os2 zips \ CC="gcc -Zomf -O -Wimplicit" \ CFLAGS="-DOS2 -DASM_CRC" \ AS="gcc -Zomf" \ ASFLAGS="-Di386" \ LDFLAGS="-o ./" \ LDFLAGS2="-Zcrtdll -Zstack 320 -s" \ OUT="-o" \ OBJ=".obj" \ CRCA_O="crc_gcc.obj" \ OBJA="matchgcc.obj" \ DEF="os2/zip.def" # emx 0.9c, gcc, OMF format, statically linked zlib, C runtime, and emx gcczlib: $(MAKE) -f os2/makefile.os2 zips \ CC="gcc -Zomf -O -Wimplicit" \ CFLAGS="-DOS2 -DUSE_ZLIB" \ AS="gcc -Zomf" \ ASFLAGS="-Di386 -DUSE_ZLIB" \ LDFLAGS="-o ./" \ LDFLAGS2="-L. -lzlib -Zsys -Zstack 320 -s -Zsmall-conv" \ OUT="-o" \ OBJ=".obj" \ CRCA_O="" \ OBJA="" \ DEF="os2/zip.def" # emx 0.9c, gcc, a.out format, with debug info for gdb gccdebug: $(MAKE) -f os2/makefile.os2 zips \ CC="gcc -g -Wimplicit" \ CFLAGS="-DOS2 -DASM_CRC" \ AS="gcc" \ ASFLAGS="-Di386" \ LDFLAGS="-o ./" \ LDFLAGS2="" \ OUT="-o" \ OBJ=".o" \ CRCA_O="crc_gcc.o" \ OBJA="matchgcc.o" \ DEF="os2/zip.def" # emx 0.9c, gcc, a.out format, for MS-DOS gccdos: $(MAKE) -f os2/makefile.os2 zips \ CC="gcc -O -Wimplicit" \ CFLAGS="-DDOS -DMSDOS -DASM_CRC" \ AS="gcc" \ ASFLAGS="-Di386" \ LDFLAGS="-o ./" \ LDFLAGS2="-s -Zsmall-conv" \ OUT="-o" \ OBJ=".o" \ CRCA_O="crc_gcc.o" \ OBJA="matchgcc.o" \ OBJ2="msdos.o" \ OBJU2="msdos_.o" \ OSDEP_H="msdos/osdep.h" \ ZIPUP_H="msdos/zipup.h" # emx 0.9c, gcc, RSXNT 1.4, cross-compilation for Win32 gccwin32: $(MAKE) -f os2/makefile.os2 zips \ CC="gcc -Zwin32 -O -m486 -Wall" \ CFLAGS="-DWIN32 -DASM_CRC" \ AS="gcc -Zwin32" \ ASFLAGS="-Di386" \ LDFLAGS="-o ./" \ LDFLAGS2="-ladvapi32 -Zsys -Zsmall-conv -s" \ OUT="-o" \ OBJ=".o" \ CRCA_O="crc_gcc.o" \ OBJA="matchgcc.o" \ OBJ2="win32zip.o win32.o nt.o" \ OBJU2="win32_.o" \ OSDEP_H="win32/osdep.h" \ ZIPUP_H="win32/zipup.h" \ DEF="win32/zip.def" # emx 0.9c, gcc, RSXNT 1.4, cross-compilation for Win32, use emx C rtl DLL gccw32dyn: $(MAKE) -f os2/makefile.os2 zips \ CC="gcc -Zwin32 -Zcrtdll=crtrsxnt -O -m486 -Wall" \ CFLAGS="-DWIN32 -DASM_CRC" \ AS="gcc -Zwin32" \ ASFLAGS="-Di386" \ LDFLAGS="-o ./" \ LDFLAGS2="-ladvapi32 -s" \ OUT="-o" \ OBJ=".o" \ CRCA_O="crc_gcc.o" \ OBJA="matchgcc.o" \ OBJ2="win32zip.o win32.o nt.o" \ OBJU2="win32_.o" \ OSDEP_H="win32/osdep.h" \ ZIPUP_H="win32/zipup.h" \ DEF="win32/zip.def" # VPATH = .;os2 # variables #default settings for target dependent macros: DIRSEP = / AS_DIRSEP = / # LOCAL_OPTS = CCFLAGS = $(CFLAGS) $(LOCAL_OPTS) OSDEP_H = os2/osdep.h ZIPUP_H = os2/os2zip.h os2/zipup.h CRCA_O = OBJZ = zip$(OBJ) zipfile$(OBJ) zipup$(OBJ) fileio$(OBJ) util$(OBJ) \ crc32$(OBJ) $(CRCA_O) globals$(OBJ) \ deflate$(OBJ) trees$(OBJ) crypt$(OBJ) ttyio$(OBJ) OBJ2 = os2zip$(OBJ) os2$(OBJ) os2acl$(OBJ) OBJU = zipfile_$(OBJ) fileio_$(OBJ) util_$(OBJ) globals$(OBJ) OBJU2 = os2zip_$(OBJ) OBJN = zipnote$(OBJ) $(OBJU) $(OBJU2) OBJS = zipsplit$(OBJ) $(OBJU) $(OBJU2) OBJC = zipcloak$(OBJ) crc32_$(OBJ) crypt_$(OBJ) ttyio$(OBJ) $(OBJU) $(OBJU2) ZIP_H = zip.h ziperr.h tailor.h $(OSDEP_H) # rules .SUFFIXES: .c $(OBJ) .c$(OBJ): $(CC) -c -I. $(CCFLAGS) $< .asm$(OBJ): $(AS) $(ASFLAGS) $< $(ASEOL) # targets zips: zip.exe zipnote.exe zipsplit.exe zipcloak.exe zip$(OBJ): zip.c $(ZIP_H) revision.h crc32.h crypt.h ttyio.h zipfile$(OBJ): zipfile.c $(ZIP_H) crc32.h zipup$(OBJ): zipup.c $(ZIP_H) revision.h crc32.h crypt.h $(ZIPUP_H) fileio$(OBJ): fileio.c $(ZIP_H) crc32.h util$(OBJ): util.c $(ZIP_H) globals$(OBJ): globals.c $(ZIP_H) deflate$(OBJ): deflate.c $(ZIP_H) trees$(OBJ): trees.c $(ZIP_H) crc32$(OBJ): crc32.c $(ZIP_H) crc32.h crypt$(OBJ): crypt.c $(ZIP_H) crypt.h crc32.h ttyio.h ttyio$(OBJ): ttyio.c $(ZIP_H) crypt.h ttyio.h os2zip$(OBJ): os2/os2zip.c $(ZIP_H) os2/os2zip.h os2/os2acl.h $(CC) -c -I. $(CCFLAGS) os2$(DIRSEP)os2zip.c os2$(OBJ): os2/os2.c $(ZIP_H) os2/os2zip.h $(CC) -c -I. $(CCFLAGS) os2$(DIRSEP)os2.c os2acl$(OBJ): os2/os2acl.c os2/os2acl.h $(CC) -c -I. $(CCFLAGS) os2$(DIRSEP)os2acl.c msdos$(OBJ): msdos/msdos.c $(ZIP_H) $(CC) -c -I. $(CCFLAGS) msdos$(DIRSEP)msdos.c win32zip$(OBJ): win32/win32zip.c $(ZIP_H) win32/win32zip.h win32/nt.h $(CC) -c -I. $(CCFLAGS) win32$(DIRSEP)win32zip.c win32$(OBJ): win32/win32.c $(ZIP_H) win32/win32zip.h $(CC) -c -I. $(CCFLAGS) win32$(DIRSEP)win32.c nt$(OBJ): win32/nt.c win32/nt.h $(CC) -c -I. $(CCFLAGS) win32$(DIRSEP)nt.c crc_i86$(OBJ): msdos/crc_i86.asm # 16bit only $(AS) $(ASFLAGS) msdos$(AS_DIRSEP)crc_i86.asm $(ASEOL) crc_i386$(OBJ): win32/crc_i386.asm # 32bit, MASM $(AS) $(ASFLAGS) win32$(AS_DIRSEP)crc_i386.asm $(ASEOL) crc_gcc$(OBJ): crc_i386.S # 32bit, GNU AS $(AS) $(ASFLAGS) -x assembler-with-cpp -c -o $@ crc_i386.S match$(OBJ): msdos/match.asm $(AS) $(ASFLAGS) msdos$(AS_DIRSEP)match.asm $(ASEOL) match32$(OBJ): win32/match32.asm $(AS) $(ASFLAGS) win32$(AS_DIRSEP)match32.asm matchgcc$(OBJ): match.S $(AS) $(ASFLAGS) -x assembler-with-cpp -c -o $@ match.S zipcloak$(OBJ): zipcloak.c $(ZIP_H) revision.h crc32.h crypt.h ttyio.h zipnote$(OBJ): zipnote.c $(ZIP_H) revision.h zipsplit$(OBJ): zipsplit.c $(ZIP_H) revision.h zipfile_$(OBJ): zipfile.c $(ZIP_H) crc32.h $(CC) -c -I. $(CCFLAGS) -DUTIL $(OUT)$@ zipfile.c fileio_$(OBJ): fileio.c $(ZIP_H) crc32.h $(CC) -c -I. $(CCFLAGS) -DUTIL $(OUT)$@ fileio.c util_$(OBJ): util.c $(ZIP_H) os2/os2zip.h $(CC) -c -I. $(CCFLAGS) -DUTIL $(OUT)$@ util.c crc32_$(OBJ): crc32.c $(ZIP_H) crc32.h $(CC) -c -I. $(CCFLAGS) -DUTIL $(OUT)$@ crc32.c crypt_$(OBJ): crypt.c $(ZIP_H) crypt.h crc32.h ttyio.h $(CC) -c -I. $(CCFLAGS) -DUTIL $(OUT)$@ crypt.c os2zip_$(OBJ): os2/os2zip.c $(ZIP_H) os2/os2zip.h $(CC) -c -I. $(CCFLAGS) -DUTIL $(OUT)$@ os2$(DIRSEP)os2zip.c msdos_$(OBJ): msdos/msdos.c $(ZIP_H) $(CC) -c -I. $(CCFLAGS) -DUTIL $(OUT)$@ msdos$(DIRSEP)msdos.c win32_$(OBJ): win32/win32.c $(ZIP_H) win32/win32zip.h $(CC) -c -I. $(CCFLAGS) -DUTIL $(OUT)$@ win32$(DIRSEP)win32.c zip.exe: $(OBJZ) $(OBJ2) $(OBJA) $(CC) $(LDFLAGS)$@ $(DEF) $(OBJZ) $(OBJ2) $(OBJA) $(LDFLAGS2) zipcloak.exe: $(OBJC) $(CC) $(LDFLAGS)$@ $(DEF) $(OBJC) $(LDFLAGS2) zipnote.exe: $(OBJN) $(CC) $(LDFLAGS)$@ $(DEF) $(OBJN) $(LDFLAGS2) zipsplit.exe: $(OBJS) $(CC) $(LDFLAGS)$@ $(DEF) $(OBJS) $(LDFLAGS2) zip30/os2/match32.asm0100644000076400000060000001552010304173030012421 0ustar edisk;=========================================================================== ; Copyright (c) 1990-2005 Info-ZIP. All rights reserved. ; ; See the accompanying file LICENSE, version 2005-Feb-10 or later ; (the contents of which are also included in zip.h) for terms of use. ; If, for some reason, all these files are missing, the Info-ZIP license ; also may be found at: ftp://ftp.info-zip.org/pub/infozip/license.html ;=========================================================================== ; ; match32.asm by Jean-loup Gailly. ; match32.asm, optimized version of longest_match() in deflate.c ; To be used only with 32 bit flat model. To simplify the code, the option ; -DDYN_ALLOC is not supported. ; This file is only optional. If you don't have an assembler, use the ; C version (add -DNO_ASM to CFLAGS in makefile and remove match.o ; from OBJI). If you have reduced WSIZE in zip.h, then make sure this is ; assembled with an equivalent -DWSIZE=. ; Caution: this module works for IBM's C/C++ compiler versions 2 and 3 ; and for Watcom's 32-bit C/C++ compiler. Both pass the first (and only) ; argument for longest_match in the EAX register, not on the stack, with ; the default calling conventions (_System would use the stack). ; ;============================================================================== ; ; Do NOT assemble this source if external crc32 routine from zlib gets used. ; IFNDEF USE_ZLIB ; .386 name match BSS32 segment dword USE32 public 'BSS' extrn window : byte extrn prev : word extrn prev_length : dword extrn strstart : dword extrn match_start : dword extrn max_chain_length : dword extrn good_match : dword extrn nice_match : dword BSS32 ends CODE32 segment dword USE32 public 'CODE' assume cs:CODE32, ds:FLAT, ss:FLAT public match_init public longest_match ifndef WSIZE WSIZE equ 32768 ; keep in sync with zip.h ! endif MIN_MATCH equ 3 MAX_MATCH equ 258 MIN_LOOKAHEAD equ (MAX_MATCH+MIN_MATCH+1) MAX_DIST equ (WSIZE-MIN_LOOKAHEAD) ; initialize or check the variables used in match.asm. match_init proc near ret match_init endp ; ----------------------------------------------------------------------- ; Set match_start to the longest match starting at the given string and ; return its length. Matches shorter or equal to prev_length are discarded, ; in which case the result is equal to prev_length and match_start is ; garbage. ; IN assertions: cur_match is the head of the hash chain for the current ; string (strstart) and its distance is <= MAX_DIST, and prev_length >= 1 ; int longest_match(cur_match) longest_match proc near ; return address ; esp+16 push ebp ; esp+12 push edi ; esp+8 push esi ; esp+4 lea ebx,window add ebx,2 window_off equ dword ptr [esp] push ebx ; esp ; match equ esi ; scan equ edi ; chain_length equ ebp ; best_len equ ebx ; limit equ edx mov esi,eax ; cur_match mov edx,strstart mov ebp,max_chain_length ; chain_length = max_chain_length mov edi,edx sub edx,MAX_DIST ; limit = strstart-MAX_DIST cld ; string ops increment esi and edi jae short limit_ok sub edx,edx ; limit = NIL limit_ok: add edi,window_off ; edi = offset(window + strstart + 2) mov ebx,prev_length ; best_len = prev_length mov cx,[edi-2] ; cx = scan[0..1] mov ax,[ebx+edi-3] ; ax = scan[best_len-1..best_len] cmp ebx,good_match ; do we have a good match already? jb do_scan shr ebp,2 ; chain_length >>= 2 jmp short do_scan align 4 ; align destination of branch long_loop: ; at this point, edi == scan+2, esi == cur_match mov ax,[ebx+edi-3] ; ax = scan[best_len-1..best_len] mov cx,[edi-2] ; cx = scan[0..1] short_loop: ; at this point, edi == scan+2, esi == cur_match, ; ax = scan[best_len-1..best_len] and cx = scan[0..1] and esi,WSIZE-1 ; not needed if WSIZE=32768 dec ebp ; --chain_length shl esi,1 ; cur_match as word index mov si,prev[esi] ; cur_match = prev[cur_match] ; top word of esi is still 0 jz the_end cmp esi,edx ; cur_match <= limit ? jbe short the_end do_scan: cmp ax,word ptr window[ebx+esi-1] ; check match at best_len-1 jne short_loop cmp cx,word ptr window[esi] ; check min_match_length match jne short_loop add esi,window_off ; esi = match mov ecx,(MAX_MATCH-2)/2 ; scan for at most MAX_MATCH bytes mov eax,edi ; eax = scan+2 repe cmpsw ; loop until mismatch je maxmatch ; match of length MAX_MATCH? mismatch: mov cl,[edi-2] ; mismatch on first or second byte? xchg eax,edi ; edi = scan+2, eax = end of scan sub cl,[esi-2] ; cl = 0 if first bytes equal sub eax,edi ; eax = len sub esi,window_off ; esi = match - (2 + offset(window)) sub esi,eax ; esi = cur_match (= match - len) sub cl,1 ; set carry if cl == 0 (can't use DEC) adc eax,0 ; eax = carry ? len+1 : len cmp eax,ebx ; len > best_len ? jle long_loop mov match_start,esi ; match_start = cur_match mov ebx,eax ; ebx = best_len = len ifdef FULL_SEARCH cmp eax,MAX_MATCH ; len >= MAX_MATCH ? else cmp eax,nice_match ; len >= nice_match ? endif jl long_loop the_end: mov eax,ebx ; result = eax = best_len pop ebx pop esi pop edi pop ebp ret maxmatch: ; come here if maximum match cmpsb ; increment esi and edi jmp mismatch ; force match_length = MAX_LENGTH longest_match endp CODE32 ends ; ENDIF ; !USE_ZLIB ; end zip30/os2/os2.c0100644000076400000060000003310410304175400011326 0ustar edisk/* Copyright (c) 1990-2005 Info-ZIP. All rights reserved. See the accompanying file LICENSE, version 2005-Feb-10 or later (the contents of which are also included in zip.h) for terms of use. If, for some reason, all these files are missing, the Info-ZIP license also may be found at: ftp://ftp.info-zip.org/pub/infozip/license.html */ #include "zip.h" #ifndef UTIL /* the companion #endif is a bit of ways down ... */ #include #if defined(__IBMC__) || defined(MSC) #include #endif /* Extra malloc() space in names for cutpath() */ #define PAD 0 #define PATH_END '/' #include "os2zip.h" /* Library functions not in (most) header files */ extern char *label; local ulg label_time = 0; local ulg label_mode = 0; local time_t label_utim = 0; /* Local functions */ local char *readd OF((DIR *)); local char *readd(d) DIR *d; /* directory stream to read from */ /* Return a pointer to the next name in the directory stream d, or NULL if no more entries or an error occurs. */ { struct dirent *e; e = readdir(d); return e == NULL ? (char *) NULL : e->d_name; } int wild(w) char *w; /* path/pattern to match */ /* If not in exclude mode, expand the pattern based on the contents of the file system. Return an error code in the ZE_ class. */ { DIR *d; /* stream for reading directory */ char *e; /* name found in directory */ int r; /* temporary variable */ char *n; /* constructed name from directory */ int f; /* true if there was a match */ char *a; /* alloc'ed space for name */ char *p; /* path */ char *q; /* name */ char v[5]; /* space for device current directory */ if (volume_label == 1) { volume_label = 2; label = getVolumeLabel((w != NULL && w[1] == ':') ? to_up(w[0]) : '\0', &label_time, &label_mode, &label_utim); if (label != NULL) { newname(label, 0, 0); } if (w == NULL || (w[1] == ':' && w[2] == '\0')) return ZE_OK; /* "zip -$ foo a:" can be used to force drive name */ } if (w == NULL) return ZE_OK; /* special handling of stdin request */ if (strcmp(w, "-") == 0) /* if compressing stdin */ return newname(w, 0, 0); /* Allocate and copy pattern */ if ((p = a = malloc(strlen(w) + 1)) == NULL) return ZE_MEM; strcpy(p, w); /* catch special case: treat "*.*" as "*" for DOS-impaired people */ r = strlen(p); if (strcmp(p + r - 3, "*.*") == 0) p[r - 2] = '\0'; /* Normalize path delimiter as '/'. */ for (q = p; *q; q++) /* use / consistently */ if (*q == '\\') *q = '/'; /* Only name can have special matching characters */ if ((q = isshexp(p)) != NULL && (strrchr(q, '/') != NULL || strrchr(q, ':') != NULL)) { free((zvoid *)a); return ZE_PARMS; } /* Separate path and name into p and q */ if ((q = strrchr(p, '/')) != NULL && (q == p || q[-1] != ':')) { *q++ = '\0'; /* path/name -> path, name */ if (*p == '\0') /* path is just / */ p = strcpy(v, "/."); } else if ((q = strrchr(p, ':')) != NULL) { /* has device and no or root path */ *q++ = '\0'; p = strcat(strcpy(v, p), ":"); /* copy device as path */ if (*q == '/') /* -> device:/., name */ { strcat(p, "/"); q++; } strcat(p, "."); } else if (recurse && (strcmp(p, ".") == 0 || strcmp(p, "..") == 0)) { /* current or parent directory */ /* I can't understand Mark's code so I am adding a hack here to get * "zip -r foo ." to work. Allow the dubious "zip -r foo .." but * reject "zip -rm foo ..". */ if (dispose && strcmp(p, "..") == 0) ziperr(ZE_PARMS, "cannot remove parent directory"); q = "*"; } else /* no path or device */ { q = p; p = strcpy(v, "."); } if (recurse && *q == '\0') { q = "*"; } /* Search that level for matching names */ if ((d = opendir(p)) == NULL) { free((zvoid *)a); return ZE_MISS; } if ((r = strlen(p)) > 1 && (strcmp(p + r - 2, ":.") == 0 || strcmp(p + r - 2, "/.") == 0)) *(p + r - 1) = '\0'; f = 0; while ((e = readd(d)) != NULL) { if (strcmp(e, ".") && strcmp(e, "..") && MATCH(q, e, 0)) { f = 1; if (strcmp(p, ".") == 0) { /* path is . */ r = procname(e, 0); /* name is name */ if (r) { f = 0; break; } } else { if ((n = malloc(strlen(p) + strlen(e) + 2)) == NULL) { free((zvoid *)a); closedir(d); return ZE_MEM; } n = strcpy(n, p); if (n[r = strlen(n) - 1] != '/' && n[r] != ':') strcat(n, "/"); r = procname(strcat(n, e), 0); /* name is path/name */ free((zvoid *)n); if (r) { f = 0; break; } } } } closedir(d); /* Done */ free((zvoid *)a); return f ? ZE_OK : ZE_MISS; } int procname(n, caseflag) char *n; /* name to process */ int caseflag; /* true to force case-sensitive match */ /* Process a name or sh expression to operate on (or exclude). Return an error code in the ZE_ class. */ { char *a; /* path and name for recursion */ DIR *d; /* directory stream from opendir() */ char *e; /* pointer to name from readd() */ int m; /* matched flag */ char *p; /* path for recursion */ struct stat s; /* result of stat() */ struct zlist far *z; /* steps through zfiles list */ if (n == NULL) /* volume_label request in freshen|delete mode ?? */ return ZE_OK; if (strcmp(n, "-") == 0) /* if compressing stdin */ return newname(n, 0, caseflag); else if (LSSTAT(n, &s) #if defined(__TURBOC__) || defined(__WATCOMC__) /* For these 2 compilers, stat() succeeds on wild card names! */ || isshexp(n) #endif ) { /* Not a file or directory--search for shell expression in zip file */ p = ex2in(n, 0, (int *)NULL); /* shouldn't affect matching chars */ m = 1; for (z = zfiles; z != NULL; z = z->nxt) { if (MATCH(p, z->iname, caseflag)) { z->mark = pcount ? filter(z->zname, caseflag) : 1; if (verbose) fprintf(mesg, "zip diagnostic: %scluding %s\n", z->mark ? "in" : "ex", z->name); m = 0; } } free((zvoid *)p); return m ? ZE_MISS : ZE_OK; } /* Live name--use if file, recurse if directory */ for (p = n; *p; p++) /* use / consistently */ if (*p == '\\') *p = '/'; if ((s.st_mode & S_IFDIR) == 0) { /* add or remove name of file */ if ((m = newname(n, 0, caseflag)) != ZE_OK) return m; } else { /* Add trailing / to the directory name */ if ((p = malloc(strlen(n)+2)) == NULL) return ZE_MEM; if (strcmp(n, ".") == 0 || strcmp(n, "/.") == 0) { *p = '\0'; /* avoid "./" prefix and do not create zip entry */ } else { strcpy(p, n); a = p + strlen(p); if (a[-1] != '/') strcpy(a, "/"); if (dirnames && (m = newname(p, 1, caseflag)) != ZE_OK) { free((zvoid *)p); return m; } } /* recurse into directory */ if (recurse && (d = opendir(n)) != NULL) { while ((e = readd(d)) != NULL) { if (strcmp(e, ".") && strcmp(e, "..")) { if ((a = malloc(strlen(p) + strlen(e) + 1)) == NULL) { closedir(d); free((zvoid *)p); return ZE_MEM; } strcat(strcpy(a, p), e); if ((m = procname(a, caseflag)) != ZE_OK) /* recurse on name */ { if (m == ZE_MISS) zipwarn("name not matched: ", a); else ziperr(m, a); } free((zvoid *)a); } } closedir(d); } free((zvoid *)p); } /* (s.st_mode & S_IFDIR) == 0) */ return ZE_OK; } char *ex2in(x, isdir, pdosflag) char *x; /* external file name */ int isdir; /* input: x is a directory */ int *pdosflag; /* output: force MSDOS file attributes? */ /* Convert the external file name to a zip file name, returning the malloc'ed string or NULL if not enough memory. */ { char *n; /* internal file name (malloc'ed) */ char *t; /* shortened name */ int dosflag; dosflag = dosify || IsFileSystemFAT(x) || (x == label); if (!dosify && use_longname_ea && (t = GetLongPathEA(x)) != NULL) { x = t; dosflag = 0; } /* Find starting point in name before doing malloc */ /* Strip drive specification */ t = *x && *(x + 1) == ':' ? x + 2 : x; /* Strip "//host/share/" part of a UNC name */ if ((!strncmp(x,"//",2) || !strncmp(x,"\\\\",2)) && (x[2] != '\0' && x[2] != '/' && x[2] != '\\')) { n = x + 2; while (*n != '\0' && *n != '/' && *n != '\\') n++; /* strip host name */ if (*n != '\0') { n++; while (*n != '\0' && *n != '/' && *n != '\\') n++; /* strip `share' name */ } if (*n != '\0') t = n + 1; } /* Strip leading "/" to convert an absolute path into a relative path */ while (*t == '/' || *t == '\\') t++; /* Strip leading "./" as well as drive letter */ while (*t == '.' && (t[1] == '/' || t[1] == '\\')) t += 2; /* Make changes, if any, to the copied name (leave original intact) */ for (n = t; *n; n++) if (*n == '\\') *n = '/'; if (!pathput) t = last(t, PATH_END); /* Malloc space for internal name and copy it */ if ((n = malloc(strlen(t) + 1)) == NULL) return NULL; strcpy(n, t); if (dosify) msname(n); /* Returned malloc'ed name */ if (pdosflag) *pdosflag = dosflag; return n; } char *in2ex(n) char *n; /* internal file name */ /* Convert the zip file name to an external file name, returning the malloc'ed string or NULL if not enough memory. */ { char *x; /* external file name */ if ((x = malloc(strlen(n) + 1 + PAD)) == NULL) return NULL; strcpy(x, n); return x; } void stamp(f, d) char *f; /* name of file to change */ ulg d; /* dos-style time to change it to */ /* Set last updated and accessed time of file f to the DOS time d. */ { SetFileTime(f, d); } ulg filetime(f, a, n, t) char *f; /* name of file to get info on */ ulg *a; /* return value: file attributes */ long *n; /* return value: file size */ iztimes *t; /* return value: access, modific. and creation times */ /* If file *f does not exist, return 0. Else, return the file's last modified date and time as an MSDOS date and time. The date and time is returned in a long with the date most significant to allow unsigned integer comparison of absolute times. Also, if a is not a NULL pointer, store the file attributes there, with the high two bytes being the Unix attributes, and the low byte being a mapping of that to DOS attributes. If n is not NULL, store the file size there. If t is not NULL, the file's access, modification and creation times are stored there as UNIX time_t values. If f is "-", use standard input as the file. If f is a device, return a file size of -1 */ { struct stat s; /* results of stat() */ char *name; ulg r; unsigned int len = strlen(f); int isstdin = !strcmp(f, "-"); if (f == label) { if (a != NULL) *a = label_mode; if (n != NULL) *n = -2L; /* convention for a label name */ if (t != NULL) t->atime = t->mtime = t->ctime = label_utim; return label_time; } if ((name = malloc(len + 1)) == NULL) { ZIPERR(ZE_MEM, "filetime"); } strcpy(name, f); if (name[len - 1] == '/') name[len - 1] = '\0'; /* not all systems allow stat'ing a file with / appended */ if (isstdin) { /* it is common for some PC based compilers to fail with fstat() on devices or pipes */ if (fstat(fileno(stdin), &s) != 0) { s.st_mode = S_IFREG; s.st_size = -1L; } time(&s.st_ctime); s.st_atime = s.st_mtime = s.st_ctime; } else if (LSSTAT(name, &s) != 0) { /* Accept about any file kind including directories * (stored with trailing / with -r option) */ free(name); return 0; } if (a != NULL) { *a = ((ulg)s.st_mode << 16) | (isstdin ? 0L : (ulg)GetFileMode(name)); } if (n != NULL) *n = (s.st_mode & S_IFMT) == S_IFREG ? s.st_size : -1L; #ifdef __WATCOMC__ /* of course, Watcom always has to make an exception */ if (s.st_atime == 312764400) s.st_atime = s.st_mtime; if (s.st_ctime == 312764400) s.st_ctime = s.st_mtime; #endif if (t != NULL) { t->atime = s.st_atime; t->mtime = s.st_mtime; t->ctime = s.st_ctime; } r = GetFileTime(name); free(name); return r; } int deletedir(d) char *d; /* directory to delete */ /* Delete the directory *d if it is empty, do nothing otherwise. Return the result of rmdir(), delete(), or system(). */ { return rmdir(d); } #if defined MY_ZCALLOC /* Special zcalloc function for MEMORY16 (MSDOS/OS2) */ #ifdef MSC /* Microsoft C */ zvoid far *zcalloc (unsigned items, unsigned size) { return (zvoid far *)halloc((long)items, size); } zvoid zcfree (zvoid far *ptr) { hfree((void huge *)ptr); } #endif /* MSC */ #endif /* MY_ZCALLOC */ #endif /* !UTIL */ zip30/os2/os2acl.c0100644000076400000060000002240510154332176012020 0ustar edisk/* Copyright (c) 1990-2000 Info-ZIP. All rights reserved. See the accompanying file LICENSE, version 2000-Apr-09 or later (the contents of which are also included in zip.h) for terms of use. If, for some reason, all these files are missing, the Info-ZIP license also may be found at: ftp://ftp.info-zip.org/pub/infozip/license.html */ /* os2acl.c - access to OS/2 (LAN Server) ACLs * * Author: Kai Uwe Rommel * Created: Mon Aug 08 1994 * */ /* * supported 32-bit compilers: * - emx+gcc * - IBM C Set++ 2.1 or newer * - Watcom C/C++ 10.0 or newer * * supported 16-bit compilers: * - MS C 6.00A * - Watcom C/C++ 10.0 or newer * * supported OS/2 LAN environments: * - IBM LAN Server/Requester 3.0, 4.0 and 5.0 (Warp Server) * - IBM Peer 1.0 (Warp Connect) */ #ifdef KUR static char *rcsid = "$Id: os2acl.c,v 1.3 1996/04/03 19:18:27 rommel Exp rommel $"; static char *rcsrev = "$Revision: 1.3 $"; #endif /* * $Log: os2acl.c,v $ * Revision 1.3 1996/04/03 19:18:27 rommel * minor fixes * * Revision 1.2 1996/03/30 22:03:52 rommel * avoid frequent dynamic allocation for every call * streamlined code * * Revision 1.1 1996/03/30 09:35:00 rommel * Initial revision * */ #include #include #include #include #include #define INCL_NOPM #define INCL_DOS #define INCL_DOSERRORS #include #include "os2/os2acl.h" #define UNLEN 20 #if defined(__WATCOMC__) && defined(__386__) && !defined(__32BIT__) #define __32BIT__ #endif #ifdef __32BIT__ typedef ULONG U_INT; #ifdef __EMX__ #define PSTR16 _far16ptr #define PTR16(x) _emx_32to16(x) #else /* other 32-bit */ #define PSTR16 PCHAR16 #define PTR16(x) ((PCHAR16)(x)) #endif #else /* 16-bit */ typedef USHORT U_INT; #define PSTR16 PSZ #define PTR16(x) (x) #endif typedef struct access_list { char acl_ugname[UNLEN+1]; char acl_pad; USHORT acl_access; } ACCLIST; typedef struct access_info { PSTR16 acc_resource_name; USHORT acc_attr; USHORT acc_count; } ACCINFO; static ACCINFO *ai; static char *path, *data; #ifdef __32BIT__ #ifdef __EMX__ static USHORT (APIENTRY *_NetAccessGetInfo)(PSZ pszServer, PSZ pszResource, USHORT sLevel, PVOID pbBuffer, USHORT cbBuffer, PUSHORT pcbTotalAvail); static USHORT (APIENTRY *_NetAccessSetInfo)(PSZ pszServer, PSZ pszResource, USHORT sLevel, PVOID pbBuffer, USHORT cbBuffer, USHORT sParmNum); static USHORT (APIENTRY *_NetAccessAdd)(PSZ pszServer, USHORT sLevel, PVOID pbBuffer, USHORT cbBuffer); USHORT NetAccessGetInfo(PSZ pszServer, PSZ pszResource, USHORT sLevel, PVOID pbBuffer, USHORT cbBuffer, PUSHORT pcbTotalAvail) { return (USHORT) (_THUNK_PROLOG (4+4+2+4+2+4); _THUNK_FLAT (pszServer); _THUNK_FLAT (pszResource); _THUNK_SHORT (sLevel); _THUNK_FLAT (pbBuffer); _THUNK_SHORT (cbBuffer); _THUNK_FLAT (pcbTotalAvail); _THUNK_CALLI (_emx_32to16(_NetAccessGetInfo))); } USHORT NetAccessSetInfo(PSZ pszServer, PSZ pszResource, USHORT sLevel, PVOID pbBuffer, USHORT cbBuffer, USHORT sParmNum) { return (USHORT) (_THUNK_PROLOG (4+4+2+4+2+2); _THUNK_FLAT (pszServer); _THUNK_FLAT (pszResource); _THUNK_SHORT (sLevel); _THUNK_FLAT (pbBuffer); _THUNK_SHORT (cbBuffer); _THUNK_SHORT (sParmNum); _THUNK_CALLI (_emx_32to16(_NetAccessSetInfo))); } USHORT NetAccessAdd(PSZ pszServer, USHORT sLevel, PVOID pbBuffer, USHORT cbBuffer) { return (USHORT) (_THUNK_PROLOG (4+2+4+2); _THUNK_FLAT (pszServer); _THUNK_SHORT (sLevel); _THUNK_FLAT (pbBuffer); _THUNK_SHORT (cbBuffer); _THUNK_CALLI (_emx_32to16(_NetAccessAdd))); } #else /* other 32-bit */ APIRET16 (* APIENTRY16 NetAccessGetInfo)(PCHAR16 pszServer, PCHAR16 pszResource, USHORT sLevel, PVOID16 pbBuffer, USHORT cbBuffer, PVOID16 pcbTotalAvail); APIRET16 (* APIENTRY16 NetAccessSetInfo)(PCHAR16 pszServer, PCHAR16 pszResource, USHORT sLevel, PVOID16 pbBuffer, USHORT cbBuffer, USHORT sParmNum); APIRET16 (* APIENTRY16 NetAccessAdd)(PCHAR16 pszServer, USHORT sLevel, PVOID16 pbBuffer, USHORT cbBuffer); #define _NetAccessGetInfo NetAccessGetInfo #define _NetAccessSetInfo NetAccessSetInfo #define _NetAccessAdd NetAccessAdd #if !defined(__IBMC__) || !defined(__TILED__) #define _tmalloc malloc #define _tfree free #endif #endif #else /* 16-bit */ USHORT (APIENTRY *NetAccessGetInfo)(PSZ pszServer, PSZ pszResource, USHORT sLevel, PVOID pbBuffer, USHORT cbBuffer, PUSHORT pcbTotalAvail); USHORT (APIENTRY *NetAccessSetInfo)(PSZ pszServer, PSZ pszResource, USHORT sLevel, PVOID pbBuffer, USHORT cbBuffer, USHORT sParmNum); USHORT (APIENTRY *NetAccessAdd)(PSZ pszServer, USHORT sLevel, PVOID pbBuffer, USHORT cbBuffer); #define _NetAccessGetInfo NetAccessGetInfo #define _NetAccessSetInfo NetAccessSetInfo #define _NetAccessAdd NetAccessAdd #define _tmalloc malloc #define _tfree free #define DosQueryProcAddr(handle, ord, name, funcptr) \ DosGetProcAddr(handle, name, funcptr) #define DosQueryCurrentDir DosQCurDir #define DosQueryCurrentDisk DosQCurDisk #endif static BOOL acl_init(void) { static BOOL initialized, netapi_avail; HMODULE netapi; char buf[256]; if (initialized) return netapi_avail; initialized = TRUE; if (DosLoadModule(buf, sizeof(buf), "NETAPI", &netapi)) return FALSE; if (DosQueryProcAddr(netapi, 0, "NETACCESSGETINFO", (PFN *) &_NetAccessGetInfo) || DosQueryProcAddr(netapi, 0, "NETACCESSSETINFO", (PFN *) &_NetAccessSetInfo) || DosQueryProcAddr(netapi, 0, "NETACCESSADD", (PFN *) &_NetAccessAdd)) return FALSE; #if defined(__WATCOMC__) && defined(__386__) NetAccessGetInfo = (PVOID) (ULONG) (PVOID16) NetAccessGetInfo; NetAccessSetInfo = (PVOID) (ULONG) (PVOID16) NetAccessSetInfo; NetAccessAdd = (PVOID) (ULONG) (PVOID16) NetAccessAdd; #endif if ((path = _tmalloc(CCHMAXPATH)) == NULL) return FALSE; if ((data = _tmalloc(ACL_BUFFERSIZE)) == NULL) return FALSE; if ((ai = _tmalloc(sizeof(ACCINFO))) == NULL) return -1; netapi_avail = TRUE; return netapi_avail; } static void acl_mkpath(char *buffer, const char *source) { char *ptr; static char cwd[CCHMAXPATH]; static U_INT cwdlen; U_INT cdrive; ULONG drivemap; if (isalpha((int)source[0]) && source[1] == ':') buffer[0] = 0; /* fully qualified names */ else { if (cwd[0] == 0) { DosQueryCurrentDisk(&cdrive, &drivemap); cwd[0] = (char)(cdrive + '@'); cwd[1] = ':'; cwd[2] = '\\'; cwdlen = sizeof(cwd) - 3; DosQueryCurrentDir(0, cwd + 3, &cwdlen); cwdlen = strlen(cwd); } if (source[0] == '/' || source[0] == '\\') { if (source[1] == '/' || source[1] == '\\') buffer[0] = 0; /* UNC names */ else { strncpy(buffer, cwd, 2); buffer[2] = 0; } } else { strcpy(buffer, cwd); if (cwd[cwdlen - 1] != '\\' && cwd[cwdlen - 1] != '/') strcat(buffer, "/"); } } strcat(buffer, source); for (ptr = buffer; *ptr; ptr++) if (*ptr == '/') *ptr = '\\'; if (ptr[-1] == '\\') ptr[-1] = 0; strupr(buffer); } static int acl_bin2text(char *data, char *text) { ACCINFO *ai; ACCLIST *al; U_INT cnt, offs; ai = (ACCINFO *) data; al = (ACCLIST *) (data + sizeof(ACCINFO)); offs = sprintf(text, "ACL1:%X,%d\n", ai -> acc_attr, ai -> acc_count); for (cnt = 0; cnt < ai -> acc_count; cnt++) offs += sprintf(text + offs, "%s,%X\n", al[cnt].acl_ugname, al[cnt].acl_access); return strlen(text); } int acl_get(char *server, const char *resource, char *buffer) { USHORT datalen; PSZ srv = NULL; int rc; if (!acl_init()) return -1; if (server) srv = server; acl_mkpath(path, resource); datalen = 0; rc = NetAccessGetInfo(srv, path, 1, data, ACL_BUFFERSIZE, &datalen); if (rc == 0) acl_bin2text(data, buffer); return rc; } static int acl_text2bin(char *data, char *text, char *path) { ACCINFO *ai; ACCLIST *al; char *ptr, *ptr2; U_INT cnt; ai = (ACCINFO *) data; ai -> acc_resource_name = PTR16(path); if (sscanf(text, "ACL1:%hX,%hd", &ai -> acc_attr, &ai -> acc_count) != 2) return ERROR_INVALID_PARAMETER; al = (ACCLIST *) (data + sizeof(ACCINFO)); ptr = strchr(text, '\n') + 1; for (cnt = 0; cnt < ai -> acc_count; cnt++) { ptr2 = strchr(ptr, ','); strncpy(al[cnt].acl_ugname, ptr, ptr2 - ptr); al[cnt].acl_ugname[ptr2 - ptr] = 0; sscanf(ptr2 + 1, "%hx", &al[cnt].acl_access); ptr = strchr(ptr, '\n') + 1; } return sizeof(ACCINFO) + ai -> acc_count * sizeof(ACCLIST); } int acl_set(char *server, const char *resource, char *buffer) { USHORT datalen; PSZ srv = NULL; if (!acl_init()) return -1; if (server) srv = server; acl_mkpath(path, resource); ai -> acc_resource_name = PTR16(path); ai -> acc_attr = 0; ai -> acc_count = 0; NetAccessAdd(srv, 1, ai, sizeof(ACCINFO)); /* Ignore any errors, most probably because ACL already exists. */ /* In any such case, try updating the existing ACL. */ datalen = acl_text2bin(data, buffer, path); return NetAccessSetInfo(srv, path, 1, data, datalen, 0); } /* end of os2acl.c */ zip30/os2/os2acl.h0100644000076400000060000000151307076031362012024 0ustar edisk/* Copyright (c) 1990-2000 Info-ZIP. All rights reserved. See the accompanying file LICENSE, version 2000-Apr-09 or later (the contents of which are also included in zip.h) for terms of use. If, for some reason, all these files are missing, the Info-ZIP license also may be found at: ftp://ftp.info-zip.org/pub/infozip/license.html */ /* os2acl.h * * Author: Kai Uwe Rommel * Created: Fri Mar 29 1996 */ /* $Id: os2acl.h,v 1.1 1996/03/30 09:35:00 rommel Exp rommel $ */ /* * $Log: os2acl.h,v $ * Revision 1.1 1996/03/30 09:35:00 rommel * Initial revision * */ #ifndef _OS2ACL_H #define _OS2ACL_H #define ACL_BUFFERSIZE 4096 int acl_get(char *server, const char *resource, char *buffer); int acl_set(char *server, const char *resource, char *buffer); #endif /* _OS2ACL_H */ /* end of os2acl.h */ zip30/os2/os2zip.c0100644000076400000060000006752510304175670012100 0ustar edisk/* * @(#)dir.c 1.4 87/11/06 Public Domain. * * A public domain implementation of BSD directory routines for * MS-DOS. Written by Michael Rendell ({uunet,utai}michael@garfield), * August 1987 * * Ported to OS/2 by Kai Uwe Rommel * Addition of other OS/2 file system specific code * Placed into the public domain */ /* does also contain EA access code for use in ZIP */ #ifdef OS2 #if defined(__EMX__) && !defined(__32BIT__) # define __32BIT__ #endif #include "zip.h" #include #include #include #ifndef __BORLANDC__ #include #endif #define INCL_NOPM #define INCL_DOSNLS #define INCL_DOSERRORS #include #include "os2zip.h" #include "os2acl.h" #ifndef max #define max(a, b) ((a) < (b) ? (b) : (a)) #endif #ifdef __32BIT__ #define DosFindFirst(p1, p2, p3, p4, p5, p6) \ DosFindFirst(p1, p2, p3, p4, p5, p6, 1) #else #define DosQueryCurrentDisk DosQCurDisk #define DosQueryFSAttach(p1, p2, p3, p4, p5) \ DosQFSAttach(p1, p2, p3, p4, p5, 0) #define DosQueryFSInfo(d, l, b, s) \ DosQFSInfo(d, l, b, s) #define DosQueryPathInfo(p1, p2, p3, p4) \ DosQPathInfo(p1, p2, p3, p4, 0) #define DosSetPathInfo(p1, p2, p3, p4, p5) \ DosSetPathInfo(p1, p2, p3, p4, p5, 0) #define DosEnumAttribute(p1, p2, p3, p4, p5, p6, p7) \ DosEnumAttribute(p1, p2, p3, p4, p5, p6, p7, 0) #define DosFindFirst(p1, p2, p3, p4, p5, p6) \ DosFindFirst(p1, p2, p3, p4, p5, p6, 0) #define DosMapCase DosCaseMap #endif #ifndef UTIL extern int noisy; #ifndef S_IFMT #define S_IFMT 0xF000 #endif static int attributes = _A_DIR | _A_HIDDEN | _A_SYSTEM; static char *getdirent(char *); static void free_dircontents(struct _dircontents *); #ifdef __32BIT__ static HDIR hdir; static ULONG count; static FILEFINDBUF3 find; #else static HDIR hdir; static USHORT count; static FILEFINDBUF find; #endif DIR *opendir(const char *name) { struct stat statb; DIR *dirp; char c; char *s; struct _dircontents *dp; char nbuf[MAXPATHLEN + 1]; int len; attributes = hidden_files ? (_A_DIR | _A_HIDDEN | _A_SYSTEM) : _A_DIR; strcpy(nbuf, name); if ((len = strlen(nbuf)) == 0) return NULL; if (((c = nbuf[len - 1]) == '\\' || c == '/') && (len > 1)) { nbuf[len - 1] = 0; --len; if (nbuf[len - 1] == ':') { strcpy(nbuf+len, "\\."); len += 2; } } else if (nbuf[len - 1] == ':') { strcpy(nbuf+len, "."); ++len; } #ifndef __BORLANDC__ /* when will we ever see a Borland compiler that can properly stat !!! */ if (stat(nbuf, &statb) < 0 || (statb.st_mode & S_IFMT) != S_IFDIR) return NULL; #endif if ((dirp = malloc(sizeof(DIR))) == NULL) return NULL; if (nbuf[len - 1] == '.' && (len == 1 || nbuf[len - 2] != '.')) strcpy(nbuf+len-1, "*.*"); else if (((c = nbuf[len - 1]) == '\\' || c == '/') && (len == 1)) strcpy(nbuf+len, "*"); else strcpy(nbuf+len, "\\*"); /* len is no longer correct (but no longer needed) */ dirp -> dd_loc = 0; dirp -> dd_contents = dirp -> dd_cp = NULL; if ((s = getdirent(nbuf)) == NULL) return dirp; do { if (((dp = malloc(sizeof(struct _dircontents))) == NULL) || ((dp -> _d_entry = malloc(strlen(s) + 1)) == NULL) ) { if (dp) free(dp); free_dircontents(dirp -> dd_contents); return NULL; } if (dirp -> dd_contents) { dirp -> dd_cp -> _d_next = dp; dirp -> dd_cp = dirp -> dd_cp -> _d_next; } else dirp -> dd_contents = dirp -> dd_cp = dp; strcpy(dp -> _d_entry, s); dp -> _d_next = NULL; dp -> _d_size = find.cbFile; dp -> _d_mode = find.attrFile; dp -> _d_time = *(unsigned *) &(find.ftimeLastWrite); dp -> _d_date = *(unsigned *) &(find.fdateLastWrite); } while ((s = getdirent(NULL)) != NULL); dirp -> dd_cp = dirp -> dd_contents; return dirp; } void closedir(DIR * dirp) { free_dircontents(dirp -> dd_contents); free(dirp); } struct dirent *readdir(DIR * dirp) { static struct dirent dp; if (dirp -> dd_cp == NULL) return NULL; dp.d_namlen = dp.d_reclen = strlen(strcpy(dp.d_name, dirp -> dd_cp -> _d_entry)); dp.d_ino = 0; dp.d_size = dirp -> dd_cp -> _d_size; dp.d_mode = dirp -> dd_cp -> _d_mode; dp.d_time = dirp -> dd_cp -> _d_time; dp.d_date = dirp -> dd_cp -> _d_date; dirp -> dd_cp = dirp -> dd_cp -> _d_next; dirp -> dd_loc++; return &dp; } void seekdir(DIR * dirp, long off) { long i = off; struct _dircontents *dp; if (off >= 0) { for (dp = dirp -> dd_contents; --i >= 0 && dp; dp = dp -> _d_next); dirp -> dd_loc = off - (i + 1); dirp -> dd_cp = dp; } } long telldir(DIR * dirp) { return dirp -> dd_loc; } static void free_dircontents(struct _dircontents * dp) { struct _dircontents *odp; while (dp) { if (dp -> _d_entry) free(dp -> _d_entry); dp = (odp = dp) -> _d_next; free(odp); } } static char *getdirent(char *dir) { int done; static int lower; if (dir != NULL) { /* get first entry */ hdir = HDIR_SYSTEM; count = 1; done = DosFindFirst(dir, &hdir, attributes, &find, sizeof(find), &count); lower = IsFileSystemFAT(dir); } else /* get next entry */ done = DosFindNext(hdir, &find, sizeof(find), &count); if (done == 0) { if (lower) StringLower(find.achName); return find.achName; } else { DosFindClose(hdir); return NULL; } } /* FAT / HPFS detection */ int IsFileSystemFAT(char *dir) { static USHORT nLastDrive = -1, nResult; ULONG lMap; BYTE bData[64]; char bName[3]; #ifdef __32BIT__ ULONG nDrive, cbData; PFSQBUFFER2 pData = (PFSQBUFFER2) bData; #else USHORT nDrive, cbData; PFSQBUFFER pData = (PFSQBUFFER) bData; #endif /* We separate FAT and HPFS+other file systems here. at the moment I consider other systems to be similar to HPFS, i.e. support long file names and being case sensitive */ if (isalpha(dir[0]) && (dir[1] == ':')) nDrive = to_up(dir[0]) - '@'; else DosQueryCurrentDisk(&nDrive, &lMap); if (nDrive == nLastDrive) return nResult; bName[0] = (char) (nDrive + '@'); bName[1] = ':'; bName[2] = 0; nLastDrive = nDrive; cbData = sizeof(bData); if (!DosQueryFSAttach(bName, 0, FSAIL_QUERYNAME, (PVOID) pData, &cbData)) nResult = !strcmp((char *) pData -> szFSDName + pData -> cbName, "FAT"); else nResult = FALSE; /* End of this ugly code */ return nResult; } /* access mode bits and time stamp */ int GetFileMode(char *name) { #ifdef __32BIT__ FILESTATUS3 fs; return DosQueryPathInfo(name, 1, &fs, sizeof(fs)) ? -1 : fs.attrFile; #else USHORT mode; return DosQFileMode(name, &mode, 0L) ? -1 : mode; #endif } ulg GetFileTime(char *name) { #ifdef __32BIT__ FILESTATUS3 fs; #else FILESTATUS fs; #endif USHORT nDate, nTime; DATETIME dtCurrent; if (strcmp(name, "-") == 0) { DosGetDateTime(&dtCurrent); fs.fdateLastWrite.day = dtCurrent.day; fs.fdateLastWrite.month = dtCurrent.month; fs.fdateLastWrite.year = dtCurrent.year - 1980; fs.ftimeLastWrite.hours = dtCurrent.hours; fs.ftimeLastWrite.minutes = dtCurrent.minutes; fs.ftimeLastWrite.twosecs = dtCurrent.seconds / 2; } else if (DosQueryPathInfo(name, 1, (PBYTE) &fs, sizeof(fs))) return -1; nDate = * (USHORT *) &fs.fdateLastWrite; nTime = * (USHORT *) &fs.ftimeLastWrite; return ((ULONG) nDate) << 16 | nTime; } void SetFileTime(char *path, ulg stamp) { FILESTATUS fs; USHORT fd, ft; if (DosQueryPathInfo(path, FIL_STANDARD, (PBYTE) &fs, sizeof(fs))) return; fd = (USHORT) (stamp >> 16); ft = (USHORT) stamp; fs.fdateLastWrite = fs.fdateCreation = * (FDATE *) &fd; fs.ftimeLastWrite = fs.ftimeCreation = * (FTIME *) &ft; DosSetPathInfo(path, FIL_STANDARD, (PBYTE) &fs, sizeof(fs), 0); } /* read volume label */ char *getVolumeLabel(int drive, unsigned long *vtime, unsigned long *vmode, time_t *utim) { static FSINFO fi; if (DosQueryFSInfo(drive ? drive - 'A' + 1 : 0, FSIL_VOLSER, (PBYTE) &fi, sizeof(fi))) return NULL; time(utim); *vtime = unix2dostime(utim); *vmode = _A_VOLID | _A_ARCHIVE; return (fi.vol.cch > 0) ? fi.vol.szVolLabel : NULL; } /* FAT / HPFS name conversion stuff */ int IsFileNameValid(char *name) { HFILE hf; #ifdef __32BIT__ ULONG uAction; #else USHORT uAction; #endif switch(DosOpen(name, &hf, &uAction, 0, 0, FILE_OPEN, OPEN_ACCESS_READONLY | OPEN_SHARE_DENYNONE, 0)) { case ERROR_INVALID_NAME: case ERROR_FILENAME_EXCED_RANGE: return FALSE; case NO_ERROR: DosClose(hf); default: return TRUE; } } void ChangeNameForFAT(char *name) { char *src, *dst, *next, *ptr, *dot, *start; static char invalid[] = ":;,=+\"[]<>| \t"; if (isalpha(name[0]) && (name[1] == ':')) start = name + 2; else start = name; src = dst = start; if ((*src == '/') || (*src == '\\')) src++, dst++; while (*src) { for (next = src; *next && (*next != '/') && (*next != '\\'); next++); for (ptr = src, dot = NULL; ptr < next; ptr++) if (*ptr == '.') { dot = ptr; /* remember last dot */ *ptr = '_'; } if (dot == NULL) for (ptr = src; ptr < next; ptr++) if (*ptr == '_') dot = ptr; /* remember last _ as if it were a dot */ if (dot && (dot > src) && ((next - dot <= 4) || ((next - src > 8) && (dot - src > 3)))) { if (dot) *dot = '.'; for (ptr = src; (ptr < dot) && ((ptr - src) < 8); ptr++) *dst++ = *ptr; for (ptr = dot; (ptr < next) && ((ptr - dot) < 4); ptr++) *dst++ = *ptr; } else { if (dot && (next - src == 1)) *dot = '.'; /* special case: "." as a path component */ for (ptr = src; (ptr < next) && ((ptr - src) < 8); ptr++) *dst++ = *ptr; } *dst++ = *next; /* either '/' or 0 */ if (*next) { src = next + 1; if (*src == 0) /* handle trailing '/' on dirs ! */ *dst = 0; } else break; } for (src = start; *src != 0; ++src) if ((strchr(invalid, *src) != NULL) || (*src == ' ')) *src = '_'; } /* .LONGNAME EA code */ typedef struct { ULONG cbList; /* length of value + 22 */ #ifdef __32BIT__ ULONG oNext; #endif BYTE fEA; /* 0 */ BYTE cbName; /* length of ".LONGNAME" = 9 */ USHORT cbValue; /* length of value + 4 */ BYTE szName[10]; /* ".LONGNAME" */ USHORT eaType; /* 0xFFFD for length-preceded ASCII */ USHORT eaSize; /* length of value */ BYTE szValue[CCHMAXPATH]; } FEALST; typedef struct { ULONG cbList; #ifdef __32BIT__ ULONG oNext; #endif BYTE cbName; BYTE szName[10]; /* ".LONGNAME" */ } GEALST; char *GetLongNameEA(const char *name) { EAOP eaop; GEALST gealst; static FEALST fealst; char *ptr; eaop.fpGEAList = (PGEALIST) &gealst; eaop.fpFEAList = (PFEALIST) &fealst; eaop.oError = 0; strcpy((char *) gealst.szName, ".LONGNAME"); gealst.cbName = (BYTE) strlen((char *) gealst.szName); #ifdef __32BIT__ gealst.oNext = 0; #endif gealst.cbList = sizeof(gealst); fealst.cbList = sizeof(fealst); if (DosQueryPathInfo(name, FIL_QUERYEASFROMLIST, (PBYTE) &eaop, sizeof(eaop))) return NULL; if (fealst.cbValue > 4 && fealst.eaType == 0xFFFD) { fealst.szValue[fealst.eaSize] = 0; for (ptr = fealst.szValue; *ptr; ptr++) if (*ptr == '/' || *ptr == '\\') *ptr = '!'; return (char *) fealst.szValue; } return NULL; } char *GetLongPathEA(const char *name) { static char nbuf[CCHMAXPATH + 1]; char tempbuf[CCHMAXPATH + 1]; char *comp, *next, *ea, sep; BOOL bFound = FALSE; nbuf[0] = 0; strncpy(tempbuf, name, CCHMAXPATH); tempbuf[CCHMAXPATH] = '\0'; next = tempbuf; while (*next) { comp = next; while (*next != '\\' && *next != '/' && *next != 0) next++; sep = *next; *next = 0; ea = GetLongNameEA(tempbuf); strcat(nbuf, ea ? ea : comp); bFound = bFound || (ea != NULL); if (sep) { strcat(nbuf, "\\"); *next++ = sep; } } return (nbuf[0] != 0) && bFound ? nbuf : NULL; } /* general EA code */ typedef struct { USHORT nID; USHORT nSize; ULONG lSize; } EFHEADER, *PEFHEADER; #ifdef __32BIT__ /* Perhaps due to bugs in the current OS/2 2.0 kernel, the success or failure of the DosEnumAttribute() and DosQueryPathInfo() system calls depends on the area where the return buffers are allocated. This differs for the various compilers, for some alloca() works, for some malloc() works, for some, both work. We'll have to live with that. */ /* The use of malloc() is not very convenient, because it requires backtracking (i.e. free()) at error returns. We do that for system calls that may fail, but not for malloc() calls, because they are VERY unlikely to fail. If ever, we just leave some memory allocated over the usually short lifetime of a zip process ... */ #ifdef __GNUC__ #define alloc(x) alloca(x) #define unalloc(x) #else #define alloc(x) malloc(x) #define unalloc(x) free(x) #endif void GetEAs(char *path, char **bufptr, size_t *size, char **cbufptr, size_t *csize) { FILESTATUS4 fs; PDENA2 pDENA, pFound; EAOP2 eaop; PGEA2 pGEA; PGEA2LIST pGEAlist; PFEA2LIST pFEAlist; PEFHEADER pEAblock; ULONG ulAttributes, ulMemoryBlock; ULONG nLength; ULONG nBlock; char szName[CCHMAXPATH]; *size = *csize = 0; strcpy(szName, path); nLength = strlen(szName); if (szName[nLength - 1] == '/') szName[nLength - 1] = 0; if (DosQueryPathInfo(szName, FIL_QUERYEASIZE, (PBYTE) &fs, sizeof(fs))) return; nBlock = max(fs.cbList, 65535); if ((pDENA = alloc((size_t) nBlock)) == NULL) return; ulAttributes = -1; if (DosEnumAttribute(ENUMEA_REFTYPE_PATH, szName, 1, pDENA, nBlock, &ulAttributes, ENUMEA_LEVEL_NO_VALUE) || ulAttributes == 0 || (pGEAlist = alloc((size_t) nBlock)) == NULL) { unalloc(pDENA); return; } pGEA = pGEAlist -> list; memset(pGEAlist, 0, nBlock); pFound = pDENA; while (ulAttributes--) { if (!(strcmp(pFound -> szName, ".LONGNAME") == 0 && use_longname_ea)) { pGEA -> cbName = pFound -> cbName; strcpy(pGEA -> szName, pFound -> szName); nLength = sizeof(GEA2) + strlen(pGEA -> szName); nLength = ((nLength - 1) / sizeof(ULONG) + 1) * sizeof(ULONG); pGEA -> oNextEntryOffset = ulAttributes ? nLength : 0; pGEA = (PGEA2) ((PCH) pGEA + nLength); } pFound = (PDENA2) ((PCH) pFound + pFound -> oNextEntryOffset); } if (pGEA == pGEAlist -> list) /* no attributes to save */ { unalloc(pDENA); unalloc(pGEAlist); return; } pGEAlist -> cbList = (PCH) pGEA - (PCH) pGEAlist; pFEAlist = (PVOID) pDENA; /* reuse buffer */ pFEAlist -> cbList = nBlock; eaop.fpGEA2List = pGEAlist; eaop.fpFEA2List = pFEAlist; eaop.oError = 0; if (DosQueryPathInfo(szName, FIL_QUERYEASFROMLIST, (PBYTE) &eaop, sizeof(eaop))) { unalloc(pDENA); unalloc(pGEAlist); return; } /* The maximum compressed size is (in case of STORE type) the uncompressed size plus the size of the compression type field plus the size of the CRC field + 2*5 deflate overhead bytes for uncompressable data. (5 bytes per 32Kb block, max compressed size = 2 blocks) */ ulAttributes = pFEAlist -> cbList; ulMemoryBlock = ulAttributes + sizeof(USHORT) + sizeof(ULONG) + EB_DEFLAT_EXTRA; pEAblock = (PEFHEADER) malloc(sizeof(EFHEADER) + ulMemoryBlock); if (pEAblock == NULL) { unalloc(pDENA); unalloc(pGEAlist); return; } *bufptr = (char *) pEAblock; *size = sizeof(EFHEADER); pEAblock -> nID = EF_OS2EA; pEAblock -> nSize = sizeof(pEAblock -> lSize); pEAblock -> lSize = ulAttributes; /* uncompressed size */ nLength = memcompress((char *) (pEAblock + 1), ulMemoryBlock, (char *) pFEAlist, ulAttributes); *size += nLength; pEAblock -> nSize += nLength; if ((pEAblock = (PEFHEADER) malloc(sizeof(EFHEADER))) == NULL) { unalloc(pDENA); unalloc(pGEAlist); return; } *cbufptr = (char *) pEAblock; *csize = sizeof(EFHEADER); pEAblock -> nID = EF_OS2EA; pEAblock -> nSize = sizeof(pEAblock -> lSize); pEAblock -> lSize = ulAttributes; if (noisy) printf(" (%ld bytes EA's)", ulAttributes); unalloc(pDENA); unalloc(pGEAlist); } #else /* !__32BIT__ */ typedef struct { ULONG oNextEntryOffset; BYTE fEA; BYTE cbName; USHORT cbValue; CHAR szName[1]; } FEA2, *PFEA2; typedef struct { ULONG cbList; FEA2 list[1]; } FEA2LIST, *PFEA2LIST; void GetEAs(char *path, char **bufptr, size_t *size, char **cbufptr, size_t *csize) { FILESTATUS2 fs; PDENA1 pDENA, pFound; EAOP eaop; PGEALIST pGEAlist; PGEA pGEA; PFEALIST pFEAlist; PFEA pFEA; PFEA2LIST pFEA2list; PFEA2 pFEA2; EFHEADER *pEAblock; ULONG ulAttributes; USHORT nLength, nMaxSize; char szName[CCHMAXPATH]; *size = *csize = 0; strcpy(szName, path); nLength = strlen(szName); if (szName[nLength - 1] == '/') szName[nLength - 1] = 0; if (DosQueryPathInfo(szName, FIL_QUERYEASIZE, (PBYTE) &fs, sizeof(fs)) || fs.cbList <= 2 * sizeof(ULONG)) return; ulAttributes = -1; nMaxSize = (USHORT) min(fs.cbList * 2, 65520L); if ((pDENA = malloc((size_t) nMaxSize)) == NULL) return; if (DosEnumAttribute(ENUMEA_REFTYPE_PATH, szName, 1, pDENA, fs.cbList, &ulAttributes, ENUMEA_LEVEL_NO_VALUE) || ulAttributes == 0 || (pGEAlist = malloc(nMaxSize)) == NULL) { free(pDENA); return; } pGEA = pGEAlist -> list; pFound = pDENA; while (ulAttributes--) { nLength = strlen(pFound -> szName); if (!(strcmp(pFound -> szName, ".LONGNAME") == 0 && use_longname_ea)) { pGEA -> cbName = pFound -> cbName; strcpy(pGEA -> szName, pFound -> szName); pGEA++; pGEA = (PGEA) (((PCH) pGEA) + nLength); } pFound++; pFound = (PDENA1) (((PCH) pFound) + nLength); } if (pGEA == pGEAlist -> list) { free(pDENA); free(pGEAlist); return; } pGEAlist -> cbList = (PCH) pGEA - (PCH) pGEAlist; pFEAlist = (PFEALIST) pDENA; /* reuse buffer */ pFEAlist -> cbList = fs.cbList; pFEA = pFEAlist -> list; eaop.fpGEAList = pGEAlist; eaop.fpFEAList = pFEAlist; eaop.oError = 0; if (DosQueryPathInfo(szName, FIL_QUERYEASFROMLIST, (PBYTE) &eaop, sizeof(eaop))) { free(pDENA); free(pGEAlist); return; } /* now convert into new OS/2 2.0 32-bit format */ pFEA2list = (PFEA2LIST) pGEAlist; /* reuse buffer */ pFEA2 = pFEA2list -> list; while ((PCH) pFEA - (PCH) pFEAlist < pFEAlist -> cbList) { nLength = sizeof(FEA) + pFEA -> cbName + 1 + pFEA -> cbValue; memcpy((PCH) pFEA2 + sizeof(pFEA2 -> oNextEntryOffset), pFEA, nLength); memset((PCH) pFEA2 + sizeof(pFEA2 -> oNextEntryOffset) + nLength, 0, 3); pFEA = (PFEA) ((PCH) pFEA + nLength); nLength = sizeof(FEA2) + pFEA2 -> cbName + 1 + pFEA2 -> cbValue; nLength = ((nLength - 1) / sizeof(ULONG) + 1) * sizeof(ULONG); /* rounded up to 4-byte boundary */ pFEA2 -> oNextEntryOffset = ((PCH) pFEA - (PCH) pFEAlist < pFEAlist -> cbList) ? nLength : 0; pFEA2 = (PFEA2) ((PCH) pFEA2 + nLength); } pFEA2list -> cbList = (PCH) pFEA2 - (PCH) pFEA2list; ulAttributes = pFEA2list -> cbList; pEAblock = (PEFHEADER) pDENA; /* reuse buffer */ *bufptr = (char *) pEAblock; *size = sizeof(EFHEADER); pEAblock -> nID = EF_OS2EA; pEAblock -> nSize = sizeof(pEAblock -> lSize); pEAblock -> lSize = ulAttributes; /* uncompressed size */ nLength = (USHORT) memcompress((char *) (pEAblock + 1), nMaxSize - sizeof(EFHEADER), (char *) pFEA2list, ulAttributes); *size += nLength; pEAblock -> nSize += nLength; pEAblock = (PEFHEADER) pGEAlist; *cbufptr = (char *) pEAblock; *csize = sizeof(EFHEADER); pEAblock -> nID = EF_OS2EA; pEAblock -> nSize = sizeof(pEAblock -> lSize); pEAblock -> lSize = ulAttributes; if (noisy) printf(" (%ld bytes EA's)", ulAttributes); } #endif /* __32BIT__ */ void GetACL(char *path, char **bufptr, size_t *size, char **cbufptr, size_t *csize) { static char *buffer; char *cbuffer; long bytes, cbytes; PEFHEADER pACLblock; if (buffer == NULL) /* avoid frequent allocation (for every file) */ if ((buffer = malloc(ACL_BUFFERSIZE)) == NULL) return; if (acl_get(NULL, path, buffer)) return; /* this will be the most likely case */ bytes = strlen(buffer); /* The maximum compressed size is (in case of STORE type) the uncompressed size plus the size of the compression type field plus the size of the CRC field + 2*5 deflate overhead bytes for uncompressable data. (5 bytes per 32Kb block, max compressed size = 2 blocks) */ cbytes = bytes + sizeof(USHORT) + sizeof(ULONG) + EB_DEFLAT_EXTRA; if ((*bufptr = realloc(*bufptr, *size + sizeof(EFHEADER) + cbytes)) == NULL) return; pACLblock = (PEFHEADER) (*bufptr + *size); cbuffer = (char *) (pACLblock + 1); cbytes = memcompress(cbuffer, cbytes, buffer, bytes); *size += sizeof(EFHEADER) + cbytes; pACLblock -> nID = EF_ACL; pACLblock -> nSize = sizeof(pACLblock -> lSize) + cbytes; pACLblock -> lSize = bytes; /* uncompressed size */ if ((*cbufptr = realloc(*cbufptr, *csize + sizeof(EFHEADER))) == NULL) return; pACLblock = (PEFHEADER) (*cbufptr + *csize); *csize += sizeof(EFHEADER); pACLblock -> nID = EF_ACL; pACLblock -> nSize = sizeof(pACLblock -> lSize); pACLblock -> lSize = bytes; if (noisy) printf(" (%ld bytes ACL)", bytes); } #ifdef USE_EF_UT_TIME int GetExtraTime(struct zlist far *z, iztimes *z_utim) { int eb_c_size = EB_HEADSIZE + EB_UT_LEN(1); int eb_l_size = eb_c_size; char *eb_c_ptr; char *eb_l_ptr; unsigned long ultime; #ifdef IZ_CHECK_TZ if (!zp_tz_is_valid) return ZE_OK; /* skip silently no correct tz info */ #endif eb_c_ptr = realloc(z->cextra, (z->cext + eb_c_size)); if (eb_c_ptr == NULL) return ZE_MEM; z->cextra = eb_c_ptr; eb_c_ptr += z->cext; z->cext += eb_c_size; eb_c_ptr[0] = 'U'; eb_c_ptr[1] = 'T'; eb_c_ptr[2] = EB_UT_LEN(1); /* length of data part of e.f. */ eb_c_ptr[3] = 0; eb_c_ptr[4] = EB_UT_FL_MTIME; ultime = (unsigned long) z_utim->mtime; eb_c_ptr[5] = (char)(ultime); eb_c_ptr[6] = (char)(ultime >> 8); eb_c_ptr[7] = (char)(ultime >> 16); eb_c_ptr[8] = (char)(ultime >> 24); if (z_utim->mtime != z_utim->atime || z_utim->mtime != z_utim->ctime) { eb_c_ptr[4] = EB_UT_FL_MTIME | EB_UT_FL_ATIME | EB_UT_FL_CTIME; eb_l_size = EB_HEADSIZE + EB_UT_LEN(3); /* only on HPFS they can differ */ /* so only then it makes sense to store all three time stamps */ } eb_l_ptr = realloc(z->extra, (z->ext + eb_l_size)); if (eb_l_ptr == NULL) return ZE_MEM; z->extra = eb_l_ptr; eb_l_ptr += z->ext; z->ext += eb_l_size; memcpy(eb_l_ptr, eb_c_ptr, eb_c_size); if (eb_l_size > eb_c_size) { eb_l_ptr[2] = EB_UT_LEN(3); ultime = (unsigned long) z_utim->atime; eb_l_ptr[9] = (char)(ultime); eb_l_ptr[10] = (char)(ultime >> 8); eb_l_ptr[11] = (char)(ultime >> 16); eb_l_ptr[12] = (char)(ultime >> 24); ultime = (unsigned long) z_utim->ctime; eb_l_ptr[13] = (char)(ultime); eb_l_ptr[14] = (char)(ultime >> 8); eb_l_ptr[15] = (char)(ultime >> 16); eb_l_ptr[16] = (char)(ultime >> 24); } return ZE_OK; } #endif /* USE_EF_UT_TIME */ int set_extra_field(struct zlist far *z, iztimes *z_utim) { /* store EA data in local header, and size only in central headers */ GetEAs(z->name, &z->extra, &z->ext, &z->cextra, &z->cext); /* store ACL data in local header, and size only in central headers */ GetACL(z->name, &z->extra, &z->ext, &z->cextra, &z->cext); #ifdef USE_EF_UT_TIME /* store extended time stamps in both headers */ return GetExtraTime(z, z_utim); #else /* !USE_EF_UT_TIME */ return ZE_OK; #endif /* ?USE_EF_UT_TIME */ } #endif /* !UTIL */ /* Initialize the table of uppercase characters including handling of country dependent characters. */ void init_upper() { COUNTRYCODE cc; unsigned nCnt, nU; for (nCnt = 0; nCnt < sizeof(upper); nCnt++) upper[nCnt] = lower[nCnt] = (unsigned char) nCnt; cc.country = cc.codepage = 0; DosMapCase(sizeof(upper), &cc, (PCHAR) upper); for (nCnt = 0; nCnt < 256; nCnt++) { nU = upper[nCnt]; if (nU != nCnt && lower[nU] == (unsigned char) nU) lower[nU] = (unsigned char) nCnt; } for (nCnt = 'A'; nCnt <= 'Z'; nCnt++) lower[nCnt] = (unsigned char) (nCnt - 'A' + 'a'); } char *StringLower(char *szArg) { unsigned char *szPtr; for (szPtr = (unsigned char *) szArg; *szPtr; szPtr++) *szPtr = lower[*szPtr]; return szArg; } #if defined(__IBMC__) && defined(__DEBUG_ALLOC__) void DebugMalloc(void) { _dump_allocated(0); /* print out debug malloc memory statistics */ } #endif /******************************/ /* Function version_local() */ /******************************/ void version_local() { static ZCONST char CompiledWith[] = "Compiled with %s%s for %s%s%s%s.\n\n"; #if defined(__IBMC__) || defined(__WATCOMC__) || defined(_MSC_VER) char buf[80]; #endif printf(CompiledWith, #ifdef __GNUC__ # ifdef __EMX__ /* __EMX__ is defined as "1" only (sigh) */ "emx+gcc ", __VERSION__, # else "gcc/2 ", __VERSION__, # endif #elif defined(__IBMC__) "IBM ", # if (__IBMC__ < 200) (sprintf(buf, "C Set/2 %d.%02d", __IBMC__/100,__IBMC__%100), buf), # elif (__IBMC__ < 300) (sprintf(buf, "C Set++ %d.%02d", __IBMC__/100,__IBMC__%100), buf), # else (sprintf(buf, "Visual Age C++ %d.%02d", __IBMC__/100,__IBMC__%100), buf), # endif #elif defined(__WATCOMC__) "Watcom C", (sprintf(buf, " (__WATCOMC__ = %d)", __WATCOMC__), buf), #elif defined(__TURBOC__) # ifdef __BORLANDC__ "Borland C++", # if (__BORLANDC__ < 0x0460) " 1.0", # elif (__BORLANDC__ == 0x0460) " 1.5", # else " 2.0", # endif # else "Turbo C", # if (__TURBOC__ >= 661) "++ 1.0 or later", # elif (__TURBOC__ == 661) " 3.0?", # elif (__TURBOC__ == 397) " 2.0", # else " 1.0 or 1.5?", # endif # endif #elif defined(MSC) "Microsoft C ", # ifdef _MSC_VER (sprintf(buf, "%d.%02d", _MSC_VER/100, _MSC_VER%100), buf), # else "5.1 or earlier", # endif #else "unknown compiler", "", #endif /* __GNUC__ */ "OS/2", /* GRR: does IBM C/2 identify itself as IBM rather than Microsoft? */ #if (defined(MSC) || (defined(__WATCOMC__) && !defined(__386__))) # if defined(M_I86HM) || defined(__HUGE__) " (16-bit, huge)", # elif defined(M_I86LM) || defined(__LARGE__) " (16-bit, large)", # elif defined(M_I86MM) || defined(__MEDIUM__) " (16-bit, medium)", # elif defined(M_I86CM) || defined(__COMPACT__) " (16-bit, compact)", # elif defined(M_I86SM) || defined(__SMALL__) " (16-bit, small)", # elif defined(M_I86TM) || defined(__TINY__) " (16-bit, tiny)", # else " (16-bit)", # endif #else " 2.x/3.x (32-bit)", #endif #ifdef __DATE__ " on ", __DATE__ #else "", "" #endif ); /* temporary debugging code for Borland compilers only */ #ifdef __TURBOC__ printf("\t(__TURBOC__ = 0x%04x = %d)\n", __TURBOC__, __TURBOC__); #ifdef __BORLANDC__ printf("\t(__BORLANDC__ = 0x%04x)\n",__BORLANDC__); #else printf("\tdebug(__BORLANDC__ not defined)\n"); #endif #ifdef __TCPLUSPLUS__ printf("\t(__TCPLUSPLUS__ = 0x%04x)\n", __TCPLUSPLUS__); #else printf("\tdebug(__TCPLUSPLUS__ not defined)\n"); #endif #ifdef __BCPLUSPLUS__ printf("\t(__BCPLUSPLUS__ = 0x%04x)\n\n", __BCPLUSPLUS__); #else printf("\tdebug(__BCPLUSPLUS__ not defined)\n\n"); #endif #endif /* __TURBOC__ */ } /* end function version_local() */ #endif /* OS2 */ zip30/os2/os2zip.h0100644000076400000060000000462707420227716012103 0ustar edisk/* * @(#) dir.h 1.4 87/11/06 Public Domain. * * A public domain implementation of BSD directory routines for * MS-DOS. Written by Michael Rendell ({uunet,utai}michael@garfield), * August 1987 * * Ported to OS/2 by Kai Uwe Rommel * Addition of other OS/2 file system specific code * Placed into the public domain */ #define MAXNAMLEN 256 #define MAXPATHLEN 256 #define _A_RONLY 0x01 #define _A_HIDDEN 0x02 #define _A_SYSTEM 0x04 #define _A_VOLID 0x08 #define _A_DIR 0x10 #define _A_ARCHIVE 0x20 struct dirent { ino_t d_ino; /* a bit of a farce */ int d_reclen; /* more farce */ int d_namlen; /* length of d_name */ char d_name[MAXNAMLEN + 1]; /* null terminated */ /* nonstandard fields */ long d_size; /* size in bytes */ unsigned d_mode; /* DOS or OS/2 file attributes */ unsigned d_time; unsigned d_date; }; /* The fields d_size and d_mode are extensions by me (Kai Uwe Rommel). * The find_first and find_next calls deliver this data without any extra cost. * If this data is needed, these fields save a lot of extra calls to stat() * (each stat() again performs a find_first call !). */ struct _dircontents { char *_d_entry; long _d_size; unsigned _d_mode, _d_time, _d_date; struct _dircontents *_d_next; }; typedef struct _dirdesc { int dd_id; /* uniquely identify each open directory */ long dd_loc; /* where we are in directory entry is this */ struct _dircontents *dd_contents; /* pointer to contents of dir */ struct _dircontents *dd_cp; /* pointer to current position */ } DIR; extern DIR *opendir(const char *); extern struct dirent *readdir(DIR *); extern void seekdir(DIR *, long); extern long telldir(DIR *); extern void closedir(DIR *); #define rewinddir(dirp) seekdir(dirp, 0L) int GetFileMode(char *name); ulg GetFileTime(char *name); void SetFileTime(char *path, ulg stamp); char *getVolumeLabel(int drive, unsigned long *time, unsigned long *mode, time_t *utim); int IsFileNameValid(char *name); int IsFileSystemFAT(char *dir); void ChangeNameForFAT(char *name); char *GetLongNameEA(const char *name); char *GetLongPathEA(const char *name); void GetEAs(char *name, char **bufptr, size_t *size, char **cbufptr, size_t *csize); char *StringLower(char *); zip30/os2/osdep.h0100644000076400000060000001211707011111616011743 0ustar edisk/* Copyright (c) 1990-1999 Info-ZIP. All rights reserved. See the accompanying file LICENSE, version 1999-Oct-05 or later (the contents of which are also included in zip.h) for terms of use. If, for some reason, both of these files are missing, the Info-ZIP license also may be found at: ftp://ftp.cdrom.com/pub/infozip/license.html */ #if defined(__OS2__) && !defined(OS2) # define OS2 #endif /* Automatic setting of the common Microsoft C idenfifier MSC. * NOTE: Watcom also defines M_I*86 ! */ #if defined(_MSC_VER) || (defined(M_I86) && !defined(__WATCOMC__)) # ifndef MSC # define MSC /* This should work for older MSC, too! */ # endif #endif #if defined(__WATCOMC__) && defined(__386__) # define WATCOMC_386 #endif #if defined(__EMX__) || defined(WATCOMC_386) || defined(__BORLANDC__) # if (defined(OS2) && !defined(__32BIT__)) # define __32BIT__ # endif #endif #if defined(OS2) && !defined(__32BIT__) # define MEMORY16 #endif #ifndef NO_ASM # define ASMV /* # define ASM_CRC */ #endif /* enable creation of UTC time fields unless explicitely suppressed */ #if (!defined(NO_EF_UT_TIME) && !defined(USE_EF_UT_TIME)) # define USE_EF_UT_TIME #endif /* check that TZ environment variable is defined before using UTC times */ #if (!defined(NO_IZ_CHECK_TZ) && !defined(IZ_CHECK_TZ)) # define IZ_CHECK_TZ #endif #ifndef ZP_NEED_MEMCOMPR # define ZP_NEED_MEMCOMPR #endif #ifdef MEMORY16 # ifdef __TURBOC__ # include # if defined(__COMPACT__) || defined(__LARGE__) || defined(__HUGE__) # if defined(DYNAMIC_CRC_TABLE) && defined(DYNALLOC_CRCTAB) error: No dynamic CRC table allocation with Borland C far data models. # endif /* DYNAMIC_CRC_TABLE */ # endif /* Turbo/Borland C far data memory models */ # define nearmalloc malloc # define nearfree free # define DYN_ALLOC # else /* !__TURBOC__ */ # include # define nearmalloc _nmalloc # define nearfree _nfree # define farmalloc _fmalloc # define farfree _ffree # endif /* ?__TURBOC__ */ # define MY_ZCALLOC 1 #endif /* MEMORY16 */ /* The symbol MSDOS is consistently used in the generic source files * to identify code to support for MSDOS (and MSDOS related) stuff. * e.g: FAT or (FAT like) file systems, * '\\' as directory separator in paths, * "\r\n" as record (line) terminator in text files, ... * * MSDOS is defined anyway with MS C 16-bit. So the block above works. * For the 32-bit compilers, MSDOS must not be defined in the block above. */ #if (defined(OS2) && !defined(MSDOS)) # define MSDOS /* inherit MS-DOS file system etc. stuff */ #endif #define USE_CASE_MAP #define PROCNAME(n) (action == ADD || action == UPDATE ? wild(n) : \ procname(n, 1)) /* time stamp resolution of file system is 2 seconds */ #define ROUNDED_TIME(time) ((time_t)(((unsigned long)(time) + 1) & (~1))) #define FOPR "rb" #define FOPM "r+b" #define FOPW "wb" #ifdef __32BIT__ # define CBSZ 0x40000 # define ZBSZ 0x40000 #else # define CBSZ 0xE000 # define ZBSZ 0x7F00 /* Some libraries do not allow a buffer size > 32K */ #endif #include #include #include #ifdef ZCRYPT_INTERNAL # ifndef __GO32__ # include /* getpid() declaration for srand seed */ # endif #endif /* for some (all ?) versions of IBM C Set/2 and IBM C Set++ */ #ifndef S_IFMT # define S_IFMT 0xF000 #endif /* !S_IFMT */ #ifdef MSC # define NO_UNISTD_H #endif #ifdef __WATCOMC__ # define NO_MKTEMP /* Get asm routines to link properly without using "__cdecl": */ # ifdef __386__ # ifdef ASMV # pragma aux window "*"; # pragma aux prev "*"; # pragma aux prev_length "*"; # pragma aux strstart "*"; # pragma aux match_start "*"; # pragma aux max_chain_length "*"; # pragma aux good_match "*"; # pragma aux nice_match "*"; # pragma aux match_init "*"; # pragma aux longest_match "*"; # endif # ifndef USE_ZLIB # pragma aux crc32 "_*" parm caller [] value [eax] modify [eax] # pragma aux get_crc_table "_*" parm caller [] value [eax] \ modify [eax ecx edx] # endif /* !USE_ZLIB */ # else /* !__386__ */ # if defined(ASMV) || defined(ASM_CRC) /*# error 16 bit assembly modules currently DO NOT WORK with Watcom C. */ # endif # ifdef ASMV # pragma aux match_init "_*" parm caller [] loadds modify [ax bx] # pragma aux longest_match "_*" parm caller [] loadds value [ax] \ modify [ax bx cx dx es] # endif # ifndef USE_ZLIB # pragma aux crc32 "_*" parm caller [] value [ax dx] \ modify [ax bx cx dx es] # pragma aux get_crc_table "_*" parm caller [] value [ax] \ modify [ax bx cx dx] # endif /* !USE_ZLIB */ # endif /* ?__386__ */ #endif #ifdef __IBMC__ # define NO_UNISTD_H # define NO_MKTEMP # define timezone _timezone /* (underscore names work with */ # define tzset _tzset /* all versions of C Set) */ #endif zip30/os2/zip.def0100644000076400000060000000015206254362776011765 0ustar ediskNAME WINDOWCOMPAT NEWFILES DESCRIPTION 'The world-famous zip utilities from Info-ZIP' ; STACKSIZE 0x50000 zip30/os2/zipup.h0100644000076400000060000000106207011111626011776 0ustar edisk/* Copyright (c) 1990-1999 Info-ZIP. All rights reserved. See the accompanying file LICENSE, version 1999-Oct-05 or later (the contents of which are also included in zip.h) for terms of use. If, for some reason, both of these files are missing, the Info-ZIP license also may be found at: ftp://ftp.cdrom.com/pub/infozip/license.html */ #define fhow (O_RDONLY|O_BINARY) #define fbad (-1) typedef int ftype; #define zopen(n,p) open(n,p) #define zread(f,b,n) read(f,b,n) #define zclose(f) close(f) #define zerr(f) (k == (extent)(-1L)) #define zstdin 0 zip30/proginfo/0040755000076400000060000000000011033727766011623 5ustar ediskzip30/proginfo/3rdparty.bug0100644000076400000060000001277506674677766014126 0ustar ediskKnown, current PKZIP bugs/limitations: ------------------------------------- - PKUNZIP 2.04g is reported to corrupt some files when compressing them with the -ex option; when tested, the files fail the CRC check, and comparison with the original file shows bogus data (6K in one case) embedded in the middle. PKWARE apparently characterized this as a "known problem." - PKUNZIP 2.04g considers volume labels valid only if originated on a FAT file system, but other OSes and file systems (e.g., Amiga and OS/2 HPFS) support volume labels, too. - PKUNZIP 2.04g can restore volume labels created by Zip 2.x but not by PKZIP 2.04g (OS/2 DOS box only??). - PKUNZIP 2.04g gives an error message for stored directory entries created under other OSes (although it creates the directory anyway), and PKZIP -vt does not report the directory attribute bit as being set, even if it is. - PKZIP 2.04g mangles unknown extra fields (especially OS/2 extended attri- butes) when adding new files to an existing zipfile [example: Walnut Creek Hobbes March 1995 CD-ROM, FILE_ID.DIZ additions]. - PKUNZIP 2.04g is unable to detect or deal with prepended junk in a zipfile, reporting CRC errors in valid compressed data. - PKUNZIP 2.04g (registered version) incorrectly updates/freshens the AV extra field in authenticated archives. The resultant extra block length and total extra field length are inconsistent. - [Windows version 2.01] Win95 long filenames (VFAT) are stored OK, but the file system is always listed as ordinary DOS FAT. - [Windows version 2.50] NT long filenames (NTFS) are stored OK, but the file system is always listed as ordinary DOS FAT. - PKZIP 2.04 for DOS encrypts using the OEM code page for 8-bit passwords, while PKZIP 2.50 for Windows uses Latin-1 (ISO 8859-1). This means an archive encrypted with an 8-bit password with one of the two PKZIP versions cannot be decrypted with the other version. - PKZIP for Windows GUI (v 2.60), PKZIP for Windows command line (v 2.50) and PKZIP for Unix (v 2.51) save the host's native file timestamps, but only in a local extra field. Thus, timestamp-related selections (update or freshen, both in extraction or archiving operations) use the DOS-format localtime records in the Zip archives for comparisons. This may result in wrong decisions of the program when updating archives that were previously created in a different local time zone. - PKZIP releases newer than PKZIP for DOS 2.04g (PKZIP for Windows, both GUI v 2.60 and console v 2.50; PKZIP for Unix v 2.51; probably others too) use different code pages for storing filenames in central (OEM Codepage) and local (ANSI / ISO 8859-1 Codepage) headers. When a stored filename contains extended-ASCII characters, the local and central filename fields do not match. As a consequence, Info-ZIP's Zip program considers such archives as being corrupt and does not allow to modify them. Beginning with release 5.41, Info-ZIP's UnZip contains a workaround to list AND extract such archives with the correct filenames. Maybe PKWARE has implemented this "feature" to allow extraction of their "made-by-PKZIP for Unix/Windows" archives using old (v5.2 and earlier) versions of Info-ZIP's UnZip for Unix/WinNT ??? (UnZip versions before v 5.3 assumed that all archive entries were encoded in the codepage of the UnZip program's host system.) - PKUNZIP 2.04g is reported to have problems with archives created on and/or copied from Iomega ZIP drives (irony, eh?). Known, current WinZip bugs/limitations: -------------------------------------- - [16-bit version 6.1a] NT short filenames (FAT) are stored OK, but the file system is always listed as NTFS. - WinZip doesn't allow 8-bit passwords, which means it cannot decrypt an archive created with an 8-bit password (by PKZIP or Info-ZIP's Zip). - WinZip (at least Versions 6.3 PL1, 7.0 SR1) fails to remove old extra fields when freshening existing archive entries. When updating archives created by Info-ZIP's Zip that contain UT time stamp extra field blocks, UnZip cannot display or restore the updated (DOS) time stamps of the freshened archive members. Known, current other third-party Zip utils bugs/limitations: ------------------------------------------------------------ - Asi's PKZip clones for Macintosh (versions 2.3 and 2.10d) are thoroughly broken. They create invalid Zip archives! a) For the first entry, both compressed size and uncompressed length are recorded as 0, despite the fact that compressed data of non-zero length has been added. b) Their program creates extra fields with an (undocumented) internal structure that violates the requirements of PKWARE's Zip format specification document "appnote.txt": Their extra field seems to contain pure data; the 4-byte block header consisting of block ID and data length is missing. Possibly current PKZIP bugs: --------------------------- - PKZIP (2.04g?) can silently ignore read errors on network drives, storing the correct CRC and compressed length but an incorrect and inconsistent uncompressed length. - PKZIP (2.04g?), when deleting files from within a zipfile on a Novell drive, sometimes only zeros out the data while failing to shrink the zipfile. Other limitations: ----------------- - PKZIP 1.x and 2.x encryption has been cracked (known-plaintext approach; see http://www.cryptography.com/ for details). [many other bugs in PKZIP 1.0, 1.1, 1.93a, 2.04c and 2.04e] zip30/proginfo/algorith.txt0100644000076400000060000000650306254362756014201 0ustar ediskZip's deflation algorithm is a variation of LZ77 (Lempel-Ziv 1977, see reference below). It finds duplicated strings in the input data. The second occurrence of a string is replaced by a pointer to the previous string, in the form of a pair (distance, length). Distances are limited to 32K bytes, and lengths are limited to 258 bytes. When a string does not occur anywhere in the previous 32K bytes, it is emitted as a sequence of literal bytes. (In this description, 'string' must be taken as an arbitrary sequence of bytes, and is not restricted to printable characters.) Literals or match lengths are compressed with one Huffman tree, and match distances are compressed with another tree. The trees are stored in a compact form at the start of each block. The blocks can have any size (except that the compressed data for one block must fit in available memory). A block is terminated when zip determines that it would be useful to start another block with fresh trees. (This is somewhat similar to compress.) Duplicated strings are found using a hash table. All input strings of length 3 are inserted in the hash table. A hash index is computed for the next 3 bytes. If the hash chain for this index is not empty, all strings in the chain are compared with the current input string, and the longest match is selected. The hash chains are searched starting with the most recent strings, to favor small distances and thus take advantage of the Huffman encoding. The hash chains are singly linked. There are no deletions from the hash chains, the algorithm simply discards matches that are too old. To avoid a worst-case situation, very long hash chains are arbitrarily truncated at a certain length, determined by a runtime option (zip -1 to -9). So zip does not always find the longest possible match but generally finds a match which is long enough. zip also defers the selection of matches with a lazy evaluation mechanism. After a match of length N has been found, zip searches for a longer match at the next input byte. If a longer match is found, the previous match is truncated to a length of one (thus producing a single literal byte) and the longer match is emitted afterwards. Otherwise, the original match is kept, and the next match search is attempted only N steps later. The lazy match evaluation is also subject to a runtime parameter. If the current match is long enough, zip reduces the search for a longer match, thus speeding up the whole process. If compression ratio is more important than speed, zip attempts a complete second search even if the first match is already long enough. The lazy match evaluation is not performed for the fastest compression modes (speed options -1 to -3). For these fast modes, new strings are inserted in the hash table only when no match was found, or when the match is not too long. This degrades the compression ratio but saves time since there are both fewer insertions and fewer searches. Jean-loup Gailly jloup@chorus.fr References: [LZ77] Ziv J., Lempel A., "A Universal Algorithm for Sequential Data Compression", IEEE Transactions on Information Theory", Vol. 23, No. 3, pp. 337-343. APPNOTE.TXT documentation file in PKZIP 1.93a. It is available by ftp in ftp.cso.uiuc.edu:/pc/exec-pc/pkz193a.exe [128.174.5.59] 'Deflate' Compressed Data Format Specification: ftp://ftp.uu.net/pub/archiving/zip/doc/deflate-1.1.doc zip30/proginfo/ebcdic.msg0100644000076400000060000000452107753470746013552 0ustar ediskFrom dima@mitrah.ru Mon Nov 10 02:25:38 2003 Return-Path: Received: from b.mx.sonic.net (eth0.b.mx.sonic.net [209.204.159.4]) by eth0.a.lds.sonic.net (8.12.10/8.12.9) with ESMTP id hAAAPccT025257 for ; Mon, 10 Nov 2003 02:25:38 -0800 Received: from icicle.pobox.com (icicle.pobox.com [207.8.214.2]) by b.mx.sonic.net (8.12.10/8.12.7) with ESMTP id hAAAPar9007141 for ; Mon, 10 Nov 2003 02:25:37 -0800 Received: from icicle.pobox.com (localhost[127.0.0.1]) by icicle.pobox.com (Postfix) with ESMTP id 9BA347A96B for ; Sat, 8 Nov 2003 06:15:13 -0500 (EST) Delivered-To: newt@pobox.com Received: from mail.ropnet.ru (mail.ropnet.ru[212.42.37.90]) by icicle.pobox.com (Postfix) with ESMTP id A96817A8F7 for ; Sat, 8 Nov 2003 06:15:04 -0500 (EST) Received: from d34-67.ropnet.ru (d34-67.ropnet.ru [212.42.34.67]) by mail.ropnet.ru (8.11.7/8.11.7) with ESMTP id hA8BEjF76200 for ; Sat, 8 Nov 2003 14:14:46 +0300 (MSK) Resent-Date: Sat, 8 Nov 2003 14:14:46 +0300 (MSK) Resent-Message-Id: <200311081114.hA8BEjF76200@mail.ropnet.ru> Date: Sat, 8 Nov 2003 14:18:18 +0300 From: Dmitri Koulikov X-Mailer: The Bat! (v1.62r) Personal Reply-To: Dmitri Koulikov X-Priority: 3 (Normal) Message-ID: <815640011.20031108141818@mitrah.ru> To: newt@pobox.com Subject: unzip and zip lack NLS - 2 Resent-From: Dmitri Koulikov MIME-Version: 1.0 Content-Type: multipart/mixed; boundary="----------EB1581C42AB86662" Status: R ------------EB1581C42AB86662 Content-Type: text/plain; charset=us-ascii Content-Transfer-Encoding: 7bit Hello Greg Roelofs, By mistake I sent you wrong version of ebcdic.h. Now it is as it have to. Additionally I found that zip works with Russian filenames good. But fails to process -D switch. So I have to chahge zipfile.c. Most probably this is not good but it works. -- Best regards, Dmitri mailto:dima@mitrah.ru ------------EB1581C42AB86662 Content-Type: application/octet-stream; name="ebcdic.h" Content-Transfer-Encoding: base64 Content-Disposition: attachment; filename="ebcdic.h" ------------EB1581C42AB86662 Content-Type: application/octet-stream; name="zipfile.c" Content-Transfer-Encoding: base64 Content-Disposition: attachment; filename="zipfile.c" ------------EB1581C42AB86662-- zip30/proginfo/extrafld.txt0100644000076400000060000017323511010763610014164 0ustar ediskThe following are the known types of zipfile extra fields as of this writing. Extra fields are documented in PKWARE's appnote.txt and are intended to allow for backward- and forward-compatible extensions to the zipfile format. Multiple extra-field types may be chained together, provided that the total length of all extra-field data is less than 64KB. (In fact, PKWARE requires that the total length of the entire file header, including timestamp, file attributes, filename, comment, extra field, etc., be no more than 64KB.) Each extra-field type (or subblock) must contain a four-byte header con- sisting of a two-byte header ID and a two-byte length (little-endian) for the remaining data in the subblock. If there are additional subblocks within the extra field, the header for each one will appear immediately following the data for the previous subblock (i.e., with no padding for alignment). All integer fields in the descriptions below are in little-endian (Intel) format unless otherwise specified. Note that "Short" means two bytes, "Long" means four bytes, and "Long-Long" means eight bytes, regardless of their native sizes. Unless specifically noted, all integer fields should be interpreted as unsigned (non-negative) numbers. Christian Spieler, 20010517 Updated to include the Unicode extra fields. Added new Unix extra field. Ed Gordon, 20060819, 20070607, 20070909, 20080426, 20080509 ------------------------- Header ID's of 0 thru 31 are reserved for use by PKWARE. The remaining ID's can be used by third party vendors for proprietary usage. The current Header ID mappings defined by PKWARE are: 0x0001 ZIP64 extended information extra field 0x0007 AV Info 0x0009 OS/2 extended attributes (also Info-ZIP) 0x000a NTFS (Win9x/WinNT FileTimes) 0x000c OpenVMS (also Info-ZIP) 0x000d Unix 0x000f Patch Descriptor 0x0014 PKCS#7 Store for X.509 Certificates 0x0015 X.509 Certificate ID and Signature for individual file 0x0016 X.509 Certificate ID for Central Directory The Header ID mappings defined by Info-ZIP and third parties are: 0x0065 IBM S/390 attributes - uncompressed 0x0066 IBM S/390 attributes - compressed 0x07c8 Info-ZIP Macintosh (old, J. Lee) 0x2605 ZipIt Macintosh (first version) 0x2705 ZipIt Macintosh v 1.3.5 and newer (w/o full filename) 0x334d Info-ZIP Macintosh (new, D. Haase's 'Mac3' field ) 0x4154 Tandem NSK 0x4341 Acorn/SparkFS (David Pilling) 0x4453 Windows NT security descriptor (binary ACL) 0x4704 VM/CMS 0x470f MVS 0x4854 Theos, old inofficial port 0x4b46 FWKCS MD5 (see below) 0x4c41 OS/2 access control list (text ACL) 0x4d49 Info-ZIP OpenVMS (obsolete) 0x4d63 Macintosh SmartZIP, by Macro Bambini 0x4f4c Xceed original location extra field 0x5356 AOS/VS (binary ACL) 0x5455 extended timestamp 0x5855 Info-ZIP Unix (original; also OS/2, NT, etc.) 0x554e Xceed unicode extra field 0x6375 Info-ZIP Unicode Comment 0x6542 BeOS (BeBox, PowerMac, etc.) 0x6854 Theos 0x7075 Info-ZIP Unicode Path 0x756e ASi Unix 0x7855 Info-ZIP Unix (previous new) 0x7875 Info-ZIP Unix (new) 0xfb4a SMS/QDOS The following are detailed descriptions of the known extra-field block types: -OS/2 Extended Attributes Extra Field: ==================================== The following is the layout of the OS/2 extended attributes "extra" block. (Last Revision 19960922) Note: all fields stored in Intel low-byte/high-byte order. Local-header version: Value Size Description ----- ---- ----------- (OS/2) 0x0009 Short tag for this extra block type TSize Short total data size for this block BSize Long uncompressed EA data size CType Short compression type EACRC Long CRC value for uncompressed EA data (var.) variable compressed EA data Central-header version: Value Size Description ----- ---- ----------- (OS/2) 0x0009 Short tag for this extra block type TSize Short total data size for this block (4) BSize Long size of uncompressed local EA data The value of CType is interpreted according to the "compression method" section above; i.e., 0 for stored, 8 for deflated, etc. The OS/2 extended attribute structure (FEA2LIST) is compressed and then stored in its entirety within this structure. There will only ever be one block of data in the variable-length field. -OS/2 Access Control List Extra Field: ==================================== The following is the layout of the OS/2 ACL extra block. (Last Revision 19960922) Local-header version: Value Size Description ----- ---- ----------- (ACL) 0x4c41 Short tag for this extra block type ("AL") TSize Short total data size for this block BSize Long uncompressed ACL data size CType Short compression type EACRC Long CRC value for uncompressed ACL data (var.) variable compressed ACL data Central-header version: Value Size Description ----- ---- ----------- (ACL) 0x4c41 Short tag for this extra block type ("AL") TSize Short total data size for this block (4) BSize Long size of uncompressed local ACL data The value of CType is interpreted according to the "compression method" section above; i.e., 0 for stored, 8 for deflated, etc. The uncompressed ACL data consist of a text header of the form "ACL1:%hX,%hd\n", where the first field is the OS/2 ACCINFO acc_attr member and the second is acc_count, followed by acc_count strings of the form "%s,%hx\n", where the first field is acl_ugname (user group name) and the second acl_access. This block type will be extended for other operating systems as needed. -Windows NT Security Descriptor Extra Field: ========================================== The following is the layout of the NT Security Descriptor (another type of ACL) extra block. (Last Revision 19960922) Local-header version: Value Size Description ----- ---- ----------- (SD) 0x4453 Short tag for this extra block type ("SD") TSize Short total data size for this block BSize Long uncompressed SD data size Version Byte version of uncompressed SD data format CType Short compression type EACRC Long CRC value for uncompressed SD data (var.) variable compressed SD data Central-header version: Value Size Description ----- ---- ----------- (SD) 0x4453 Short tag for this extra block type ("SD") TSize Short total data size for this block (4) BSize Long size of uncompressed local SD data The value of CType is interpreted according to the "compression method" section above; i.e., 0 for stored, 8 for deflated, etc. Version specifies how the compressed data are to be interpreted and allows for future expansion of this extra field type. Currently only version 0 is defined. For version 0, the compressed data are to be interpreted as a single valid Windows NT SECURITY_DESCRIPTOR data structure, in self-relative format. -PKWARE Win95/WinNT Extra Field: ============================== The following description covers PKWARE's "NTFS" attributes "extra" block, introduced with the release of PKZIP 2.50 for Windows. (Last Revision 20001118) (Note: At this time the Mtime, Atime and Ctime values may be used on any WIN32 system.) [Info-ZIP note: In the current implementations, this field has a fixed total data size of 32 bytes and is only stored as local extra field.] Value Size Description ----- ---- ----------- (NTFS) 0x000a Short Tag for this "extra" block type TSize Short Total Data Size for this block Reserved Long for future use Tag1 Short NTFS attribute tag value #1 Size1 Short Size of attribute #1, in bytes (var.) SubSize1 Attribute #1 data . . . TagN Short NTFS attribute tag value #N SizeN Short Size of attribute #N, in bytes (var.) SubSize1 Attribute #N data For NTFS, values for Tag1 through TagN are as follows: (currently only one set of attributes is defined for NTFS) Tag Size Description ----- ---- ----------- 0x0001 2 bytes Tag for attribute #1 Size1 2 bytes Size of attribute #1, in bytes (24) Mtime 8 bytes 64-bit NTFS file last modification time Atime 8 bytes 64-bit NTFS file last access time Ctime 8 bytes 64-bit NTFS file creation time The total length for this block is 28 bytes, resulting in a fixed size value of 32 for the TSize field of the NTFS block. The NTFS filetimes are 64-bit unsigned integers, stored in Intel (least significant byte first) byte order. They determine the number of 1.0E-07 seconds (1/10th microseconds!) past WinNT "epoch", which is "01-Jan-1601 00:00:00 UTC". -PKWARE OpenVMS Extra Field: ========================== The following is the layout of PKWARE's OpenVMS attributes "extra" block. (Last Revision 12/17/91) Note: all fields stored in Intel low-byte/high-byte order. Value Size Description ----- ---- ----------- (VMS) 0x000c Short Tag for this "extra" block type TSize Short Total Data Size for this block CRC Long 32-bit CRC for remainder of the block Tag1 Short OpenVMS attribute tag value #1 Size1 Short Size of attribute #1, in bytes (var.) Size1 Attribute #1 data . . . TagN Short OpenVMS attribute tage value #N SizeN Short Size of attribute #N, in bytes (var.) SizeN Attribute #N data Rules: 1. There will be one or more of attributes present, which will each be preceded by the above TagX & SizeX values. These values are identical to the ATR$C_XXXX and ATR$S_XXXX constants which are defined in ATR.H under OpenVMS C. Neither of these values will ever be zero. 2. No word alignment or padding is performed. 3. A well-behaved PKZIP/OpenVMS program should never produce more than one sub-block with the same TagX value. Also, there will never be more than one "extra" block of type 0x000c in a particular directory record. -Info-ZIP VMS Extra Field: ======================== The following is the layout of Info-ZIP's VMS attributes extra block for VAX or Alpha AXP. The local-header and central-header versions are identical. (Last Revision 19960922) Value Size Description ----- ---- ----------- (VMS2) 0x4d49 Short tag for this extra block type ("JM") TSize Short total data size for this block ID Long block ID Flags Short info bytes BSize Short uncompressed block size Reserved Long (reserved) (var.) variable compressed VMS file-attributes block The block ID is one of the following unterminated strings: "VFAB" struct FAB "VALL" struct XABALL "VFHC" struct XABFHC "VDAT" struct XABDAT "VRDT" struct XABRDT "VPRO" struct XABPRO "VKEY" struct XABKEY "VMSV" version (e.g., "V6.1"; truncated at hyphen) "VNAM" reserved The lower three bits of Flags indicate the compression method. The currently defined methods are: 0 stored (not compressed) 1 simple "RLE" 2 deflated The "RLE" method simply replaces zero-valued bytes with zero-valued bits and non-zero-valued bytes with a "1" bit followed by the byte value. The variable-length compressed data contains only the data corre- sponding to the indicated structure or string. Typically multiple VMS2 extra fields are present (each with a unique block type). -Info-ZIP Macintosh Extra Field: ============================== The following is the layout of the (old) Info-ZIP resource-fork extra block for Macintosh. The local-header and central-header versions are identical. (Last Revision 19960922) Value Size Description ----- ---- ----------- (Mac) 0x07c8 Short tag for this extra block type TSize Short total data size for this block "JLEE" beLong extra-field signature FInfo 16 bytes Macintosh FInfo structure CrDat beLong HParamBlockRec fileParam.ioFlCrDat MdDat beLong HParamBlockRec fileParam.ioFlMdDat Flags beLong info bits DirID beLong HParamBlockRec fileParam.ioDirID VolName 28 bytes volume name (optional) All fields but the first two are in native Macintosh format (big-endian Motorola order, not little-endian Intel). The least significant bit of Flags is 1 if the file is a data fork, 0 other- wise. In addition, if this extra field is present, the filename has an extra 'd' or 'r' appended to indicate data fork or resource fork. The 28-byte VolName field may be omitted. -ZipIt Macintosh Extra Field (long): ================================== The following is the layout of the ZipIt extra block for Macintosh. The local-header and central-header versions are identical. (Last Revision 19970130) Value Size Description ----- ---- ----------- (Mac2) 0x2605 Short tag for this extra block type TSize Short total data size for this block "ZPIT" beLong extra-field signature FnLen Byte length of FileName FileName variable full Macintosh filename FileType Byte[4] four-byte Mac file type string Creator Byte[4] four-byte Mac creator string -ZipIt Macintosh Extra Field (short): =================================== The following is the layout of a shortened variant of the ZipIt extra block for Macintosh (without "full name" entry). This variant is used by ZipIt 1.3.5 and newer for entries that do not need a "full Mac filename" record. The local-header and central-header versions are identical. (Last Revision 19980903) Value Size Description ----- ---- ----------- (Mac2b) 0x2705 Short tag for this extra block type TSize Short total data size for this block (12) "ZPIT" beLong extra-field signature FileType Byte[4] four-byte Mac file type string Creator Byte[4] four-byte Mac creator string -Info-ZIP Macintosh Extra Field (new): ==================================== The following is the layout of the (new) Info-ZIP extra block for Macintosh, designed by Dirk Haase. All values are in little-endian. (Last Revision 19981005) Local-header version: Value Size Description ----- ---- ----------- (Mac3) 0x334d Short tag for this extra block type ("M3") TSize Short total data size for this block BSize Long uncompressed finder attribute data size Flags Short info bits fdType Byte[4] Type of the File (4-byte string) fdCreator Byte[4] Creator of the File (4-byte string) (CType) Short compression type (CRC) Long CRC value for uncompressed MacOS data Attribs variable finder attribute data (see below) Central-header version: Value Size Description ----- ---- ----------- (Mac3) 0x334d Short tag for this extra block type ("M3") TSize Short total data size for this block BSize Long uncompressed finder attribute data size Flags Short info bits fdType Byte[4] Type of the File (4-byte string) fdCreator Byte[4] Creator of the File (4-byte string) The third bit of Flags in both headers indicates whether the LOCAL extra field is uncompressed (and therefore whether CType and CRC are omitted): Bits of the Flags: bit 0 if set, file is a data fork; otherwise unset bit 1 if set, filename will be not changed bit 2 if set, Attribs is uncompressed (no CType, CRC) bit 3 if set, date and times are in 64 bit if zero date and times are in 32 bit. bit 4 if set, timezone offsets fields for the native Mac times are omitted (UTC support deactivated) bits 5-15 reserved; Attributes: Attribs is a Mac-specific block of data in little-endian format with the following structure (if compressed, uncompress it first): Value Size Description ----- ---- ----------- fdFlags Short Finder Flags fdLocation.v Short Finder Icon Location fdLocation.h Short Finder Icon Location fdFldr Short Folder containing file FXInfo 16 bytes Macintosh FXInfo structure FXInfo-Structure: fdIconID Short fdUnused[3] Short unused but reserved 6 bytes fdScript Byte Script flag and number fdXFlags Byte More flag bits fdComment Short Comment ID fdPutAway Long Home Dir ID FVersNum Byte file version number may be not used by MacOS ACUser Byte directory access rights FlCrDat ULong date and time of creation FlMdDat ULong date and time of last modification FlBkDat ULong date and time of last backup These time numbers are original Mac FileTime values (local time!). Currently, date-time width is 32-bit, but future version may support be 64-bit times (see flags) CrGMTOffs Long(signed!) difference "local Creat. time - UTC" MdGMTOffs Long(signed!) difference "local Modif. time - UTC" BkGMTOffs Long(signed!) difference "local Backup time - UTC" These "local time - UTC" differences (stored in seconds) may be used to support timestamp adjustment after inter-timezone transfer. These fields are optional; bit 4 of the flags word controls their presence. Charset Short TextEncodingBase (Charset) valid for the following two fields FullPath variable Path of the current file. Zero terminated string (C-String) Currently coded in the native Charset. Comment variable Finder Comment of the current file. Zero terminated string (C-String) Currently coded in the native Charset. -SmartZIP Macintosh Extra Field: ==================================== The following is the layout of the SmartZIP extra block for Macintosh, designed by Marco Bambini. Local-header version: Value Size Description ----- ---- ----------- 0x4d63 Short tag for this extra block type ("cM") TSize Short total data size for this block (64) "dZip" beLong extra-field signature fdType Byte[4] Type of the File (4-byte string) fdCreator Byte[4] Creator of the File (4-byte string) fdFlags beShort Finder Flags fdLocation.v beShort Finder Icon Location fdLocation.h beShort Finder Icon Location fdFldr beShort Folder containing file CrDat beLong HParamBlockRec fileParam.ioFlCrDat MdDat beLong HParamBlockRec fileParam.ioFlMdDat frScroll.v Byte vertical pos. of folder's scroll bar fdScript Byte Script flag and number frScroll.h Byte horizontal pos. of folder's scroll bar fdXFlags Byte More flag bits FileName Byte[32] full Macintosh filename (pascal string) All fields but the first two are in native Macintosh format (big-endian Motorola order, not little-endian Intel). The extra field size is fixed to 64 bytes. The local-header and central-header versions are identical. -Acorn SparkFS Extra Field: ========================= The following is the layout of David Pilling's SparkFS extra block for Acorn RISC OS. The local-header and central-header versions are identical. (Last Revision 19960922) Value Size Description ----- ---- ----------- (Acorn) 0x4341 Short tag for this extra block type ("AC") TSize Short total data size for this block (20) "ARC0" Long extra-field signature LoadAddr Long load address or file type ExecAddr Long exec address Attr Long file permissions Zero Long reserved; always zero The following bits of Attr are associated with the given file permissions: bit 0 user-writable ('W') bit 1 user-readable ('R') bit 2 reserved bit 3 locked ('L') bit 4 publicly writable ('w') bit 5 publicly readable ('r') bit 6 reserved bit 7 reserved -VM/CMS Extra Field: ================== The following is the layout of the file-attributes extra block for VM/CMS. The local-header and central-header versions are identical. (Last Revision 19960922) Value Size Description ----- ---- ----------- (VM/CMS) 0x4704 Short tag for this extra block type TSize Short total data size for this block flData variable file attributes data flData is an uncompressed fldata_t struct. -MVS Extra Field: =============== The following is the layout of the file-attributes extra block for MVS. The local-header and central-header versions are identical. (Last Revision 19960922) Value Size Description ----- ---- ----------- (MVS) 0x470f Short tag for this extra block type TSize Short total data size for this block flData variable file attributes data flData is an uncompressed fldata_t struct. -PKWARE Unix Extra Field: ======================== The following is the layout of PKWARE's Unix "extra" block. It was introduced with the release of PKZIP for Unix 2.50. Note: all fields are stored in Intel low-byte/high-byte order. (Last Revision 19980901) This field has a minimum data size of 12 bytes and is only stored as local extra field. Value Size Description ----- ---- ----------- (Unix0) 0x000d Short Tag for this "extra" block type TSize Short Total Data Size for this block AcTime Long time of last access (UTC/GMT) ModTime Long time of last modification (UTC/GMT) UID Short Unix user ID GID Short Unix group ID (var) variable Variable length data field The variable length data field will contain file type specific data. Currently the only values allowed are the original "linked to" file names for hard or symbolic links, and the major and minor device node numbers for character and block device nodes. Since device nodes cannot be either symbolic or hard links, only one set of variable length data is stored. Link files will have the name of the original file stored. This name is NOT NULL terminated. Its size can be determined by checking TSize - 12. Device entries will have eight bytes stored as two 4 byte entries (in little-endian format). The first entry will be the major device number, and the second the minor device number. [Info-ZIP note: The fixed part of this field has the same layout as Info-ZIP's abandoned "Unix1 timestamps & owner ID info" extra field; only the two tag bytes are different.] -PATCH Descriptor Extra Field: ============================ The following is the layout of the Patch Descriptor "extra" block. Note: all fields stored in Intel low-byte/high-byte order. Value Size Description ----- ---- ----------- (Patch) 0x000f Short Tag for this "extra" block type TSize Short Size of the total "extra" block Version Short Version of the descriptor Flags Long Actions and reactions (see below) OldSize Long Size of the file about to be patched OldCRC Long 32-bit CRC of the file about to be patched NewSize Long Size of the resulting file NewCRC Long 32-bit CRC of the resulting file Actions and reactions Bits Description ---- ---------------- 0 Use for autodetection 1 Treat as selfpatch 2-3 RESERVED 4-5 Action (see below) 6-7 RESERVED 8-9 Reaction (see below) to absent file 10-11 Reaction (see below) to newer file 12-13 Reaction (see below) to unknown file 14-15 RESERVED 16-31 RESERVED Actions Action Value ------ ----- none 0 add 1 delete 2 patch 3 Reactions Reaction Value -------- ----- ask 0 skip 1 ignore 2 fail 3 -PKCS#7 Store for X.509 Certificates: =================================== This field is contains the information about each certificate a file is signed with. This field should only appear in the first central directory record, and will be ignored in any other record. Note: all fields stored in Intel low-byte/high-byte order. Value Size Description ----- ---- ----------- (Store) 0x0014 2 bytes Tag for this "extra" block type SSize 2 bytes Size of the store data SData (variable) Data about the store SData Value Size Description ----- ---- ----------- Version 2 bytes Version number, 0x0001 for now StoreD (variable) Actual store data The StoreD member is suitable for passing as the pbData member of a CRYPT_DATA_BLOB to the CertOpenStore() function in Microsoft's CryptoAPI. The SSize member above will be cbData + 6, where cbData is the cbData member of the same CRYPT_DATA_BLOB. The encoding type to pass to CertOpenStore() should be PKCS_7_ANS_ENCODING | X509_ASN_ENCODING. -X.509 Certificate ID and Signature for individual file: ====================================================== This field contains the information about which certificate in the PKCS#7 Store was used to sign the particular file. It also contains the signature data. This field can appear multiple times, but can only appear once per certificate. Note: all fields stored in Intel low-byte/high-byte order. Value Size Description ----- ---- ----------- (CID) 0x0015 2 bytes Tag for this "extra" block type CSize 2 bytes Size of Method Method (variable) Method Value Size Description ----- ---- ----------- Version 2 bytes Version number, for now 0x0001 AlgID 2 bytes Algorithm ID used for signing IDSize 2 bytes Size of Certificate ID data CertID (variable) Certificate ID data SigSize 2 bytes Size of Signature data Sig (variable) Signature data CertID Value Size Description ----- ---- ----------- Size1 4 bytes Size of CertID, should be (IDSize - 4) Size1 4 bytes A bug in version one causes this value to appear twice. IssSize 4 bytes Issuer data size Issuer (variable) Issuer data SerSize 4 bytes Serial Number size Serial (variable) Serial Number data The Issuer and IssSize members are suitable for creating a CRYPT_DATA_BLOB to be the Issuer member of a CERT_INFO struct. The Serial and SerSize members would be the SerialNumber member of the same CERT_INFO struct. This struct would be used to find the certificate in the store the file was signed with. Those structures are from the MS CryptoAPI. Sig and SigSize are the actual signature data and size generated by signing the file with the MS CryptoAPI using a hash created with the given AlgID. -X.509 Certificate ID and Signature for central directory: ======================================================== This field contains the information about which certificate in the PKCS#7 Store was used to sign the central directory. It should only appear with the first central directory record, along with the store. The data structure is the same as the CID, except that SigSize will be 0, and there will be no Sig member. This field is also kept after the last central directory record, as the signature data (ID 0x05054b50, it looks like a central directory record of a different type). This second copy of the data is the Signature Data member of the record, and will have a SigSize that is non-zero, and will have Sig data. Note: all fields stored in Intel low-byte/high-byte order. Value Size Description ----- ---- ----------- (CDID) 0x0016 2 bytes Tag for this "extra" block type CSize 2 bytes Size of Method Method (variable) -ZIP64 Extended Information Extra Field: ====================================== The following is the layout of the ZIP64 extended information "extra" block. If one of the size or offset fields in the Local or Central directory record is too small to hold the required data, a ZIP64 extended information record is created. The order of the fields in the ZIP64 extended information record is fixed, but the fields will only appear if the corresponding Local or Central directory record field is set to 0xFFFF or 0xFFFFFFFF. Note: all fields stored in Intel low-byte/high-byte order. Value Size Description ----- ---- ----------- (ZIP64) 0x0001 2 bytes Tag for this "extra" block type Size 2 bytes Size of this "extra" block Original Size 8 bytes Original uncompresseed file size Compressed Size 8 bytes Size of compressed data Relative Header Offset 8 bytes Offset of local header record Disk Start Number 4 bytes Number of the disk on which this file starts This entry in the Local header must include BOTH original and compressed file sizes. -Extended Timestamp Extra Field: ============================== The following is the layout of the extended-timestamp extra block. (Last Revision 19970118) Local-header version: Value Size Description ----- ---- ----------- (time) 0x5455 Short tag for this extra block type ("UT") TSize Short total data size for this block Flags Byte info bits (ModTime) Long time of last modification (UTC/GMT) (AcTime) Long time of last access (UTC/GMT) (CrTime) Long time of original creation (UTC/GMT) Central-header version: Value Size Description ----- ---- ----------- (time) 0x5455 Short tag for this extra block type ("UT") TSize Short total data size for this block Flags Byte info bits (refers to local header!) (ModTime) Long time of last modification (UTC/GMT) The central-header extra field contains the modification time only, or no timestamp at all. TSize is used to flag its presence or absence. But note: If "Flags" indicates that Modtime is present in the local header field, it MUST be present in the central header field, too! This correspondence is required because the modification time value may be used to support trans-timezone freshening and updating operations with zip archives. The time values are in standard Unix signed-long format, indicating the number of seconds since 1 January 1970 00:00:00. The times are relative to Coordinated Universal Time (UTC), also sometimes referred to as Greenwich Mean Time (GMT). To convert to local time, the software must know the local timezone offset from UTC/GMT. The lower three bits of Flags in both headers indicate which time- stamps are present in the LOCAL extra field: bit 0 if set, modification time is present bit 1 if set, access time is present bit 2 if set, creation time is present bits 3-7 reserved for additional timestamps; not set Those times that are present will appear in the order indicated, but any combination of times may be omitted. (Creation time may be present without access time, for example.) TSize should equal (1 + 4*(number of set bits in Flags)), as the block is currently defined. Other timestamps may be added in the future. -Info-ZIP Unix Extra Field (type 1): ================================== The following is the layout of the old Info-ZIP extra block for Unix. It has been replaced by the extended-timestamp extra block (0x5455) and the Unix type 2 extra block (0x7855). (Last Revision 19970118) Local-header version: Value Size Description ----- ---- ----------- (Unix1) 0x5855 Short tag for this extra block type ("UX") TSize Short total data size for this block AcTime Long time of last access (UTC/GMT) ModTime Long time of last modification (UTC/GMT) UID Short Unix user ID (optional) GID Short Unix group ID (optional) Central-header version: Value Size Description ----- ---- ----------- (Unix1) 0x5855 Short tag for this extra block type ("UX") TSize Short total data size for this block AcTime Long time of last access (GMT/UTC) ModTime Long time of last modification (GMT/UTC) The file access and modification times are in standard Unix signed- long format, indicating the number of seconds since 1 January 1970 00:00:00. The times are relative to Coordinated Universal Time (UTC), also sometimes referred to as Greenwich Mean Time (GMT). To convert to local time, the software must know the local timezone offset from UTC/GMT. The modification time may be used by non-Unix systems to support inter-timezone freshening and updating of zip archives. The local-header extra block may optionally contain UID and GID info for the file. The local-header TSize value is the only indication of this. Note that Unix UIDs and GIDs are usually specific to a particular machine, and they generally require root access to restore. This extra field type is obsolete, but it has been in use since mid-1994. Therefore future archiving software should continue to support it. Some guidelines: An archive member should either contain the old "Unix1" extra field block or the new extra field types "time" and/or "Unix2". If both the old "Unix1" block type and one or both of the new block types "time" and "Unix2" are found, the "Unix1" block should be considered invalid and ignored. Unarchiving software should recognize both old and new extra field block types, but the info from new types overrides the old "Unix1" field. Archiving software should recognize "Unix1" extra fields for timestamp comparison but never create it for updated, freshened or new archive members. When copying existing members to a new archive, any "Unix1" extra field blocks should be converted to the new "time" and/or "Unix2" types. -Info-ZIP Unix Extra Field (type 2): ================================== The following is the layout of the new Info-ZIP extra block for Unix. (Last Revision 19960922) Local-header version: Value Size Description ----- ---- ----------- (Unix2) 0x7855 Short tag for this extra block type ("Ux") TSize Short total data size for this block (4) UID Short Unix user ID GID Short Unix group ID Central-header version: Value Size Description ----- ---- ----------- (Unix2) 0x7855 Short tag for this extra block type ("Ux") TSize Short total data size for this block (0) The data size of the central-header version is zero; it is used solely as a flag that UID/GID info is present in the local-header extra field. If additional fields are ever added to the local version, the central version may be extended to indicate this. Note that Unix UIDs and GIDs are usually specific to a particular machine, and they generally require root access to restore. -ASi Unix Extra Field: ==================== The following is the layout of the ASi extra block for Unix. The local-header and central-header versions are identical. (Last Revision 19960916) Value Size Description ----- ---- ----------- (Unix3) 0x756e Short tag for this extra block type ("nu") TSize Short total data size for this block CRC Long CRC-32 of the remaining data Mode Short file permissions SizDev Long symlink'd size OR major/minor dev num UID Short user ID GID Short group ID (var.) variable symbolic link filename Mode is the standard Unix st_mode field from struct stat, containing user/group/other permissions, setuid/setgid and symlink info, etc. If Mode indicates that this file is a symbolic link, SizDev is the size of the file to which the link points. Otherwise, if the file is a device, SizDev contains the standard Unix st_rdev field from struct stat (includes the major and minor numbers of the device). SizDev is undefined in other cases. If Mode indicates that the file is a symbolic link, the final field will be the name of the file to which the link points. The file- name length can be inferred from TSize. [Note that TSize may incorrectly refer to the data size not counting the CRC; i.e., it may be four bytes too small.] -BeOS Extra Field: ================ The following is the layout of the file-attributes extra block for BeOS. (Last Revision 19970531) Local-header version: Value Size Description ----- ---- ----------- (BeOS) 0x6542 Short tag for this extra block type ("Be") TSize Short total data size for this block BSize Long uncompressed file attribute data size Flags Byte info bits (CType) Short compression type (CRC) Long CRC value for uncompressed file attribs Attribs variable file attribute data Central-header version: Value Size Description ----- ---- ----------- (BeOS) 0x6542 Short tag for this extra block type ("Be") TSize Short total data size for this block (5) BSize Long size of uncompr. local EF block data Flags Byte info bits The least significant bit of Flags in both headers indicates whether the LOCAL extra field is uncompressed (and therefore whether CType and CRC are omitted): bit 0 if set, Attribs is uncompressed (no CType, CRC) bits 1-7 reserved; if set, assume error or unknown data Currently the only supported compression types are deflated (type 8) and stored (type 0); the latter is not used by Info-ZIP's Zip but is supported by UnZip. Attribs is a BeOS-specific block of data in big-endian format with the following structure (if compressed, uncompress it first): Value Size Description ----- ---- ----------- Name variable attribute name (null-terminated string) Type Long attribute type (32-bit unsigned integer) Size Long Long data size for this sub-block (64 bits) Data variable attribute data The attribute structure is repeated for every attribute. The Data field may contain anything--text, flags, bitmaps, etc. -SMS/QDOS Extra Field: ==================== The following is the layout of the file-attributes extra block for SMS/QDOS. The local-header and central-header versions are identical. (Last Revision 19960929) Value Size Description ----- ---- ----------- (QDOS) 0xfb4a Short tag for this extra block type TSize Short total data size for this block LongID Long extra-field signature (ExtraID) Long additional signature/flag bytes QDirect 64 bytes qdirect structure LongID may be "QZHD" or "QDOS". In the latter case, ExtraID will be present. Its first three bytes are "02\0"; the last byte is currently undefined. QDirect contains the file's uncompressed directory info (qdirect struct). Its elements are in native (big-endian) format: d_length beLong file length d_access byte file access type d_type byte file type d_datalen beLong data length d_reserved beLong unused d_szname beShort size of filename d_name 36 bytes filename d_update beLong time of last update d_refdate beLong file version number d_backup beLong time of last backup (archive date) -AOS/VS Extra Field: ================== The following is the layout of the extra block for Data General AOS/VS. The local-header and central-header versions are identical. (Last Revision 19961125) Value Size Description ----- ---- ----------- (AOSVS) 0x5356 Short tag for this extra block type ("VS") TSize Short total data size for this block "FCI\0" Long extra-field signature Version Byte version of AOS/VS extra block (10 = 1.0) Fstat variable fstat packet AclBuf variable raw ACL data ($MXACL bytes) Fstat contains the file's uncompressed fstat packet, which is one of the following: normal fstat packet (P_FSTAT struct) DIR/CPD fstat packet (P_FSTAT_DIR struct) unit (device) fstat packet (P_FSTAT_UNIT struct) IPC file fstat packet (P_FSTAT_IPC struct) AclBuf contains the raw ACL data; its length is $MXACL. -Tandem NSK Extra Field: ====================== The following is the layout of the file-attributes extra block for Tandem NSK. The local-header and central-header versions are identical. (Last Revision 19981221) Value Size Description ----- ---- ----------- (TA) 0x4154 Short tag for this extra block type ("TA") TSize Short total data size for this block (20) NSKattrs 20 Bytes NSK attributes -THEOS Extra Field: ================= The following is the layout of the file-attributes extra block for Theos. The local-header and central-header versions are identical. (Last Revision 19990206) Value Size Description ----- ---- ----------- (Theos) 0x6854 Short 'Th' signature size Short size of extra block flags Byte reserved for future use filesize Long file size fileorg Byte type of file (see below) keylen Short key length for indexed and keyed files, data segment size for 16 bits programs reclen Short record length for indexed,keyed and direct, text segment size for 16 bits programs filegrow Byte growing factor for indexed,keyed and direct protect Byte protections (see below) reserved Short reserved for future use File types ========== 0x80 library (keyed access list of files) 0x40 directory 0x10 stream file 0x08 direct file 0x04 keyed file 0x02 indexed file 0x0e reserved 0x01 16 bits real mode program (obsolete) 0x21 16 bits protected mode program 0x41 32 bits protected mode program Protection codes ================ User protection --------------- 0x01 non readable 0x02 non writable 0x04 non executable 0x08 non erasable Other protection ---------------- 0x10 non readable 0x20 non writable 0x40 non executable Theos before 4.0 0x40 modified Theos 4.x 0x80 not hidden -THEOS old inofficial Extra Field: ================================ The following is the layout of an inoffical former version of a Theos file-attributes extra blocks. This layout was never published and is no longer created. However, UnZip can optionally support it when compiling with the option flag OLD_THEOS_EXTRA defined. Both the local-header and central-header versions are identical. (Last Revision 19990206) Value Size Description ----- ---- ----------- (THS0) 0x4854 Short 'TH' signature size Short size of extra block flags Short reserved for future use filesize Long file size reclen Short record length for indexed,keyed and direct, text segment size for 16 bits programs keylen Short key length for indexed and keyed files, data segment size for 16 bits programs filegrow Byte growing factor for indexed,keyed and direct reserved 3 Bytes reserved for future use -FWKCS MD5 Extra Field: ===================== The FWKCS Contents_Signature System, used in automatically identifying files independent of filename, optionally adds and uses an extra field to support the rapid creation of an enhanced contents_signature. There is no local-header version; the following applies only to the central header. (Last Revision 19961207) Central-header version: Value Size Description ----- ---- ----------- (MD5) 0x4b46 Short tag for this extra block type ("FK") TSize Short total data size for this block (19) "MD5" 3 bytes extra-field signature MD5hash 16 bytes 128-bit MD5 hash of uncompressed data (low byte first) When FWKCS revises a .ZIP file central directory to add this extra field for a file, it also replaces the central directory entry for that file's uncompressed file length with a measured value. FWKCS provides an option to strip this extra field, if present, from a .ZIP file central directory. In adding this extra field, FWKCS preserves .ZIP file Authenticity Verification; if stripping this extra field, FWKCS preserves all versions of AV through PKZIP version 2.04g. FWKCS, and FWKCS Contents_Signature System, are trademarks of Frederick W. Kantor. (1) R. Rivest, RFC1321.TXT, MIT Laboratory for Computer Science and RSA Data Security, Inc., April 1992. ll.76-77: "The MD5 algorithm is being placed in the public domain for review and possible adoption as a standard." -Info-ZIP Unicode Path Extra Field: ================================= Stores the UTF-8 version of the entry path as stored in the local header and central directory header. (Last Revision 20070912) Value Size Description ----- ---- ----------- (UPath) 0x7075 Short tag for this extra block type ("up") TSize Short total data size for this block Version 1 byte version of this extra field, currently 1 NameCRC32 4 bytes File Name Field CRC32 Checksum UnicodeName Variable UTF-8 version of the entry File Name Currently Version is set to the number 1. If there is a need to change this field, the version will be incremented. Changes may not be backward compatible so this extra field should not be used if the version is not recognized. The NameCRC32 is the standard zip CRC32 checksum of the File Name field in the header. This is used to verify that the header File Name field has not changed since the Unicode Path extra field was created. This can happen if a utility renames the entry but does not update the UTF-8 path extra field. If the CRC check fails, this UTF-8 Path Extra Field should be ignored and the File Name field in the header used instead. The UnicodeName is the UTF-8 version of the contents of the File Name field in the header. As UnicodeName is defined to be UTF-8, no UTF-8 byte order mark (BOM) is used. The length of this field is determined by subtracting the size of the previous fields from TSize. If both the File Name and Comment fields are UTF-8, the new General Purpose Bit Flag, bit 11 (Language encoding flag (EFS)), can be used to indicate that both the header File Name and Comment fields are UTF-8 and, in this case, the Unicode Path and Unicode Comment extra fields are not needed and should not be created. Note that, for backward compatibility, bit 11 should only be used if the native character set of the paths and comments being zipped up are already in UTF-8. The same method, either bit 11 or extra fields, should be used in both the local and central directory headers. -Info-ZIP Unicode Comment Extra Field: ==================================== Stores the UTF-8 version of the entry comment as stored in the central directory header. (Last Revision 20070912) Value Size Description ----- ---- ----------- (UCom) 0x6375 Short tag for this extra block type ("uc") TSize Short total data size for this block Version 1 byte version of this extra field, currently 1 ComCRC32 4 bytes Comment Field CRC32 Checksum UnicodeCom Variable UTF-8 version of the entry comment Currently Version is set to the number 1. If there is a need to change this field, the version will be incremented. Changes may not be backward compatible so this extra field should not be used if the version is not recognized. The ComCRC32 is the standard zip CRC32 checksum of the Comment field in the central directory header. This is used to verify that the comment field has not changed since the Unicode Comment extra field was created. This can happen if a utility changes the Comment field but does not update the UTF-8 Comment extra field. If the CRC check fails, this Unicode Comment extra field should be ignored and the Comment field in the header used. The UnicodeCom field is the UTF-8 version of the entry comment field in the header. As UnicodeCom is defined to be UTF-8, no UTF-8 byte order mark (BOM) is used. The length of this field is determined by subtracting the size of the previous fields from TSize. If both the File Name and Comment fields are UTF-8, the new General Purpose Bit Flag, bit 11 (Language encoding flag (EFS)), can be used to indicate both the header File Name and Comment fields are UTF-8 and, in this case, the Unicode Path and Unicode Comment extra fields are not needed and should not be created. Note that, for backward compatibility, bit 11 should only be used if the native character set of the paths and comments being zipped up are already in UTF-8. The same method, either bit 11 or extra fields, should be used in both the local and central directory headers. -Info-ZIP New Unix Extra Field: ==================================== Currently stores Unix UIDs/GIDs up to 32 bits. (Last Revision 20080509) Value Size Description ----- ---- ----------- (UnixN) 0x7875 Short tag for this extra block type ("ux") TSize Short total data size for this block Version 1 byte version of this extra field, currently 1 UIDSize 1 byte Size of UID field UID Variable UID for this entry GIDSize 1 byte Size of GID field GID Variable GID for this entry Currently Version is set to the number 1. If there is a need to change this field, the version will be incremented. Changes may not be backward compatible so this extra field should not be used if the version is not recognized. UIDSize is the size of the UID field in bytes. This size should match the size of the UID field on the target OS. UID is the UID for this entry in standard little endian format. GIDSize is the size of the GID field in bytes. This size should match the size of the GID field on the target OS. GID is the GID for this entry in standard little endian format. If both the old 16-bit Unix extra field (tag 0x7855, Info-ZIP Unix) and this extra field are present, the values in this extra field supercede the values in that extra field. zip30/proginfo/fileinfo.cms0100644000076400000060000002466606134410226014117 0ustar edisk[Quoting from a C/370 manual, courtesy of Carl Forde.] C/370 supports three types of input and output: text streams, binary streams, and record I/O. Text and binary streams are both ANSI standards; record I/O is a C/370 extension. [...] Record I/O is a C/370 extension to the ANSI standard. For files opened in record format, C/370 reads and writes one record at a time. If you try to write more data to a record than the record can hold, the data is truncated. For record I/O, C/370 only allows the use of fread() and fwrite() to read and write to the files. Any other functions (such as fprintf(), fscanf(), getc(), and putc()) fail. For record-orientated files, records do not change size when you update them. If the new data has fewer characters than the original record, the new data fills the first n characters, where n is the number of characters of the new data. The record will remain the same size, and the old characters (those after) n are left unchanged. A subsequent update begins at the next boundary. For example, if you have the string "abcdefgh": abcdefgh and you overwrite it with the string "1234", the record will look like this: 1234efgh C/370 record I/O is binary. That is, it does not interpret any of the data in a record file and therefore does not recognize control characters. The record model consists of: * A record, which is the unit of data transmitted to and from a program * A block, which is the unit of data transmitted to and from a device. Each block may contain one or more records. In the record model of I/O, records and blocks have the following attributes: RECFM Specifies the format of the data or how the data is organized on the physical device. LRECL Specifies the length of logical records (as opposed to physical ones). BLKSIZE Specifies the length of physical records (blocks on the physical device). Opening a File by Filename The filename that you specify on the call to fopen() or freopen() must be in the following format: >> ----filename---- ----filetype-------------------- | | | | --.-- -- --filemode-- | | --.-- where filename is a 1- to 8-character string of any of the characters, A-Z, a-z, 0-9, and +, -, $, #, @, :, and _. You can separate it from the filetype with one or more spaces, or with a period. [Further note: filenames are fully case-sensitive, as in Unix.] filetype is a 1- to 8-character string of any of the characters, A-Z, a-z, 0-9, and +, -, $, #, @, :, and _. You can separate it from the filemode with one or more spaces, or with a period. The separator between filetype and filemode must be the same as the one between filename and filetype. filemode is a 1- to 2-character string. The first must be any of the characters A-Z, a-z, or *. If you use the asis parameter on the fopen() or freopen() call, the first character of the filemode must be a capital letter or an asterisk. Otherwise, the function call fails. The second character of filemode is optional; if you specify it, it must be any of the digits 0-6. You cannot specify the second character if you have specified * for the first one. If you do not use periods as separators, there is no limit to how much whitespace you can have before and after the filename, the filetype, and filemode. Opening a File without a File Mode Specified If you omit the file mode or specify * for it, C/370 does one of the following when you call fopen() or freopen(): * If you have specified a read mode, C/370 looks for the named file on all the accessed readable disks, in order. If it does not find the file, the fopen() or freopen() call fails. * If you have specified any of the write modes, C/370 writes the file on the first writable disk you have accessed. Specifying a write mode on an fopen() or freopen() call that contains the filename of an existing file destroys that file. If you do not have any writable disks accessed, the call fails. fopen() and freopen() parameters recfm CMS supports only two RECFMs, V and F. [note that MVS supports 27(!) different RECFMs.] If you do not specify the RECFM for a file, C/370 determines whether is is in fixed or variable format. lrecl and blksize For files in fixed format, CMS allows records to be read and written in blocks. To have a fixed format CMS file treated as a fixed blocked CMS file, you can open the file with recfm=fb and specify the lrecl and blksize. If you do not specify a recfm on the open, the blksize can be a multiple of the lrecl, and the file is treated as if it were blocked. For files in variable format, the CMS LRECL is different from the LRECL for the record model. In the record model, the LRECL is equal to the data length plus 4 bytes (for the record descriptor word), and the BLKSIZE is equal to the LRECL plus 4 bytes (for the block descriptor word). In CMS, BDWs and RDWs do not exist, but because CMS follows the record model, you must still account for them. When you specify V, you must still allocate the record descriptor word and block descriptor word. That is, if you want a maximum of n bytes per record, you must specify a minimum LRECL of n+4 and a minimum BLKSIZE of n+8. When you are appending to V files, you can enlarge the record size dynamically, but only if you have not specified LRECL or BLKSIZE on the fopen() or freopen() command that opened the file. type If you specify this parameter, the only valid value for CMS disk files is type =record. This opens a file for record I/O. asis If you use this parameter, you can open files with mixed-case filenames such as JaMeS dAtA or pErCy.FILE. If you specify this parameter, the file mode that you specify must be a capital letter (if it is not an asterisk); otherwise; the function call fails and the value returned is NULL. Reading from Record I/O Files fread() is the only interface allowed for reading record I/O files. Each time you call fread() for a record I/O file, fread() reads one record from the system. If you call fread() with a request for less than a complete record, the requested bytes are copied to your buffer, and the file position is set to the start fo the next record. If the request is for more bytes that are in the record, one record is read and the position is set to the start of the next record. C/370 does not strip any blank characters or interpret any data. fread() returns the number of items read successfully, so if you pass a size argument equal to 1 and a count argument equal to the maximum expected length of the record, fread() returns the length, in bytes, of the record read. If you pass a size argument equal to the maximum expected length of the record, and a count argument equal to 1, fread() returns either 0 or 1, indicating whether a record of length size read. If a record is read successfully but is less than size bytes long, fread() returns 0. Writing to Record I/O Files fwrite() is the only interface allowed for writing to a file opened for record I/O. Only one record is written at a time. If you attempt to write more new data than a full record can hold or try to update a record with more data than it currently has, C/370 truncates your output at the record boundary. When C/370 performs a truncation, it sets errno and raises SIGIOERR, if SIGIOERR is not set to SIG_IGN. When you are writing new records to a fixed-record I/O file, if you try to write a short record, C/370 pads the record with nulls out to LRECL. At the completion of an fwrite(), the file position is at the start of the next record. For new data, the block is flushed out to the system as soon as it is full. fldata() Behavior When you call the fldata() function for an open CMS minidisk file, it returns a data structure that looks like this: struct __filedata { unsigned int __recfmF : 1, /* fixed length records */ __recfmV : 1, /* variable length records */ __recfmU : 1, /* n/a */ __recfmS : 1, /* n/a */ __recfmBlk : 1, /* n/a */ __recfmASA : 1, /* text mode and ASA */ __recfmM : 1, /* n/a */ __dsorgPO : 1, /* n/a */ __dsorgPDSmem : 1, /* n/a */ __dsorgPDSdir : 1, /* n/a */ __dsorgPS : 1, /* sequential data set */ __dsorgConcat : 1, /* n/a */ __dsorgMem : 1, /* n/a */ __dsorgHiper : 1, /* n/a */ __dsorgTemp : 1, /* created with tmpfile() */ __dsorgVSAM : 1, /* n/a */ __reserve1 : 1, /* n/a */ __openmode : 2, /* see below 1 */ __modeflag : 4, /* see below 2 */ __reserve2 : 9, /* n/a */ char __device; __DISK unsigned long __blksize, /* see below 3 */ __maxreclen; /* see below 4 */ unsigned short __vsamtype; /* n/a */ unsigned long __vsamkeylen; /* n/a */ unsigned long __vsamRKP; /* n/a */ char * __dsname; /* fname ftype fmode */ unsigned int __reserve4; /* n/a */ /* note 1: values are: __TEXT, __BINARY, __RECORD note 2: values are: __READ, __WRITE, __APPEND, __UPDATE these values can be added together to determine the return value; for example, a file opened with a+ will have the value __READ + __APPEND. note 3: total block size of the file, including ASA characters as well as RDW information note 4: maximum record length of the data only (includes ASA characters but excludes RDW information). */ }; zip30/proginfo/infozip.who0100644000076400000060000004022410747007444014012 0ustar ediskThese members of the Info-ZIP group contributed to the development and testing of portable Zip. They are responsible for whatever works in Zip. Whatever doesn't work is solely the fault of the authors of Zip (Mark Adler, Rich Wales, Jean-loup Gailly, Kai Uwe Rommel, Igor Mandrichenko, Onno van der Linden, Christian Spieler, John Bush, Paul Kienitz, Sergio Monesi and Karl Davis, but see the license for the latest list). If you have contributed and your name has been forgotten, please send a reminder to us using the contact information in the Readme file. The names are given here in alphabetical order, because it's impossible to classify them by importance of the contribution. Some have made a complete port to a new target, some have provided a one line fix. All are to be thanked. Mark Adler madler@tybalt.caltech.edu NeXT 2.x, Mac alan@spri.levels.unisa.edu.au Linux Jeffrey Altman jaltman@watsun.cc.columbia.edu fseek bug on NT Glenn J. Andrews oper1%drcv06.decnet@drcvax.af.mil VAX VMS James Van Artsdalen james@raid.dell.com bug report Eric Backus ericb@lsid.hp.com bug report Quentin Barnes qbarnes@urbana.css.mot.com unix/Makefile mode of installed files Elmar Bartel bartel@informatik.tu-muenchen.de Mark E. Becker mbecker@cs.uml.edu bug report Paul von Behren Paul_von_Behren@stortek.com OS/390 port Jon Bell swy@wsdot.wa.gov Intergraph/CLIX Myles Bennett - Initial UnZip 6.0 large files beta Michael Bernardi mike@childsoc.demon.co.uk RS6000 Tom Betz marob!upaya!tbetz@phri.nyu.edu SCO Xenix 2.3.1 James Birdsall jwbirdsa@picarefy.com AT&T 3B1 George boer@fwi.uva.nl OS/2 Michael Bolton bolton@vaxc.erim.org VAX/VMS Wim Bonner 27313853@WSUVM1.CSC.WSU.EDU HP 9000/840a HPUX Paul Borman prb@cray.com Cray-X/YMP,2 UNICOS 6-8 Kurt Van den Branden kvd2@bipsy.se.bel.alcatel.be VAX VMS Scott Briggs briggs@nashua.progress.com Windows NT Leslie C. Brown lbrown@BRL.MIL Pyramid MIS-4 Ralf Brown ralf@b.gp.cs.cmu.edu Pyramid MIS-4 Rodney Brown rdb@cmutual.com.au SunOS 4.1.3 DGUX OSF/1 HP-UX CRC optimization Jeremy Daniel Buhler jbuhler@owlnet.rice.edu BC++ John Bush john.bush@east.sun.com Amiga (SAS/C) Pietro Caselli zaphod@petruz.sublink.org Minix 1.5.10 Andrew A. Chernov ache@astral.msk.su FreeBSD Jeff Coffler jeffcof@microsoft.com Windows NT David Dachtera David.Dachtera@advocatehealth.com VMS link_zip.com bug Bill Davidsen davidsen@crdos1.crd.ge.com Xenix (on what?) Karl Davis riscman@geko.com.au Acorn Daniel Deimert daniel@pkmab.se zeus3.21 Zilog S8000 David Denholm denholm@sotona.physics.southampton.ac.uk VMS Harald Denker harry@hal.westfalen.de ATARI Matthew J. D'Errico doc@magna.com Bull L. Peter Deutsch ghost@aladdin.com Linux Uwe Doering gemini@geminix.in-berlin.de 386 Unix Jean-Michel Dubois jmdubois@ibcfrance.fr Theos support James P. Dugal jpd@usl.edu Pyramid 90X OSx4.1 "Evil Ed" esaffle@gmuvax2.gmu.edu Ultrix-32 V3.1 (Rev. 9) Patrick Ellis pellis@aic.mdc.com VMS zip -h appearance Thomas Esken esken@uni-muenster.de Acorn fix Dwight Estep estep@dlo10.enet.dec.com MSDOS David A. Feinleib t-davefe@microsoft.com Windows NT Joshua Felsteiner joshua@phys1.technion.ac.il Linux Greg Flint afc@klaatu.cc.purdue.edu ETA-10P* hybrid Sys V Carl Forde cforde@bcsc02.gov.bc.ca VM/CMS Jeff Foy jfoy@glia.biostr.washington.edu IRIX Sys V Rel 3.3.1 Mike Freeman mikef@pacifier.com Vax VMS Kevin M. Fritz kmfritz@apgea.army.mil Turbo C++ 1.0 Pyramid Jean-loup Gailly jloup@chorus.fr MS-DOS Microsoft C 5.1 Scott D. Galloway sgallowa@letterkenn-emh1.army.mil Sperry 5000 SysV.3 Rainer Gerling gerling@faupt101.physik.uni-erlangen.de HPUX, MSDOS Henry Gessau henryg@kullmar.kullmar.se Windows NT Ed Gordon - Zip 3.0, VB, Unicode, large files, splits, DLLs Ian E. Gorman ian@iosphere.net ported zip 2.2 to VM/CMS Wayne R. Graves graves@csa2.lbl.gov Vax VMS George Grimes grimes@netcom.com Apollo Domain SR10.4 Hunter Goatley goathunter@MadGoat.com VMS (VAX & Alpha), web and ftp sites Arnt Gulbrandsen agulbra@pvv.unit.no Linux David Gundlach david@rolf.stat.uga.edu Sun SS1+ SunOS 4.1 Peter Gutmann pgut1@cs.aukuni.ac.nz bug report Dirk Haase d_haase@sitec.de MacOS port Mark Hanning-Lee markhl@iris-355.jpl.nasa.gov SGI Walter Haidinger e9225662@student.tuwien.ac.at Amiga and general fixes Charles Hannum mycroft@ai.mit.edu bug report Greg Hartwig ghartwig@ix.netcom.com VM/CMS cleanup Tanvir Hassan tanvir.hassan@autodesk.com NT Bob Hardy hardy@lucid.com Power C on MSDOS Zachary Heilig heilig@plains.nodak.edu Turbo C++ 3.0 Chris Herborth chrish@pobox.com BeOS port Jonathan Hudson jrhudson@bigfoot.com QDOS port Mark William Jacobs mark@mensch.stanford.edu MSDOS Aubrey Jaffer jaffer@martigny.ai.mit.edu Pixel Peter Jones jones.peter@uqam.ca MIPS UMIPS 4.0 +Onolimit fix for HP-UX Kjetil W. J{\o}rgensen jorgens@lise.unit.no OSF/1, DJGPP v2 Bruce Kahn bkahn@archive.webo.dg.com MS-DOS Microsoft C 5.1 Jonathan I. Kamens jik@pit-manager.mit.edu ultrix on DECstation Dave Kapalko d.kapalko@att.com bug report Bob Kemp Robert.V.Kemp@att.com AT&T 3B2 SysV 3.2v2 Vivek Khera khera@cs.duke.edu SunOS Earl Kiech KIECH@utkvx.utk.edu VAX VMS V5.4-1A Paul Kienitz Paul.Kienitz@shelter.sf.ca.us Amiga, Watcom C David Kirschbaum kirsch@usasoc.soc.mil He got us all in this mess in the first place Thomas Klausner wiz@danbala.tuwien.ac.at cygwin32 and -k fix D. Krumbholz krumbh00@marvin.informatik.uni-dortmund.de Acorn filetype and timestamp bug report Bo Kullmar bk@kullmar.se DNIX 5.3, SunOS 4.1 Baden Kudrenecky baden@unixg.ubc.ca OS/2 Giuseppe La Sala lasala@mail.esa.esrin.it VMS Jean-Marc Lasgouttes jean-marc.lasgouttes@inria.fr Bug report Harry Langenbacher harry@neuron6.Jpl.Nasa.Gov Sun SS1+ SunOS 4.1 Michael D. Lawler mdlawler@gwmicro.com Mt.Xinu BSD 4.3 on VAX Borland C++ 4.51 Johnny Lee johnnyl@microsoft.com Microsoft C 7.0 Michael Lemke michael@io.as.utexas.edu VMS David Lemson lemson@ux1.cso.uiuc.edu Sequent Dynix 3.0.17 Tai-Shan Lin tlin@snakeyes.eecs.wsu.edu OS/2 Onno van der Linden onno@simplex.nl NetBSD, Borland C++, MSC 7.0, DJGPP 2 Michel loehden%mv13.decnet@vax.hrz.uni-marburg.de VMS Warner Losh imp@Solbourne.COM packing algorithm help Dave Lovelace davel@grex.cyberspace.org DG AOS/VS Erik Luijten erik@tntnhb3.tn.tudelft.nl problem report John Lundin lundin@urvax.urich.edu VAX VMS Igor Mandrichenko mandrichenko@m10.ihep.su VAX VMS Cliff Manis root@csoftec.csf.com SCO 2.3.1 (386) Fulvio Marino fulvio@iconet.ico.olivetti.it X/OS 2.3 & 2.4 Bill Marsh bmarsh@cod.nosc.mil SGI Iris 4D35 Michael Mauch mauch@gmx.de djgpp LFN attribute fix Peter Mauzey ptm@mtdcr.mt.lucent.com AT&T 6300, 7300 Rafal Z. Maszkowski rzm@mat.torun.edu.pl Convex Robert McBroom (?) rm3@ornl.gov DECsystem 5810 Tom McConnell tmcconne@sedona.intel.com NCR SVR4 Frank P. McIngvale frankm@eng.auburn.edu Bug report Conor McMenamin C.S.McMenamin@sussex.ac.uk MSDOS Will Menninger Win32, MinGW John Messenger jlm@proteon.com Bug report Michael kuch@mailserv.zdv.uni-tuebingen.de SGI Dan Mick dmick@pongo.west.sun.com Solaris Alan Modra alan@spri.levels.unisa.edu.au Linux Laszlo Molnar lmolnar@goliat.eik.bme.hu DJGPP v2 Jim Mollmann jmq@nccibm1.bitnet OS/2 & MVS Sergio Monesi pel0015@cdc8g5.cdc.polimi.it Acorn J. Mukherjee jmukherj@ringer.cs.utsa.edu OS/2 Anthony Naggs amn@ubik.demon.co.uk bug report Matti Narkia matti.narkia@ntc.nokia.com VAX VMS Rainer Nausedat Zip 3.0, large files Robert E. Newman Jr. newmanr@ssl.msfc.nasa.gov bug report Robert Nielsen NielsenRJ@ems.com 2.2 -V VMS bug report Christian Michel cmichel@de.ibm.com 2.2 check_dup OS/2 bug report Thomas S. Opheys opheys@kirk.fmi.uni-passau.de OS/2 Humberto Ortiz-Zuazaga zuazaga@ucunix.san.uc.edu Linux James E. O'Dell jim@fpr.com MacOS William O'Shaughnessy williamo@hpcupt1.cup.hp.com HPUX Neil Parks neil.parks@pcohio.com MSDOS Enrico Renato Palmerini palmer@vxscaq.cineca.it UNISYS 7000 Sys 5 r2.3 Geoff Pennington Geoff.Pennington@sgcs.co.uk -q output bug Keith Petersen w8sdz@simtel20.army.mil Pyramid UCB OSx4.4c George Petrov VM/CMS, MVS Alan Phillips postmaster@lancaster.ac.uk Dynix/ptx 1.3 Bruno Pillard bp@chorus.fr SunOS 4.1 Piet W. Plomp piet@icce.rug.nl MSC 7.0, SCO 3.2v4.0 John Poltorak j.poltorak@bradford.ac.uk problem report Kenneth Porter 72420.2436@compuserve.com OS/2 Norbert Pueschel pueschel@imsdd.meb.uni-bonn.de Amiga time.lib Yuval Rakavy yuval@cs.huji.ac.il MSDOS David A Rasmussen dave@convex.csd.uwm.edu Convex C220 with 9.0 OS Eric Raymond esr@snark.thyrsus.com Unix Jim Read 74312.3103@compuserve.com OS/2 Michael Regoli mr@cica.indiana.edu Ultrix 3.1 VAX 8650 BSD 4.3 IBM RT/125 BSD 4.3 MicroVAX 3500 SunOS 4.0.3 Sun 4/330 Jochen Roderburg roderburg@rrz.uni-koeln.de Digital Unix with AFS/NFS converter Rick Rodgers rodgers@maxwell.mmwb.ucsf.EDU Unix man page Greg Roelofs roe2@midway.uchicago.edu SunOS 4.1.1,4.1.2 Sun 4 Unicos 5.1--6.1.5 Cray OS/2 1.3 MS C 6.0 Ultrix 4.1,4.2 DEC 5810 VMS 5.2, 5.4 VAX 8600 Irix 3.3.2, SGI Iris 4D UTS 1.2.4 Amdahl 5880 Phil Ritzenthaler phil@cgrg.ohio-state.edu SYSV Kai Uwe Rommel rommel@ars.de or rommel@leo.org OS/2 Markus Ruppel m.ruppel@imperial.ac.uk OS/2 Shimazaki Ryo eririn@ma.mailbank.ne.jp human68k Jon Saxton jrs@panix.com Microsoft C 6.0 Steve Salisbury stevesa@msn.com Microsoft C 8.0 Timo Salmi ts@uwasa.fi bug report Darren Salt ds@youmustbejoking.demon.co.uk RISC OS NIIMI Satoshi a01309@cfi.waseda.ac.jp Human68K Tom Schmidt tschmidt@micron.com SCO 286 Martin Schulz martin.schulz@isltd.insignia.com Windows NT, Atari Steven Schweda VMS, Unix, large files Dan Seyb dseyb@halnet.com AIX Mark Shadley shadcat@catcher.com unix fixes Timur Shaporev tim@rd.relcom.msk.su MSDOS W. T. Sidney sidney@picard.med.ge.com bug report Dave Sisson daves@vtcosy.cns.vt.edu AIX 1.1.1 PS/2 & 3090 Dave Smith smithdt@bp.com Tandem port Fred Smith fredex@fcshome.stoneham.ma.us Coherent Christian Spieler spieler@ikp.tu-darmstadt.de VMS, MSDOS, emx, djgpp, WIN32, Linux Ron Srodawa srodawa@vela.acs.oakland.edu SCO Xenix/386 2.3.3 Adam Stanley astanley@winternet.com MSDOS Bertil Stenstr|m stenis@heron.dafa.se HP-UX 7.0 HP9000/835 Carl Streeter streeter@oshkoshw.bitnet OS/2 Reuben Sumner rasumner@undergrad.math.uwaterloo.ca Suggestions E-Yen Tan e-yen.tan@brasenose.oxford.ac.uk Borland C++ win32 Yoshioka Tsuneo tsuneo-y@is.aist-nara.ac.jp Multibyte charset support Paul Telles paul@pubnet.com SCO Xenix Julian Thompson jrt@oasis.icl.co.uk bug report Christopher C. Tjon tjon@plains.nodak.edu bug report Robert F Tobler rft@cs.stanford.edu bug report Eric Tomio tomio@acri.fr bug report Cosmin Truta cosmint@cs.ubbcluj.ro win32 gcc based + asm Anthony R. Venson cevens@unix1.sncc.lsu.edu MSDOS/emx Antoine Verheijen antoine@sysmail.ucs.ualberta.ca envargs fix Arjan de Vet devet@info.win.tue.nl SunOS 4.1, MSC 5.1 Santiago Vila Doncel sanvila@ba.unex.es MSDOS Johan Vromans jv@mh.nl bug report Rich Wales wales@cs.ucla.edu SunOS 4.0.3 Sun-3/50 Scott Walton scottw@io.com BSD/386 Frank J. Wancho wancho@wsmr-simtel20.army.mil TOPS-20 oyvind@stavanger.sgp.slb.com Bug report. Takahiro Watanabe wata@first.tsukuba.ac.jp fixes for INSTALL Mike White mwhite@pumatech.com wizzip DLL Ray Wickert wickert@dc-srv.pa-x.dec.com MSDOS/DJGPP Winfried Winkler willi@wap0109.chem.tu-berlin.de AIX Norman J. Wong as219@freenet.carleton.ca MSDOS Martin Zinser m.zinser@gsi.de VMS 7.x zip30/proginfo/ntsd.txt0100644000076400000060000001346706265625076013346 0ustar ediskInfo-ZIP portable Zip/UnZip Windows NT security descriptor support ================================================================== Scott Field (sfield@microsoft.com), 8 October 1996 This version of Info-ZIP's Win32 code allows for processing of Windows NT security descriptors if they were saved in the .zip file using the appropriate Win32 Zip running under Windows NT. This also requires that the file system that Zip/UnZip operates on supports persistent Acl storage. When the operating system is not Windows NT and the target file system does not support persistent Acl storage, no security descriptor processing takes place. A Windows NT security descriptor consists of any combination of the following components: an owner (Sid) a primary group (Sid) a discretionary ACL (Dacl) a system ACL (Sacl) qualifiers for the preceding items By default, Zip will save all aspects of the security descriptor except for the Sacl. The Sacl contains information pertaining to auditing of the file, and requires a security privilege be granted to the calling user in addition to being enabled by the calling application. In order to save the Sacl during Zip, the user must specify the -! switch on the Zip commandline. The user must also be granted either the SeBackupPrivilege "Backup files and directories" or the SeSystemSecurityPrivilege "Manage auditing and security log". By default, UnZip will not restore any aspects of the security descriptor. If the -X option is specified to UnZip, the Dacl is restored to the file. The other items in the security descriptor on the new file will receive default values. If the -XX option is specified to UnZip, as many aspects of the security descriptor as possible will be restored. If the calling user is granted the SeRestorePrivilege "Restore files and directories", all aspects of the security descriptor will be restored. If the calling user is only granted the SeSystemSecurityPrivilege "Manage auditing and security log", only the Dacl and Sacl will be restored to the new file. Note that when operating on files that reside on remote volumes, the privileges specified above must be granted to the calling user on that remote machine. Currently, there is no way to directly test what privileges are present on a remote machine, so Zip and UnZip make a remote privilege determination based on an indirect method. UnZip considerations -------------------- In order for file security to be processed correctly, any directory entries that have a security descriptor will be processed at the end of the unzip cycle. This allows for unzip to process files within the newly created directory regardless of the security descriptor associated with the directory entry. This also prevents security inheritance problems that can occur as a result of creating a new directory and then creating files in that directory that will inherit parent directory permissions; such inherited permissions may prevent the security descriptor taken from the zip file from being applied to the new file. If directories exist which match directory/extract paths in the .zip file, file security is not updated on the target directory. It is assumed that if the target directory already exists, then appropriate security has already been applied to that directory. "unzip -t" will test the integrity of stored security descriptors when present and the operating system is Windows NT. ZipInfo (unzip -Z) will display information on stored security descriptor when "unzip -Zv" is specifed. Potential uses ============== The obvious use for this new support is to better support backup and restore operations in a Windows NT environment where NTFS file security is utilized. This allows individuals and organizations to archive files in a portable fashion and transport these files across the organization. Another potential use of this support is setup and installation. This allows for distribution of Windows NT based applications that have preset security on files and directories. For example, prior to creation of the .zip file, the user can set file security via File Manager or Explorer on the files to be contained in the .zip file. In many cases, it is appropriate to only grant Everyone Read access to .exe and .dll files, while granting Administrators Full control. Using this support in conjunction with the unzipsfx.exe self-extractor stub can yield a useful and powerful way to install software with preset security (note that -X or -XX should be specified on the self-extractor commandline). When creating .zip files with security which are intended for transport across systems, it is important to take into account the relevance of access control entries and the associated Sid of each entry. For example, if a .zip file is created on a Windows NT workstation, and file security references local workstation user accounts (like an account named Fred), this access entry will not be relevant if the .zip file is transported to another machine. Where possible, take advantage of the built-in well-known groups, like Administrators, Everyone, Network, Guests, etc. These groups have the same meaning on any Windows NT machine. Note that the names of these groups may differ depending on the language of the installed Windows NT, but this isn't a problem since each name has well-known ID that, upon restore, translates to the correct group name regardless of locale. When access control entries contain Sid entries that reference Domain accounts, these entries will only be relevant on systems that recognize the referenced domain. Generally speaking, the only side effects of irrelevant access control entries is wasted space in the stored security descriptor and loss of complete intended access control. Such irrelevant access control entries will show up as "Account Unknown" when viewing file security with File Manager or Explorer. zip30/proginfo/perform.dos0100644000076400000060000001731406420576742014007 0ustar ediskDate: Wed, 27 Mar 1996 01:31:50 CET +0100 From: Christian Spieler (IKDA, THD, D-64289 Darmstadt) Subject: More detailed comparison of MSDOS Info-ZIP programs' performance Hello all, In response to some additional questions and requests concerning my previous message about DOS performance of 16/32-bit Info-ZIP programs, I have produced a more detailed comparison: System: Cx486DX-40, VL-bus, 8MB; IDE hard disk; DOS 6.2, HIMEM, EMM386 NOEMS NOVCPI, SMARTDRV 3MB, write back. I have used the main directory of UnZip 5.20p as source, including the objects and executable of an EMX compile for unzip.exe (to supply some binary test files). Tested programs were (my current updated sources!) Zip 2.0w and UnZip 5.20p - 16-bit MSC 5.1, compressed with LZEXE 0.91e - 32-bit Watcom C 10.5, as supplied by Kai Uwe Rommel (PMODE 1.22) - 32-bit EMX 0.9b - 32-bit DJGPP v2 - 32-bit DJGPP v1.12m4 The EMX and DJ1 (GO32) executables were bound with the full extender, to create standalone executables. A) Tests of Zip Command : "\zip.exe -q<#> tes.zip unz/*" (unz/*.* for Watcom!!) where <#> was: 0, 1, 6, 9. The test archive "tes.zip" was never deleted, this test measured "time to update archive". The following table contains average execution seconds (averaged over at least 3 runs, with the first run discarted to fill disk cache); numbers in parenteses specify the standard deviation of the last digits. cmpr level| 0 | 1 | 6 | 9 =============================================================== EMX win95 | 7.77 | 7.97 | 12.82 | 22.31 --------------------------------------------------------------- EMX | 7.15(40) | 8.00(6) | 12.52(25) | 20.93 DJ2 | 13.50(32) | 14.20(7) | 19.05 | 28.48(9) DJ1 | 13.56(30) | 14.48(3) | 18.70 | 27.43(13) WAT | 6.94(22) | 8.93 | 15.73(34) | 30.25(6) MSC | 5.99(82) | 9.40(4) | 13.59(9) | 20.77(4) =============================================================== The "EMX win95" line was created for comparison, to check the performance of emx 0.9 with the RSX extender in a DPMI environment. (This line was produced by applying the "stubbed" EMX executable in a full screen DOS box.) B) Tests of UnZip Commands : \unzip.exe -qt tes.zip (testing performance) \unzip.exe -qo tes.zip -dtm (extracting performance) The tes.zip archive created by maximum compression with the Zip test was used as example archive. Contents (archive size was 347783 bytes): 1028492 bytes uncompressed, 337235 bytes compressed, 67%, 85 files The extraction directory tm was not deleted between the individual runs, thus this measurement checks the "overwrite all" time. | testing | extracting =================================================================== EMX | 1.98 | 6.43(8) DJ2 | 2.09 | 11.85(39) DJ1 | 2.09 | 7.46(9) WAT | 2.42 | 7.10(27) MSC | 4.94 | 9.57(31) Remarks: The executables compiled by me were generated with all "performance" options enabled (ASM_CRC, and ASMV for Zip), and with full crypt support. For DJ1 and DJ2, the GCC options were "-O2 -m486", for EMX "-O -m486". The Watcom UnZip was compiled with ASM_CRC code enabled as well, but the Watcom Zip example was made without any optional assembler code! Discussion of the results: In overall performance, the EMX executables clearly win. For UnZip, emx is by far the fastest program, and the Zip performance is comparable to the 16-bit "reference". Whenever "real" work including I/O is requested, the DJGPP versions lose badly because of poor I/O performance, this is the case especially for the "newer" DJGPP v2 !!! (I tried to tweak with the transfer buffer size, but without any success.) An interesting result is that DJ v1 UnZip works remarkably better than DJ v2 (in contrast to Zip, where both executables' performance is approximately equal). The Watcom C programs show a clear performance deficit in the "computational part" (Watcom C compiler produces code that is far from optimal), but the extender (which is mostly responsible for the I/O throughput) seems to be quite fast. The "natural" performance deficit of the 16-bit MSC code, which can be clearly seen in the "testing task" comparison for UnZip, is (mostly, for Zip more than) compensated by the better I/O throughput (due to the "direct interface" between "C RTL" and "DOS services", without any mode switching). But performance is only one aspect when choosing which compiler should be used for official distribution: Sizes of the executables: | Zip || UnZip | standalone stub || standalone | stub ====================================================================== EMX | 143,364 (1) | 94,212 || 159,748 (1) | 110,596 DJ2 | 118,272 (2) | -- || 124,928 (2) | -- DJ1 | 159,744 | 88,064 || 177,152 | 105,472 WAT | 140,073 | -- || 116,231 | -- MSC | 49,212 (3) | -- || 45,510 (3) | -- (1) does not run in "DPMI only" environment (Windows DOS box) (2) requires externally supplied DPMI server (3) compressed with LZexe 0.91 Caveats/Bugs/Problems of the different extenders: EMX: - requires two different extenders to run in all DOS-compatible environments, EMX for "raw/himem/vcpi" and RSX for "dpmi" (Windows). - does not properly support time zones (no daylight savings time) DJv2: - requires an external (freely available) DPMI extender when run on plain DOS; this extender cannot (currently ??) be bound into the executable. DJv1: - uses up large amount of "low" dos memory (below 1M) when spawning another program, each instance of a DJv1 program requires its private GO32 extender copy in low dos memory (may be problem for the zip "-T" feature) Watcom/PMODE: - extended memory is allocated statically (default: ALL available memory) This means that a spawned program does not get any extended memory. You can work around this problem by setting a hard limit on the amount of extended memory available to the PMODE program, but this limit is "hard" and restricts the allocatable memory for the program itself. In detail: The Watcom zip.exe as distributed did not allow the "zip -T" feature; there was no extended memory left to spawn unzip. I could work around this problem by applying PMSETUP to change the amount of allocated extended memory to 2.0 MByte (I had 4MB free extended memory on my test system). But, this limit cannot be enlarged at runtime, when zip needs more memory to store "header info" while zipping up a huge drive, and on a system with less free memory, this method is not applicable, either. Summary: For Zip: Use the 16-bit executable whenever possible (unless you need the larger memory capabilities when zipping up a huge amount of files) As 32-bit executable, we may distribute Watcom C (after we have confirmed that enabling ASMV and ASM_CRC give us some better computational performance.) The alternative for 32-bit remains DJGPP v1, which shows the least problems (to my knowledge); v2 and EMX cannot be used because of their lack of "universality". For UnZip: Here, the Watcom C 32-bit executable is probably the best compromise, but DJ v1 could be used as well. And, after all, the 16-bit version does not lose badly when doing "real" extraction! For the SFX stub, the 16-bit version remains first choice because of its much smaller size! Best regards Christian Spieler zip30/proginfo/timezone.txt0100644000076400000060000001044106461322062014200 0ustar ediskTimezone strings: ----------------- This is a description of valid timezone strings for ENV[ARC]:TZ: "XPG3TZ - time zone information" The form of the time zone information is based on the XPG3 specification of the TZ environment variable. Spaces are allowed only in timezone designations, where they are significant. The following description closely follows the XPG3 specification, except for the paragraphs starting **CLARIFICATION**. [[],[/