Subversion Repositories Kolibri OS

Rev

Go to most recent revision | Blame | Compare with Previous | Last modification | View Log | Download | RSS feed

  1. /*
  2.   Copyright (c) 1990-2009 Info-ZIP.  All rights reserved.
  3.  
  4.   See the accompanying file LICENSE, version 2009-Jan-02 or later
  5.   (the contents of which are also included in unzip.h) for terms of use.
  6.   If, for some reason, all these files are missing, the Info-ZIP license
  7.   also may be found at:  ftp://ftp.info-zip.org/pub/infozip/license.html
  8. */
  9. /*---------------------------------------------------------------------------
  10.  
  11.   unzip.c
  12.  
  13.   UnZip - a zipfile extraction utility.  See below for make instructions, or
  14.   read the comments in Makefile and the various Contents files for more de-
  15.   tailed explanations.  To report a bug, submit a *complete* description via
  16.   //www.info-zip.org/zip-bug.html; include machine type, operating system and
  17.   version, compiler and version, and reasonably detailed error messages or
  18.   problem report.  To join Info-ZIP, see the instructions in README.
  19.  
  20.   UnZip 5.x is a greatly expanded and partially rewritten successor to 4.x,
  21.   which in turn was almost a complete rewrite of version 3.x.  For a detailed
  22.   revision history, see UnzpHist.zip at quest.jpl.nasa.gov.  For a list of
  23.   the many (near infinite) contributors, see "CONTRIBS" in the UnZip source
  24.   distribution.
  25.  
  26.   UnZip 6.0 adds support for archives larger than 4 GiB using the Zip64
  27.   extensions as well as support for Unicode information embedded per the
  28.   latest zip standard additions.
  29.  
  30.   ---------------------------------------------------------------------------
  31.  
  32.   [from original zipinfo.c]
  33.  
  34.   This program reads great gobs of totally nifty information, including the
  35.   central directory stuff, from ZIP archives ("zipfiles" for short).  It
  36.   started as just a testbed for fooling with zipfiles, but at this point it
  37.   is actually a useful utility.  It also became the basis for the rewrite of
  38.   UnZip (3.16 -> 4.0), using the central directory for processing rather than
  39.   the individual (local) file headers.
  40.  
  41.   As of ZipInfo v2.0 and UnZip v5.1, the two programs are combined into one.
  42.   If the executable is named "unzip" (or "unzip.exe", depending), it behaves
  43.   like UnZip by default; if it is named "zipinfo" or "ii", it behaves like
  44.   ZipInfo.  The ZipInfo behavior may also be triggered by use of unzip's -Z
  45.   option; for example, "unzip -Z [zipinfo_options] archive.zip".
  46.  
  47.   Another dandy product from your buddies at Newtware!
  48.  
  49.   Author:  Greg Roelofs, newt@pobox.com, http://pobox.com/~newt/
  50.            23 August 1990 -> April 1997
  51.  
  52.   ---------------------------------------------------------------------------
  53.  
  54.   Version:  unzip5??.{tar.Z | tar.gz | zip} for Unix, VMS, OS/2, MS-DOS, Amiga,
  55.               Atari, Windows 3.x/95/NT/CE, Macintosh, Human68K, Acorn RISC OS,
  56.               AtheOS, BeOS, SMS/QDOS, VM/CMS, MVS, AOS/VS, Tandem NSK, Theos
  57.               and TOPS-20.
  58.  
  59.   Copyrights:  see accompanying file "LICENSE" in UnZip source distribution.
  60.                (This software is free but NOT IN THE PUBLIC DOMAIN.)
  61.  
  62.   ---------------------------------------------------------------------------*/
  63.  
  64.  
  65.  
  66. #define __UNZIP_C       /* identifies this source module */
  67. #define UNZIP_INTERNAL
  68. #include "unzip.h"      /* includes, typedefs, macros, prototypes, etc. */
  69. #include "crypt.h"
  70. #include "unzvers.h"
  71.  
  72. #ifndef WINDLL          /* The WINDLL port uses windll/windll.c instead... */
  73.  
  74. /***************************/
  75. /* Local type declarations */
  76. /***************************/
  77.  
  78. #if (defined(REENTRANT) && !defined(NO_EXCEPT_SIGNALS))
  79. typedef struct _sign_info
  80.     {
  81.         struct _sign_info *previous;
  82.         void (*sighandler)(int);
  83.         int sigtype;
  84.     } savsigs_info;
  85. #endif
  86.  
  87. /*******************/
  88. /* Local Functions */
  89. /*******************/
  90.  
  91. #if (defined(REENTRANT) && !defined(NO_EXCEPT_SIGNALS))
  92. static int setsignalhandler OF((__GPRO__ savsigs_info **p_savedhandler_chain,
  93.                                 int signal_type, void (*newhandler)(int)));
  94. #endif
  95. #ifndef SFX
  96. static void  help_extended      OF((__GPRO));
  97. static void  show_version_info  OF((__GPRO));
  98. #endif
  99.  
  100.  
  101. /*************/
  102. /* Constants */
  103. /*************/
  104.  
  105. #include "consts.h"  /* all constant global variables are in here */
  106.                      /* (non-constant globals were moved to globals.c) */
  107.  
  108. /* constant local variables: */
  109.  
  110. #ifndef SFX
  111. #ifndef _WIN32_WCE /* Win CE does not support environment variables */
  112.    static ZCONST char Far EnvUnZip[] = ENV_UNZIP;
  113.    static ZCONST char Far EnvUnZip2[] = ENV_UNZIP2;
  114.    static ZCONST char Far EnvZipInfo[] = ENV_ZIPINFO;
  115.    static ZCONST char Far EnvZipInfo2[] = ENV_ZIPINFO2;
  116. #ifdef RISCOS
  117.    static ZCONST char Far EnvUnZipExts[] = ENV_UNZIPEXTS;
  118. #endif /* RISCOS */
  119.   static ZCONST char Far NoMemEnvArguments[] =
  120.     "envargs:  cannot get memory for arguments";
  121. #endif /* !_WIN32_WCE */
  122.   static ZCONST char Far CmdLineParamTooLong[] =
  123.     "error:  command line parameter #%d exceeds internal size limit\n";
  124. #endif /* !SFX */
  125.  
  126. #if (defined(REENTRANT) && !defined(NO_EXCEPT_SIGNALS))
  127.   static ZCONST char Far CantSaveSigHandler[] =
  128.     "error:  cannot save signal handler settings\n";
  129. #endif
  130.  
  131. #if (!defined(SFX) || defined(SFX_EXDIR))
  132.    static ZCONST char Far NotExtracting[] =
  133.      "caution:  not extracting; -d ignored\n";
  134.    static ZCONST char Far MustGiveExdir[] =
  135.      "error:  must specify directory to which to extract with -d option\n";
  136.    static ZCONST char Far OnlyOneExdir[] =
  137.      "error:  -d option used more than once (only one exdir allowed)\n";
  138. #endif
  139. #if (defined(UNICODE_SUPPORT) && !defined(UNICODE_WCHAR))
  140.   static ZCONST char Far UTF8EscapeUnSupp[] =
  141.     "warning:  -U \"escape all non-ASCII UTF-8 chars\" is not supported\n";
  142. #endif
  143.  
  144. #if CRYPT
  145.    static ZCONST char Far MustGivePasswd[] =
  146.      "error:  must give decryption password with -P option\n";
  147. #endif
  148.  
  149. #ifndef SFX
  150.    static ZCONST char Far Zfirst[] =
  151.    "error:  -Z must be first option for ZipInfo mode (check UNZIP variable?)\n";
  152. #endif
  153. static ZCONST char Far InvalidOptionsMsg[] = "error:\
  154.  -fn or any combination of -c, -l, -p, -t, -u and -v options invalid\n";
  155. static ZCONST char Far IgnoreOOptionMsg[] =
  156.   "caution:  both -n and -o specified; ignoring -o\n";
  157.  
  158. /* usage() strings */
  159. #ifndef SFX
  160. #ifdef VMS
  161.    static ZCONST char Far Example3[] = "vms.c";
  162.    static ZCONST char Far Example2[] = "  unzip \"-V\" foo \"Bar\"\
  163. (Quote names to preserve case, unless SET PROC/PARS=EXT)\n";
  164. #else /* !VMS */
  165.    static ZCONST char Far Example3[] = "ReadMe";
  166. #ifdef RISCOS
  167.    static ZCONST char Far Example2[] =
  168. "  unzip foo -d RAM:$   => extract all files from foo into RAMDisc\n";
  169. #else /* !RISCOS */
  170. #if (defined(OS2) || (defined(DOS_FLX_OS2_W32) && defined(MORE)))
  171.    static ZCONST char Far Example2[] =
  172.      "";                /* no room:  too many local3[] items */
  173. #else /* !OS2 */
  174. #ifdef MACOS
  175.    static ZCONST char Far Example2[] = ""; /* not needed */
  176. #else /* !MACOS */
  177.    static ZCONST char Far Example2[] = " \
  178. unzip -p foo | more  => send contents of foo.zip via pipe into program more\n";
  179. #endif /* ?MACOS */
  180. #endif /* ?OS2 */
  181. #endif /* ?RISCOS */
  182. #endif /* ?VMS */
  183.  
  184. /* local1[]:  command options */
  185. #if defined(TIMESTAMP)
  186.    static ZCONST char Far local1[] =
  187.      "  -T  timestamp archive to latest";
  188. #else /* !TIMESTAMP */
  189.    static ZCONST char Far local1[] = "";
  190. #endif /* ?TIMESTAMP */
  191.  
  192. /* local2[] and local3[]:  modifier options */
  193. #ifdef DOS_FLX_H68_OS2_W32
  194. #ifdef FLEXOS
  195.    static ZCONST char Far local2[] = "";
  196. #else
  197.    static ZCONST char Far local2[] =
  198.      " -$  label removables (-$$ => fixed disks)";
  199. #endif
  200. #ifdef OS2
  201. #ifdef MORE
  202.    static ZCONST char Far local3[] = "\
  203.  -X  restore ACLs if supported              -s  spaces in filenames => '_'\n\
  204.                                             -M  pipe through \"more\" pager\n";
  205. #else
  206.    static ZCONST char Far local3[] = " \
  207. -X  restore ACLs if supported              -s  spaces in filenames => '_'\n\n";
  208. #endif /* ?MORE */
  209. #else /* !OS2 */
  210. #ifdef WIN32
  211. #ifdef NTSD_EAS
  212. #ifdef MORE
  213.    static ZCONST char Far local3[] = "\
  214.  -X  restore ACLs (-XX => use privileges)   -s  spaces in filenames => '_'\n\
  215.                                             -M  pipe through \"more\" pager\n";
  216. #else
  217.    static ZCONST char Far local3[] = " \
  218. -X  restore ACLs (-XX => use privileges)   -s  spaces in filenames => '_'\n\n";
  219. #endif /* ?MORE */
  220. #else /* !NTSD_EAS */
  221. #ifdef MORE
  222.    static ZCONST char Far local3[] = "\
  223.  -M  pipe through \"more\" pager            \
  224.  -s  spaces in filenames => '_'\n\n";
  225. #else
  226.    static ZCONST char Far local3[] = " \
  227.                                            -s  spaces in filenames => '_'\n\n";
  228. #endif /* ?MORE */
  229. #endif /* ?NTSD_EAS */
  230. #else /* !WIN32 */
  231. #ifdef MORE
  232.    static ZCONST char Far local3[] = "  -\
  233. M  pipe through \"more\" pager              -s  spaces in filenames => '_'\n\n";
  234. #else
  235.    static ZCONST char Far local3[] = "\
  236.                                             -s  spaces in filenames => '_'\n";
  237. #endif
  238. #endif /* ?WIN32 */
  239. #endif /* ?OS2 || ?WIN32 */
  240. #else /* !DOS_FLX_OS2_W32 */
  241. #ifdef VMS
  242.    static ZCONST char Far local2[] = " -X  restore owner/ACL protection info";
  243. #ifdef MORE
  244.    static ZCONST char Far local3[] = "\
  245.  -Y  treat \".nnn\" as \";nnn\" version         -2  force ODS2 names\n\
  246.  --D restore dir (-D: no) timestamps        -M  pipe through \"more\" pager\n\
  247.  (Must quote upper-case options, like \"-V\", unless SET PROC/PARSE=EXTEND.)\
  248. \n\n";
  249. #else
  250.    static ZCONST char Far local3[] = "\n\
  251.  -Y  treat \".nnn\" as \";nnn\" version         -2  force ODS2 names\n\
  252.  --D restore dir (-D: no) timestamps\n\
  253.  (Must quote upper-case options, like \"-V\", unless SET PROC/PARSE=EXTEND.)\
  254. \n\n";
  255. #endif
  256. #else /* !VMS */
  257. #ifdef ATH_BEO_UNX
  258.    static ZCONST char Far local2[] = " -X  restore UID/GID info";
  259. #ifdef MORE
  260.    static ZCONST char Far local3[] = "\
  261.  -K  keep setuid/setgid/tacky permissions   -M  pipe through \"more\" pager\n";
  262. #else
  263.    static ZCONST char Far local3[] = "\
  264.  -K  keep setuid/setgid/tacky permissions\n";
  265. #endif
  266. #else /* !ATH_BEO_UNX */
  267. #ifdef TANDEM
  268.    static ZCONST char Far local2[] = "\
  269. -X  restore Tandem User ID                 -r  remove file extensions\n\
  270.  -b  create 'C' (180) text files          ";
  271. #ifdef MORE
  272.    static ZCONST char Far local3[] = " \
  273.                                            -M  pipe through \"more\" pager\n";
  274. #else
  275.    static ZCONST char Far local3[] = "\n";
  276. #endif
  277. #else /* !TANDEM */
  278. #ifdef AMIGA
  279.    static ZCONST char Far local2[] = " -N  restore comments as filenotes";
  280. #ifdef MORE
  281.    static ZCONST char Far local3[] = " \
  282.                                            -M  pipe through \"more\" pager\n";
  283. #else
  284.    static ZCONST char Far local3[] = "\n";
  285. #endif
  286. #else /* !AMIGA */
  287. #ifdef MACOS
  288.    static ZCONST char Far local2[] = " -E  show Mac info during extraction";
  289.    static ZCONST char Far local3[] = " \
  290. -i  ignore filenames in mac extra info     -J  junk (ignore) Mac extra info\n\
  291. \n";
  292. #else /* !MACOS */
  293. #ifdef MORE
  294.    static ZCONST char Far local2[] = " -M  pipe through \"more\" pager";
  295.    static ZCONST char Far local3[] = "\n";
  296. #else
  297.    static ZCONST char Far local2[] = "";   /* Atari, Mac, CMS/MVS etc. */
  298.    static ZCONST char Far local3[] = "";
  299. #endif
  300. #endif /* ?MACOS */
  301. #endif /* ?AMIGA */
  302. #endif /* ?TANDEM */
  303. #endif /* ?ATH_BEO_UNX */
  304. #endif /* ?VMS */
  305. #endif /* ?DOS_FLX_OS2_W32 */
  306. #endif /* !SFX */
  307.  
  308. #ifndef NO_ZIPINFO
  309. #ifdef VMS
  310.    static ZCONST char Far ZipInfoExample[] = "* or % (e.g., \"*font-%.zip\")";
  311. #else
  312.    static ZCONST char Far ZipInfoExample[] = "*, ?, [] (e.g., \"[a-j]*.zip\")";
  313. #endif
  314.  
  315. static ZCONST char Far ZipInfoUsageLine1[] = "\
  316. ZipInfo %d.%d%d%s of %s, by Greg Roelofs and the Info-ZIP group.\n\
  317. \n\
  318. List name, date/time, attribute, size, compression method, etc., about files\n\
  319. in list (excluding those in xlist) contained in the specified .zip archive(s).\
  320. \n\"file[.zip]\" may be a wildcard name containing %s.\n\n\
  321.   usage:  zipinfo [-12smlvChMtTz] file[.zip] [list...] [-x xlist...]\n\
  322.      or:  unzip %s-Z%s [-12smlvChMtTz] file[.zip] [list...] [-x xlist...]\n";
  323.  
  324. static ZCONST char Far ZipInfoUsageLine2[] = "\nmain\
  325. listing-format options:             -s  short Unix \"ls -l\" format (def.)\n\
  326.  -1  filenames ONLY, one per line       -m  medium Unix \"ls -l\" format\n\
  327.  -2  just filenames but allow -h/-t/-z  -l  long Unix \"ls -l\" format\n\
  328.                                         -v  verbose, multi-page format\n";
  329.  
  330. static ZCONST char Far ZipInfoUsageLine3[] = "miscellaneous options:\n\
  331.  -h  print header line       -t  print totals for listed files or for all\n\
  332.  -z  print zipfile comment   -T  print file times in sortable decimal format\
  333. \n  -C  be case-insensitive   %s\
  334.  -x  exclude filenames that follow from listing\n";
  335. #ifdef MORE
  336.    static ZCONST char Far ZipInfoUsageLine4[] =
  337.      "  -M  page output through built-in \"more\"\n";
  338. #else /* !MORE */
  339.    static ZCONST char Far ZipInfoUsageLine4[] = "";
  340. #endif /* ?MORE */
  341. #endif /* !NO_ZIPINFO */
  342.  
  343. #ifdef BETA
  344. #  ifdef VMSCLI
  345.    /* BetaVersion[] is also used in vms/cmdline.c:  do not make it static */
  346.      ZCONST char Far BetaVersion[] = "%s\
  347.        THIS IS STILL A BETA VERSION OF UNZIP%s -- DO NOT DISTRIBUTE.\n\n";
  348. #  else
  349.      static ZCONST char Far BetaVersion[] = "%s\
  350.        THIS IS STILL A BETA VERSION OF UNZIP%s -- DO NOT DISTRIBUTE.\n\n";
  351. #  endif
  352. #endif
  353.  
  354. #ifdef SFX
  355. #  ifdef VMSCLI
  356.    /* UnzipSFXBanner[] is also used in vms/cmdline.c:  do not make it static */
  357.      ZCONST char Far UnzipSFXBanner[] =
  358. #  else
  359.      static ZCONST char Far UnzipSFXBanner[] =
  360. #  endif
  361.      "UnZipSFX %d.%d%d%s of %s, by Info-ZIP (http://www.info-zip.org).\n";
  362. #  ifdef SFX_EXDIR
  363.      static ZCONST char Far UnzipSFXOpts[] =
  364.     "Valid options are -tfupcz and -d <exdir>; modifiers are -abjnoqCL%sV%s.\n";
  365. #  else
  366.      static ZCONST char Far UnzipSFXOpts[] =
  367.        "Valid options are -tfupcz; modifiers are -abjnoqCL%sV%s.\n";
  368. #  endif
  369. #else /* !SFX */
  370.    static ZCONST char Far CompileOptions[] =
  371.      "UnZip special compilation options:\n";
  372.    static ZCONST char Far CompileOptFormat[] = "        %s\n";
  373. #ifndef _WIN32_WCE /* Win CE does not support environment variables */
  374.    static ZCONST char Far EnvOptions[] =
  375.      "\nUnZip and ZipInfo environment options:\n";
  376.    static ZCONST char Far EnvOptFormat[] = "%16s:  %.1024s\n";
  377. #endif
  378.    static ZCONST char Far None[] = "[none]";
  379. #  ifdef ACORN_FTYPE_NFS
  380.      static ZCONST char Far AcornFtypeNFS[] = "ACORN_FTYPE_NFS";
  381. #  endif
  382. #  ifdef ASM_CRC
  383.      static ZCONST char Far AsmCRC[] = "ASM_CRC";
  384. #  endif
  385. #  ifdef ASM_INFLATECODES
  386.      static ZCONST char Far AsmInflateCodes[] = "ASM_INFLATECODES";
  387. #  endif
  388. #  ifdef CHECK_VERSIONS
  389.      static ZCONST char Far Check_Versions[] = "CHECK_VERSIONS";
  390. #  endif
  391. #  ifdef COPYRIGHT_CLEAN
  392.      static ZCONST char Far Copyright_Clean[] =
  393.      "COPYRIGHT_CLEAN (PKZIP 0.9x unreducing method not supported)";
  394. #  endif
  395. #  ifdef DEBUG
  396.      static ZCONST char Far UDebug[] = "DEBUG";
  397. #  endif
  398. #  ifdef DEBUG_TIME
  399.      static ZCONST char Far DebugTime[] = "DEBUG_TIME";
  400. #  endif
  401. #  ifdef DLL
  402.      static ZCONST char Far Dll[] = "DLL";
  403. #  endif
  404. #  ifdef DOSWILD
  405.      static ZCONST char Far DosWild[] = "DOSWILD";
  406. #  endif
  407. #  ifdef LZW_CLEAN
  408.      static ZCONST char Far LZW_Clean[] =
  409.      "LZW_CLEAN (PKZIP/Zip 1.x unshrinking method not supported)";
  410. #  endif
  411. #  ifndef MORE
  412.      static ZCONST char Far No_More[] = "NO_MORE";
  413. #  endif
  414. #  ifdef NO_ZIPINFO
  415.      static ZCONST char Far No_ZipInfo[] = "NO_ZIPINFO";
  416. #  endif
  417. #  ifdef NTSD_EAS
  418.      static ZCONST char Far NTSDExtAttrib[] = "NTSD_EAS";
  419. #  endif
  420. #  if defined(WIN32) && defined(NO_W32TIMES_IZFIX)
  421.      static ZCONST char Far W32NoIZTimeFix[] = "NO_W32TIMES_IZFIX";
  422. #  endif
  423. #  ifdef OLD_THEOS_EXTRA
  424.      static ZCONST char Far OldTheosExtra[] =
  425.      "OLD_THEOS_EXTRA (handle also old Theos port extra field)";
  426. #  endif
  427. #  ifdef OS2_EAS
  428.      static ZCONST char Far OS2ExtAttrib[] = "OS2_EAS";
  429. #  endif
  430. #  ifdef QLZIP
  431.      static ZCONST char Far SMSExFldOnUnix[] = "QLZIP";
  432. #  endif
  433. #  ifdef REENTRANT
  434.      static ZCONST char Far Reentrant[] = "REENTRANT";
  435. #  endif
  436. #  ifdef REGARGS
  437.      static ZCONST char Far RegArgs[] = "REGARGS";
  438. #  endif
  439. #  ifdef RETURN_CODES
  440.      static ZCONST char Far Return_Codes[] = "RETURN_CODES";
  441. #  endif
  442. #  ifdef SET_DIR_ATTRIB
  443.      static ZCONST char Far SetDirAttrib[] = "SET_DIR_ATTRIB";
  444. #  endif
  445. #  ifdef SYMLINKS
  446.      static ZCONST char Far SymLinkSupport[] =
  447.      "SYMLINKS (symbolic links supported, if RTL and file system permit)";
  448. #  endif
  449. #  ifdef TIMESTAMP
  450.      static ZCONST char Far TimeStamp[] = "TIMESTAMP";
  451. #  endif
  452. #  ifdef UNIXBACKUP
  453.      static ZCONST char Far UnixBackup[] = "UNIXBACKUP";
  454. #  endif
  455. #  ifdef USE_EF_UT_TIME
  456.      static ZCONST char Far Use_EF_UT_time[] = "USE_EF_UT_TIME";
  457. #  endif
  458. #  ifndef LZW_CLEAN
  459.      static ZCONST char Far Use_Unshrink[] =
  460.      "USE_UNSHRINK (PKZIP/Zip 1.x unshrinking method supported)";
  461. #  endif
  462. #  ifndef COPYRIGHT_CLEAN
  463.      static ZCONST char Far Use_Smith_Code[] =
  464.      "USE_SMITH_CODE (PKZIP 0.9x unreducing method supported)";
  465. #  endif
  466. #  ifdef USE_DEFLATE64
  467.      static ZCONST char Far Use_Deflate64[] =
  468.      "USE_DEFLATE64 (PKZIP 4.x Deflate64(tm) supported)";
  469. #  endif
  470. #  ifdef UNICODE_SUPPORT
  471. #   ifdef UTF8_MAYBE_NATIVE
  472. #    ifdef UNICODE_WCHAR
  473.        /* direct native UTF-8 check AND charset transform via wchar_t */
  474.        static ZCONST char Far Use_Unicode[] =
  475.        "UNICODE_SUPPORT [wide-chars, char coding: %s] (handle UTF-8 paths)";
  476. #    else
  477.        /* direct native UTF-8 check, only */
  478.        static ZCONST char Far Use_Unicode[] =
  479.        "UNICODE_SUPPORT [char coding: %s] (handle UTF-8 paths)";
  480. #    endif
  481.        static ZCONST char Far SysChUTF8[] = "UTF-8";
  482.        static ZCONST char Far SysChOther[] = "other";
  483. #   else /* !UTF8_MAYBE_NATIVE */
  484.        /* charset transform via wchar_t, no native UTF-8 support */
  485.        static ZCONST char Far Use_Unicode[] =
  486.        "UNICODE_SUPPORT [wide-chars] (handle UTF-8 paths)";
  487. #   endif /* ?UTF8_MAYBE_NATIVE */
  488. #  endif /* UNICODE_SUPPORT */
  489. #  ifdef _MBCS
  490.      static ZCONST char Far Have_MBCS_Support[] =
  491.      "MBCS-support (multibyte character support, MB_CUR_MAX = %u)";
  492. #  endif
  493. #  ifdef MULT_VOLUME
  494.      static ZCONST char Far Use_MultiVol[] =
  495.      "MULT_VOLUME (multi-volume archives supported)";
  496. #  endif
  497. #  ifdef LARGE_FILE_SUPPORT
  498.      static ZCONST char Far Use_LFS[] =
  499.      "LARGE_FILE_SUPPORT (large files over 2 GiB supported)";
  500. #  endif
  501. #  ifdef ZIP64_SUPPORT
  502.      static ZCONST char Far Use_Zip64[] =
  503.      "ZIP64_SUPPORT (archives using Zip64 for large files supported)";
  504. #  endif
  505. #  if (defined(__DJGPP__) && (__DJGPP__ >= 2))
  506. #    ifdef USE_DJGPP_ENV
  507.        static ZCONST char Far Use_DJGPP_Env[] = "USE_DJGPP_ENV";
  508. #    endif
  509. #    ifdef USE_DJGPP_GLOB
  510.        static ZCONST char Far Use_DJGPP_Glob[] = "USE_DJGPP_GLOB";
  511. #    endif
  512. #  endif /* __DJGPP__ && (__DJGPP__ >= 2) */
  513. #  ifdef USE_VFAT
  514.      static ZCONST char Far Use_VFAT_support[] = "USE_VFAT";
  515. #  endif
  516. #  ifdef USE_ZLIB
  517.      static ZCONST char Far UseZlib[] =
  518.      "USE_ZLIB (compiled with version %s; using version %s)";
  519. #  endif
  520. #  ifdef USE_BZIP2
  521.      static ZCONST char Far UseBZip2[] =
  522.      "USE_BZIP2 (PKZIP 4.6+, using bzip2 lib version %s)";
  523. #  endif
  524. #  ifdef VMS_TEXT_CONV
  525.      static ZCONST char Far VmsTextConv[] = "VMS_TEXT_CONV";
  526. #  endif
  527. #  ifdef VMSCLI
  528.      static ZCONST char Far VmsCLI[] = "VMSCLI";
  529. #  endif
  530. #  ifdef VMSWILD
  531.      static ZCONST char Far VmsWild[] = "VMSWILD";
  532. #  endif
  533. #  ifdef WILD_STOP_AT_DIR
  534.      static ZCONST char Far WildStopAtDir[] = "WILD_STOP_AT_DIR";
  535. #  endif
  536. #  if CRYPT
  537. #    ifdef PASSWD_FROM_STDIN
  538.        static ZCONST char Far PasswdStdin[] = "PASSWD_FROM_STDIN";
  539. #    endif
  540.      static ZCONST char Far Decryption[] =
  541.        "        [decryption, version %d.%d%s of %s]\n";
  542.      static ZCONST char Far CryptDate[] = CR_VERSION_DATE;
  543. #  endif
  544. #  ifndef __RSXNT__
  545. #    ifdef __EMX__
  546.        static ZCONST char Far EnvEMX[] = "EMX";
  547.        static ZCONST char Far EnvEMXOPT[] = "EMXOPT";
  548. #    endif
  549. #    if (defined(__GO32__) && (!defined(__DJGPP__) || (__DJGPP__ < 2)))
  550.        static ZCONST char Far EnvGO32[] = "GO32";
  551.        static ZCONST char Far EnvGO32TMP[] = "GO32TMP";
  552. #    endif
  553. #  endif /* !__RSXNT__ */
  554.  
  555. #ifdef VMS
  556. /* UnzipUsageLine1[] is also used in vms/cmdline.c:  do not make it static */
  557.    ZCONST char Far UnzipUsageLine1[] = "\
  558. UnZip %d.%d%d%s of %s, by Info-ZIP.  For more details see: unzip -v.\n\n";
  559. # ifdef COPYRIGHT_CLEAN
  560.    static ZCONST char Far UnzipUsageLine1v[] = "\
  561. UnZip %d.%d%d%s of %s, by Info-ZIP.  Maintained by C. Spieler.  Send\n\
  562. bug reports using http://www.info-zip.org/zip-bug.html; see README for details.\
  563. \n\n";
  564. # else
  565.    static ZCONST char Far UnzipUsageLine1v[] = "\
  566. UnZip %d.%d%d%s of %s, by Info-ZIP.  UnReduce (c) 1989 by S. H. Smith.\n\
  567. Send bug reports using //www.info-zip.org/zip-bug.html; see README for details.\
  568. \n\n";
  569. # endif /* ?COPYRIGHT_CLEAN */
  570. #else /* !VMS */
  571. # ifdef COPYRIGHT_CLEAN
  572.    static ZCONST char Far UnzipUsageLine1[] = "\
  573. UnZip %d.%d%d%s of %s, by Info-ZIP.  Maintained by C. Spieler.  Send\n\
  574. bug reports using http://www.info-zip.org/zip-bug.html; see README for details.\
  575. \n\n";
  576. # else
  577.    static ZCONST char Far UnzipUsageLine1[] = "\
  578. UnZip %d.%d%d%s of %s, by Info-ZIP.  UnReduce (c) 1989 by S. H. Smith.\n\
  579. Send bug reports using //www.info-zip.org/zip-bug.html; see README for details.\
  580. \n\n";
  581. # endif /* ?COPYRIGHT_CLEAN */
  582. # define UnzipUsageLine1v       UnzipUsageLine1
  583. #endif /* ?VMS */
  584.  
  585. static ZCONST char Far UnzipUsageLine2v[] = "\
  586. Latest sources and executables are at ftp://ftp.info-zip.org/pub/infozip/ ;\
  587. \nsee ftp://ftp.info-zip.org/pub/infozip/UnZip.html for other sites.\
  588. \n\n";
  589.  
  590. #ifdef MACOS
  591. static ZCONST char Far UnzipUsageLine2[] = "\
  592. Usage: unzip %s[-opts[modifiers]] file[.zip] [list] [-d exdir]\n \
  593. Default action is to extract files in list, to exdir;\n\
  594.  file[.zip] may be a wildcard.  %s\n";
  595. #else /* !MACOS */
  596. #ifdef VM_CMS
  597. static ZCONST char Far UnzipUsageLine2[] = "\
  598. Usage: unzip %s[-opts[modifiers]] file[.zip] [list] [-x xlist] [-d fm]\n \
  599. Default action is to extract files in list, except those in xlist, to disk fm;\
  600. \n  file[.zip] may be a wildcard.  %s\n";
  601. #else /* !VM_CMS */
  602. static ZCONST char Far UnzipUsageLine2[] = "\
  603. Usage: unzip %s[-opts[modifiers]] file[.zip] [list] [-x xlist] [-d exdir]\n \
  604. Default action is to extract files in list, except those in xlist, to exdir;\n\
  605.  file[.zip] may be a wildcard.  %s\n";
  606. #endif /* ?VM_CMS */
  607. #endif /* ?MACOS */
  608.  
  609. #ifdef NO_ZIPINFO
  610. #  define ZIPINFO_MODE_OPTION  ""
  611.    static ZCONST char Far ZipInfoMode[] =
  612.      "(ZipInfo mode is disabled in this version.)";
  613. #else
  614. #  define ZIPINFO_MODE_OPTION  "[-Z] "
  615.    static ZCONST char Far ZipInfoMode[] =
  616.      "-Z => ZipInfo mode (\"unzip -Z\" for usage).";
  617. #endif /* ?NO_ZIPINFO */
  618.  
  619. #ifdef VMS
  620.    static ZCONST char Far VMSusageLine2b[] = "\
  621. => define foreign command symbol in LOGIN.COM:  $ unzip :== $dev:[dir]unzip.exe\
  622. \n";
  623. #endif
  624.  
  625. #ifdef MACOS
  626. static ZCONST char Far UnzipUsageLine3[] = "\n\
  627.  -d  extract files into exdir               -l  list files (short format)\n\
  628.  -f  freshen existing files, create none    -t  test compressed archive data\n\
  629.  -u  update files, create if necessary      -z  display archive comment only\n\
  630.  -v  list verbosely/show version info     %s\n";
  631. #else /* !MACOS */
  632. #ifdef VM_CMS
  633. static ZCONST char Far UnzipUsageLine3[] = "\n\
  634.  -p  extract files to pipe, no messages     -l  list files (short format)\n\
  635.  -f  freshen existing files, create none    -t  test compressed archive data\n\
  636.  -u  update files, create if necessary      -z  display archive comment only\n\
  637.  -v  list verbosely/show version info     %s\n\
  638.  -x  exclude files that follow (in xlist)   -d  extract files onto disk fm\n";
  639. #else /* !VM_CMS */
  640. static ZCONST char Far UnzipUsageLine3[] = "\n\
  641.  -p  extract files to pipe, no messages     -l  list files (short format)\n\
  642.  -f  freshen existing files, create none    -t  test compressed archive data\n\
  643.  -u  update files, create if necessary      -z  display archive comment only\n\
  644.  -v  list verbosely/show version info     %s\n\
  645.  -x  exclude files that follow (in xlist)   -d  extract files into exdir\n";
  646. #endif /* ?VM_CMS */
  647. #endif /* ?MACOS */
  648.  
  649. /* There is not enough space on a standard 80x25 Windows console screen for
  650.  * the additional line advertising the UTF-8 debugging options. This may
  651.  * eventually also be the case for other ports. Probably, the -U option need
  652.  * not be shown on the introductory screen at all. [Chr. Spieler, 2008-02-09]
  653.  *
  654.  * Likely, other advanced options should be moved to an extended help page and
  655.  * the option to list that page put here.  [E. Gordon, 2008-3-16]
  656.  */
  657. #if (defined(UNICODE_SUPPORT) && !defined(WIN32))
  658. #ifdef VMS
  659. static ZCONST char Far UnzipUsageLine4[] = "\
  660. modifiers:\n\
  661.  -n  never overwrite or make a new version of an existing file\n\
  662.  -o  always make a new version (-oo: overwrite original) of an existing file\n\
  663.  -q  quiet mode (-qq => quieter)            -a  auto-convert any text files\n\
  664.  -j  junk paths (do not make directories)   -aa treat ALL files as text\n\
  665.  -U  use escapes for all non-ASCII Unicode  -UU ignore any Unicode fields\n\
  666.  -C  match filenames case-insensitively     -L  make (some) names \
  667. lowercase\n %-42s  -V  retain VMS version numbers\n%s";
  668. #else /* !VMS */
  669. static ZCONST char Far UnzipUsageLine4[] = "\
  670. modifiers:\n\
  671.  -n  never overwrite existing files         -q  quiet mode (-qq => quieter)\n\
  672.  -o  overwrite files WITHOUT prompting      -a  auto-convert any text files\n\
  673.  -j  junk paths (do not make directories)   -aa treat ALL files as text\n\
  674.  -U  use escapes for all non-ASCII Unicode  -UU ignore any Unicode fields\n\
  675.  -C  match filenames case-insensitively     -L  make (some) names \
  676. lowercase\n %-42s  -V  retain VMS version numbers\n%s";
  677. #endif /* ?VMS */
  678. #else /* !UNICODE_SUPPORT */
  679. #ifdef VMS
  680. static ZCONST char Far UnzipUsageLine4[] = "\
  681. modifiers:\n\
  682.  -n  never overwrite or make a new version of an existing file\n\
  683.  -o  always make a new version (-oo: overwrite original) of an existing file\n\
  684.  -q  quiet mode (-qq => quieter)            -a  auto-convert any text files\n\
  685.  -j  junk paths (do not make directories)   -aa treat ALL files as text\n\
  686.  -C  match filenames case-insensitively     -L  make (some) names \
  687. lowercase\n %-42s  -V  retain VMS version numbers\n%s";
  688. #else /* !VMS */
  689. static ZCONST char Far UnzipUsageLine4[] = "\
  690. modifiers:\n\
  691.  -n  never overwrite existing files         -q  quiet mode (-qq => quieter)\n\
  692.  -o  overwrite files WITHOUT prompting      -a  auto-convert any text files\n\
  693.  -j  junk paths (do not make directories)   -aa treat ALL files as text\n\
  694.  -C  match filenames case-insensitively     -L  make (some) names \
  695. lowercase\n %-42s  -V  retain VMS version numbers\n%s";
  696. #endif /* ?VMS */
  697. #endif /* ?UNICODE_SUPPORT */
  698.  
  699. static ZCONST char Far UnzipUsageLine5[] = "\
  700. See \"unzip -hh\" or unzip.txt for more help.  Examples:\n\
  701.  unzip data1 -x joe   => extract all files except joe from zipfile data1.zip\n\
  702. %s\
  703.  unzip -fo foo %-6s => quietly replace existing %s if archive file newer\n";
  704. #endif /* ?SFX */
  705.  
  706.  
  707.  
  708.  
  709.  
  710. /*****************************/
  711. /*  main() / UzpMain() stub  */
  712. /*****************************/
  713.  
  714. int MAIN(argc, argv)   /* return PK-type error code (except under VMS) */
  715.     int argc;
  716.     char *argv[];
  717. {
  718.     int r;
  719.  
  720.     CONSTRUCTGLOBALS();
  721.     r = unzip(__G__ argc, argv);
  722.     DESTROYGLOBALS();
  723.     RETURN(r);
  724. }
  725.  
  726.  
  727.  
  728.  
  729. /*******************************/
  730. /*  Primary UnZip entry point  */
  731. /*******************************/
  732.  
  733. int unzip(__G__ argc, argv)
  734.     __GDEF
  735.     int argc;
  736.     char *argv[];
  737. {
  738. #ifndef NO_ZIPINFO
  739.     char *p;
  740. #endif
  741. #if (defined(DOS_FLX_H68_NLM_OS2_W32) || !defined(SFX))
  742.     int i;
  743. #endif
  744.     int retcode, error=FALSE;
  745. #ifndef NO_EXCEPT_SIGNALS
  746. #ifdef REENTRANT
  747.     savsigs_info *oldsighandlers = NULL;
  748. #   define SET_SIGHANDLER(sigtype, newsighandler) \
  749.       if ((retcode = setsignalhandler(__G__ &oldsighandlers, (sigtype), \
  750.                                       (newsighandler))) > PK_WARN) \
  751.           goto cleanup_and_exit
  752. #else
  753. #   define SET_SIGHANDLER(sigtype, newsighandler) \
  754.       signal((sigtype), (newsighandler))
  755. #endif
  756. #endif /* NO_EXCEPT_SIGNALS */
  757.  
  758.     /* initialize international char support to the current environment */
  759.     SETLOCALE(LC_CTYPE, "");
  760.  
  761. #ifdef UNICODE_SUPPORT
  762.     /* see if can use UTF-8 Unicode locale */
  763. # ifdef UTF8_MAYBE_NATIVE
  764.     {
  765.         char *codeset;
  766. #  if !(defined(NO_NL_LANGINFO) || defined(NO_LANGINFO_H))
  767.         /* get the codeset (character set encoding) currently used */
  768. #       include <langinfo.h>
  769.  
  770.         codeset = nl_langinfo(CODESET);
  771. #  else /* NO_NL_LANGINFO || NO_LANGINFO_H */
  772.         /* query the current locale setting for character classification */
  773.         codeset = setlocale(LC_CTYPE, NULL);
  774.         if (codeset != NULL) {
  775.             /* extract the codeset portion of the locale name */
  776.             codeset = strchr(codeset, '.');
  777.             if (codeset != NULL) ++codeset;
  778.         }
  779. #  endif /* ?(NO_NL_LANGINFO || NO_LANGINFO_H) */
  780.         /* is the current codeset UTF-8 ? */
  781.         if ((codeset != NULL) && (strcmp(codeset, "UTF-8") == 0)) {
  782.             /* successfully found UTF-8 char coding */
  783.             G.native_is_utf8 = TRUE;
  784.         } else {
  785.             /* Current codeset is not UTF-8 or cannot be determined. */
  786.             G.native_is_utf8 = FALSE;
  787.         }
  788.         /* Note: At least for UnZip, trying to change the process codeset to
  789.          *       UTF-8 does not work.  For the example Linux setup of the
  790.          *       UnZip maintainer, a successful switch to "en-US.UTF-8"
  791.          *       resulted in garbage display of all non-basic ASCII characters.
  792.          */
  793.     }
  794. # endif /* UTF8_MAYBE_NATIVE */
  795.  
  796.     /* initialize Unicode */
  797.     G.unicode_escape_all = 0;
  798.     G.unicode_mismatch = 0;
  799.  
  800.     G.unipath_version = 0;
  801.     G.unipath_checksum = 0;
  802.     G.unipath_filename = NULL;
  803. #endif /* UNICODE_SUPPORT */
  804.  
  805.  
  806. #if (defined(__IBMC__) && defined(__DEBUG_ALLOC__))
  807.     extern void DebugMalloc(void);
  808.  
  809.     atexit(DebugMalloc);
  810. #endif
  811.  
  812. #ifdef MALLOC_WORK
  813.     /* The following (rather complex) expression determines the allocation
  814.        size of the decompression work area.  It simulates what the
  815.        combined "union" and "struct" declaration of the "static" work
  816.        area reservation achieves automatically at compile time.
  817.        Any decent compiler should evaluate this expression completely at
  818.        compile time and provide constants to the zcalloc() call.
  819.        (For better readability, some subexpressions are encapsulated
  820.        in temporarly defined macros.)
  821.      */
  822. #   define UZ_SLIDE_CHUNK (sizeof(shrint)+sizeof(uch)+sizeof(uch))
  823. #   define UZ_NUMOF_CHUNKS \
  824.       (unsigned)(((WSIZE+UZ_SLIDE_CHUNK-1)/UZ_SLIDE_CHUNK > HSIZE) ? \
  825.                  (WSIZE+UZ_SLIDE_CHUNK-1)/UZ_SLIDE_CHUNK : HSIZE)
  826.     G.area.Slide = (uch *)zcalloc(UZ_NUMOF_CHUNKS, UZ_SLIDE_CHUNK);
  827. #   undef UZ_SLIDE_CHUNK
  828. #   undef UZ_NUMOF_CHUNKS
  829.     G.area.shrink.Parent = (shrint *)G.area.Slide;
  830.     G.area.shrink.value = G.area.Slide + (sizeof(shrint)*(HSIZE));
  831.     G.area.shrink.Stack = G.area.Slide +
  832.                            (sizeof(shrint) + sizeof(uch))*(HSIZE);
  833. #endif
  834.  
  835. /*---------------------------------------------------------------------------
  836.     Set signal handler for restoring echo, warn of zipfile corruption, etc.
  837.   ---------------------------------------------------------------------------*/
  838. #ifndef NO_EXCEPT_SIGNALS
  839. #ifdef SIGINT
  840.     SET_SIGHANDLER(SIGINT, handler);
  841. #endif
  842. #ifdef SIGTERM                 /* some systems really have no SIGTERM */
  843.     SET_SIGHANDLER(SIGTERM, handler);
  844. #endif
  845. #if defined(SIGABRT) && !(defined(AMIGA) && defined(__SASC))
  846.     SET_SIGHANDLER(SIGABRT, handler);
  847. #endif
  848. #ifdef SIGBREAK
  849.     SET_SIGHANDLER(SIGBREAK, handler);
  850. #endif
  851. #ifdef SIGBUS
  852.     SET_SIGHANDLER(SIGBUS, handler);
  853. #endif
  854. #ifdef SIGILL
  855.     SET_SIGHANDLER(SIGILL, handler);
  856. #endif
  857. #ifdef SIGSEGV
  858.     SET_SIGHANDLER(SIGSEGV, handler);
  859. #endif
  860. #endif /* NO_EXCEPT_SIGNALS */
  861.  
  862. #if (defined(WIN32) && defined(__RSXNT__))
  863.     for (i = 0 ; i < argc; i++) {
  864.         _ISO_INTERN(argv[i]);
  865.     }
  866. #endif
  867.  
  868. /*---------------------------------------------------------------------------
  869.     Macintosh initialization code.
  870.   ---------------------------------------------------------------------------*/
  871.  
  872. #ifdef MACOS
  873.     {
  874.         int a;
  875.  
  876.         for (a = 0;  a < 4;  ++a)
  877.             G.rghCursor[a] = GetCursor(a+128);
  878.         G.giCursor = 0;
  879.     }
  880. #endif
  881.  
  882. /*---------------------------------------------------------------------------
  883.     NetWare initialization code.
  884.   ---------------------------------------------------------------------------*/
  885.  
  886. #ifdef NLM
  887.     InitUnZipConsole();
  888. #endif
  889.  
  890. /*---------------------------------------------------------------------------
  891.     Acorn RISC OS initialization code.
  892.   ---------------------------------------------------------------------------*/
  893.  
  894. #ifdef RISCOS
  895.     set_prefix();
  896. #endif
  897.  
  898. /*---------------------------------------------------------------------------
  899.     Theos initialization code.
  900.   ---------------------------------------------------------------------------*/
  901.  
  902. #ifdef THEOS
  903.     /* The easiest way found to force creation of libraries when selected
  904.      * members are to be unzipped. Explicitly add libraries names to the
  905.      * arguments list before the first member of the library.
  906.      */
  907.     if (! _setargv(&argc, &argv)) {
  908.         Info(slide, 0x401, ((char *)slide, "cannot process argv\n"));
  909.         retcode = PK_MEM;
  910.         goto cleanup_and_exit;
  911.     }
  912. #endif
  913.  
  914. /*---------------------------------------------------------------------------
  915.     Sanity checks.  Commentary by Otis B. Driftwood and Fiorello:
  916.  
  917.     D:  It's all right.  That's in every contract.  That's what they
  918.         call a sanity clause.
  919.  
  920.     F:  Ha-ha-ha-ha-ha.  You can't fool me.  There ain't no Sanity
  921.         Claus.
  922.   ---------------------------------------------------------------------------*/
  923.  
  924. #ifdef DEBUG
  925. # ifdef LARGE_FILE_SUPPORT
  926.   /* test if we can support large files - 10/6/04 EG */
  927.     if (sizeof(zoff_t) < 8) {
  928.         Info(slide, 0x401, ((char *)slide, "LARGE_FILE_SUPPORT set but not supported\n"));
  929.         retcode = PK_BADERR;
  930.         goto cleanup_and_exit;
  931.     }
  932.     /* test if we can show 64-bit values */
  933.     {
  934.         zoff_t z = ~(zoff_t)0;  /* z should be all 1s now */
  935.         char *sz;
  936.  
  937.         sz = FmZofft(z, FZOFFT_HEX_DOT_WID, "X");
  938.         if ((sz[0] != 'F') || (strlen(sz) != 16))
  939.         {
  940.             z = 0;
  941.         }
  942.  
  943.         /* shift z so only MSB is set */
  944.         z <<= 63;
  945.         sz = FmZofft(z, FZOFFT_HEX_DOT_WID, "X");
  946.         if ((sz[0] != '8') || (strlen(sz) != 16))
  947.         {
  948.             Info(slide, 0x401, ((char *)slide,
  949.               "Can't show 64-bit values correctly\n"));
  950.             retcode = PK_BADERR;
  951.             goto cleanup_and_exit;
  952.         }
  953.     }
  954. # endif /* LARGE_FILE_SUPPORT */
  955.  
  956.     /* 2004-11-30 SMS.
  957.        Test the NEXTBYTE macro for proper operation.
  958.     */
  959.     {
  960.         int test_char;
  961.         static uch test_buf[2] = { 'a', 'b' };
  962.  
  963.         G.inptr = test_buf;
  964.         G.incnt = 1;
  965.  
  966.         test_char = NEXTBYTE;           /* Should get 'a'. */
  967.         if (test_char == 'a')
  968.         {
  969.             test_char = NEXTBYTE;       /* Should get EOF, not 'b'. */
  970.         }
  971.         if (test_char != EOF)
  972.         {
  973.             Info(slide, 0x401, ((char *)slide,
  974.  "NEXTBYTE macro failed.  Try compiling with ALT_NEXTBYTE defined?"));
  975.  
  976.             retcode = PK_BADERR;
  977.             goto cleanup_and_exit;
  978.         }
  979.     }
  980. #endif /* DEBUG */
  981.  
  982. /*---------------------------------------------------------------------------
  983.     First figure out if we're running in UnZip mode or ZipInfo mode, and put
  984.     the appropriate environment-variable options into the queue.  Then rip
  985.     through any command-line options lurking about...
  986.   ---------------------------------------------------------------------------*/
  987.  
  988. #ifdef SFX
  989.     G.argv0 = argv[0];
  990. #if (defined(OS2) || defined(WIN32))
  991.     G.zipfn = GetLoadPath(__G);/* non-MSC NT puts path into G.filename[] */
  992. #else
  993.     G.zipfn = G.argv0;
  994. #endif
  995.  
  996. #ifdef VMSCLI
  997.     {
  998.         ulg status = vms_unzip_cmdline(&argc, &argv);
  999.         if (!(status & 1)) {
  1000.             retcode = (int)status;
  1001.             goto cleanup_and_exit;
  1002.         }
  1003.     }
  1004. #endif /* VMSCLI */
  1005.  
  1006.     uO.zipinfo_mode = FALSE;
  1007.     error = uz_opts(__G__ &argc, &argv);   /* UnZipSFX call only */
  1008.  
  1009. #else /* !SFX */
  1010.  
  1011. #ifdef RISCOS
  1012.     /* get the extensions to swap from environment */
  1013.     getRISCOSexts(ENV_UNZIPEXTS);
  1014. #endif
  1015.  
  1016. #ifdef MSDOS
  1017.     /* extract MKS extended argument list from environment (before envargs!) */
  1018.     mksargs(&argc, &argv);
  1019. #endif
  1020.  
  1021. #ifdef VMSCLI
  1022.     {
  1023.         ulg status = vms_unzip_cmdline(&argc, &argv);
  1024.         if (!(status & 1)) {
  1025.             retcode = (int)status;
  1026.             goto cleanup_and_exit;
  1027.         }
  1028.     }
  1029. #endif /* VMSCLI */
  1030.  
  1031.     G.noargs = (argc == 1);   /* no options, no zipfile, no anything */
  1032.  
  1033. #ifndef NO_ZIPINFO
  1034.     for (p = argv[0] + strlen(argv[0]); p >= argv[0]; --p) {
  1035.         if (*p == DIR_END
  1036. #ifdef DIR_END2
  1037.             || *p == DIR_END2
  1038. #endif
  1039.            )
  1040.             break;
  1041.     }
  1042.     ++p;
  1043.  
  1044. #ifdef THEOS
  1045.     if (strncmp(p, "ZIPINFO.",8) == 0 || strstr(p, ".ZIPINFO:") != NULL ||
  1046.         strncmp(p, "II.",3) == 0 || strstr(p, ".II:") != NULL ||
  1047. #else
  1048.     if (STRNICMP(p, LoadFarStringSmall(Zipnfo), 7) == 0 ||
  1049.         STRNICMP(p, "ii", 2) == 0 ||
  1050. #endif
  1051.         (argc > 1 && strncmp(argv[1], "-Z", 2) == 0))
  1052.     {
  1053.         uO.zipinfo_mode = TRUE;
  1054. #ifndef _WIN32_WCE /* Win CE does not support environment variables */
  1055.         if ((error = envargs(&argc, &argv, LoadFarStringSmall(EnvZipInfo),
  1056.                              LoadFarStringSmall2(EnvZipInfo2))) != PK_OK)
  1057.             perror(LoadFarString(NoMemEnvArguments));
  1058. #endif
  1059.     } else
  1060. #endif /* !NO_ZIPINFO */
  1061.     {
  1062.         uO.zipinfo_mode = FALSE;
  1063. #ifndef _WIN32_WCE /* Win CE does not support environment variables */
  1064.         if ((error = envargs(&argc, &argv, LoadFarStringSmall(EnvUnZip),
  1065.                              LoadFarStringSmall2(EnvUnZip2))) != PK_OK)
  1066.             perror(LoadFarString(NoMemEnvArguments));
  1067. #endif
  1068.     }
  1069.  
  1070.     if (!error) {
  1071.         /* Check the length of all passed command line parameters.
  1072.          * Command arguments might get sent through the Info() message
  1073.          * system, which uses the sliding window area as string buffer.
  1074.          * As arguments may additionally get fed through one of the FnFilter
  1075.          * macros, we require all command line arguments to be shorter than
  1076.          * WSIZE/4 (and ca. 2 standard line widths for fixed message text).
  1077.          */
  1078.         for (i = 1 ; i < argc; i++) {
  1079.            if (strlen(argv[i]) > ((WSIZE>>2) - 160)) {
  1080.                Info(slide, 0x401, ((char *)slide,
  1081.                  LoadFarString(CmdLineParamTooLong), i));
  1082.                retcode = PK_PARAM;
  1083.                goto cleanup_and_exit;
  1084.            }
  1085.         }
  1086. #ifndef NO_ZIPINFO
  1087.         if (uO.zipinfo_mode)
  1088.             error = zi_opts(__G__ &argc, &argv);
  1089.         else
  1090. #endif /* !NO_ZIPINFO */
  1091.             error = uz_opts(__G__ &argc, &argv);
  1092.     }
  1093.  
  1094. #endif /* ?SFX */
  1095.  
  1096.     if ((argc < 0) || error) {
  1097.         retcode = error;
  1098.         goto cleanup_and_exit;
  1099.     }
  1100.  
  1101. /*---------------------------------------------------------------------------
  1102.     Now get the zipfile name from the command line and then process any re-
  1103.     maining options and file specifications.
  1104.   ---------------------------------------------------------------------------*/
  1105.  
  1106. #ifdef DOS_FLX_H68_NLM_OS2_W32
  1107.     /* convert MSDOS-style 'backward slash' directory separators to Unix-style
  1108.      * 'forward slashes' for user's convenience (include zipfile name itself)
  1109.      */
  1110. #ifdef SFX
  1111.     for (G.pfnames = argv, i = argc;  i > 0;  --i) {
  1112. #else
  1113.     /* argc does not include the zipfile specification */
  1114.     for (G.pfnames = argv, i = argc+1;  i > 0;  --i) {
  1115. #endif
  1116. #ifdef __human68k__
  1117.         extern char *_toslash(char *);
  1118.         _toslash(*G.pfnames);
  1119. #else /* !__human68k__ */
  1120.         char *q = *G.pfnames;
  1121.  
  1122.         while (*q != '\0') {
  1123.             if (*q == '\\')
  1124.                 *q = '/';
  1125.             INCSTR(q);
  1126.         }
  1127. #endif /* ?__human68k__ */
  1128.         ++G.pfnames;
  1129.     }
  1130. #endif /* DOS_FLX_H68_NLM_OS2_W32 */
  1131.  
  1132. #ifndef SFX
  1133.     G.wildzipfn = *argv++;
  1134. #endif
  1135.  
  1136. #if (defined(SFX) && !defined(SFX_EXDIR)) /* only check for -x */
  1137.  
  1138.     G.filespecs = argc;
  1139.     G.xfilespecs = 0;
  1140.  
  1141.     if (argc > 0) {
  1142.         char **pp = argv-1;
  1143.  
  1144.         G.pfnames = argv;
  1145.         while (*++pp)
  1146.             if (strcmp(*pp, "-x") == 0) {
  1147.                 if (pp > argv) {
  1148.                     *pp = 0;              /* terminate G.pfnames */
  1149.                     G.filespecs = pp - G.pfnames;
  1150.                 } else {
  1151.                     G.pfnames = (char **)fnames;  /* defaults */
  1152.                     G.filespecs = 0;
  1153.                 }
  1154.                 G.pxnames = pp + 1;      /* excluded-names ptr: _after_ -x */
  1155.                 G.xfilespecs = argc - G.filespecs - 1;
  1156.                 break;                    /* skip rest of args */
  1157.             }
  1158.         G.process_all_files = FALSE;
  1159.     } else
  1160.         G.process_all_files = TRUE;      /* for speed */
  1161.  
  1162. #else /* !SFX || SFX_EXDIR */             /* check for -x or -d */
  1163.  
  1164.     G.filespecs = argc;
  1165.     G.xfilespecs = 0;
  1166.  
  1167.     if (argc > 0) {
  1168.         int in_files=FALSE, in_xfiles=FALSE;
  1169.         char **pp = argv-1;
  1170.  
  1171.         G.process_all_files = FALSE;
  1172.         G.pfnames = argv;
  1173.         while (*++pp) {
  1174.             Trace((stderr, "pp - argv = %d\n", pp-argv));
  1175. #ifdef CMS_MVS
  1176.             if (!uO.exdir && STRNICMP(*pp, "-d", 2) == 0) {
  1177. #else
  1178.             if (!uO.exdir && strncmp(*pp, "-d", 2) == 0) {
  1179. #endif
  1180.                 int firstarg = (pp == argv);
  1181.  
  1182.                 uO.exdir = (*pp) + 2;
  1183.                 if (in_files) {      /* ... zipfile ... -d exdir ... */
  1184.                     *pp = (char *)NULL;         /* terminate G.pfnames */
  1185.                     G.filespecs = pp - G.pfnames;
  1186.                     in_files = FALSE;
  1187.                 } else if (in_xfiles) {
  1188.                     *pp = (char *)NULL;         /* terminate G.pxnames */
  1189.                     G.xfilespecs = pp - G.pxnames;
  1190.                     /* "... -x xlist -d exdir":  nothing left */
  1191.                 }
  1192.                 /* first check for "-dexdir", then for "-d exdir" */
  1193.                 if (*uO.exdir == '\0') {
  1194.                     if (*++pp)
  1195.                         uO.exdir = *pp;
  1196.                     else {
  1197.                         Info(slide, 0x401, ((char *)slide,
  1198.                           LoadFarString(MustGiveExdir)));
  1199.                         /* don't extract here by accident */
  1200.                         retcode = PK_PARAM;
  1201.                         goto cleanup_and_exit;
  1202.                     }
  1203.                 }
  1204.                 if (firstarg) { /* ... zipfile -d exdir ... */
  1205.                     if (pp[1]) {
  1206.                         G.pfnames = pp + 1;  /* argv+2 */
  1207.                         G.filespecs = argc - (G.pfnames-argv);  /* for now... */
  1208.                     } else {
  1209.                         G.process_all_files = TRUE;
  1210.                         G.pfnames = (char **)fnames;  /* GRR: necessary? */
  1211.                         G.filespecs = 0;     /* GRR: necessary? */
  1212.                         break;
  1213.                     }
  1214.                 }
  1215.             } else if (!in_xfiles) {
  1216.                 if (strcmp(*pp, "-x") == 0) {
  1217.                     in_xfiles = TRUE;
  1218.                     if (pp == G.pfnames) {
  1219.                         G.pfnames = (char **)fnames;  /* defaults */
  1220.                         G.filespecs = 0;
  1221.                     } else if (in_files) {
  1222.                         *pp = 0;                   /* terminate G.pfnames */
  1223.                         G.filespecs = pp - G.pfnames;  /* adjust count */
  1224.                         in_files = FALSE;
  1225.                     }
  1226.                     G.pxnames = pp + 1; /* excluded-names ptr starts after -x */
  1227.                     G.xfilespecs = argc - (G.pxnames-argv);  /* anything left */
  1228.                 } else
  1229.                     in_files = TRUE;
  1230.             }
  1231.         }
  1232.     } else
  1233.         G.process_all_files = TRUE;      /* for speed */
  1234.  
  1235.     if (uO.exdir != (char *)NULL && !G.extract_flag)    /* -d ignored */
  1236.         Info(slide, 0x401, ((char *)slide, LoadFarString(NotExtracting)));
  1237. #endif /* ?(SFX && !SFX_EXDIR) */
  1238.  
  1239. #ifdef UNICODE_SUPPORT
  1240.     /* set Unicode-escape-all if option -U used */
  1241.     if (uO.U_flag == 1)
  1242. # ifdef UNICODE_WCHAR
  1243.         G.unicode_escape_all = TRUE;
  1244. # else
  1245.         Info(slide, 0x401, ((char *)slide, LoadFarString(UTF8EscapeUnSupp)));
  1246. # endif
  1247. #endif
  1248.  
  1249.  
  1250. /*---------------------------------------------------------------------------
  1251.     Okey dokey, we have everything we need to get started.  Let's roll.
  1252.   ---------------------------------------------------------------------------*/
  1253.  
  1254.     retcode = process_zipfiles(__G);
  1255.  
  1256. cleanup_and_exit:
  1257. #if (defined(REENTRANT) && !defined(NO_EXCEPT_SIGNALS))
  1258.     /* restore all signal handlers back to their state at function entry */
  1259.     while (oldsighandlers != NULL) {
  1260.         savsigs_info *thissigsav = oldsighandlers;
  1261.  
  1262.         signal(thissigsav->sigtype, thissigsav->sighandler);
  1263.         oldsighandlers = thissigsav->previous;
  1264.         free(thissigsav);
  1265.     }
  1266. #endif
  1267. #if (defined(MALLOC_WORK) && !defined(REENTRANT))
  1268.     if (G.area.Slide != (uch *)NULL) {
  1269.         free(G.area.Slide);
  1270.         G.area.Slide = (uch *)NULL;
  1271.     }
  1272. #endif
  1273. #if (defined(MSDOS) && !defined(SFX) && !defined(WINDLL))
  1274.     if (retcode != PK_OK)
  1275.         check_for_windows("UnZip");
  1276. #endif
  1277.     return(retcode);
  1278.  
  1279. } /* end main()/unzip() */
  1280.  
  1281.  
  1282.  
  1283.  
  1284.  
  1285. #if (defined(REENTRANT) && !defined(NO_EXCEPT_SIGNALS))
  1286. /*******************************/
  1287. /* Function setsignalhandler() */
  1288. /*******************************/
  1289.  
  1290. static int setsignalhandler(__G__ p_savedhandler_chain, signal_type,
  1291.                             newhandler)
  1292.     __GDEF
  1293.     savsigs_info **p_savedhandler_chain;
  1294.     int signal_type;
  1295.     void (*newhandler)(int);
  1296. {
  1297.     savsigs_info *savsig;
  1298.  
  1299.     savsig = malloc(sizeof(savsigs_info));
  1300.     if (savsig == NULL) {
  1301.         /* error message and break */
  1302.         Info(slide, 0x401, ((char *)slide, LoadFarString(CantSaveSigHandler)));
  1303.         return PK_MEM;
  1304.     }
  1305.     savsig->sigtype = signal_type;
  1306.     savsig->sighandler = signal(SIGINT, newhandler);
  1307.     if (savsig->sighandler == SIG_ERR) {
  1308.         free(savsig);
  1309.     } else {
  1310.         savsig->previous = *p_savedhandler_chain;
  1311.         *p_savedhandler_chain = savsig;
  1312.     }
  1313.     return PK_OK;
  1314.  
  1315. } /* end function setsignalhandler() */
  1316.  
  1317. #endif /* REENTRANT && !NO_EXCEPT_SIGNALS */
  1318.  
  1319.  
  1320.  
  1321.  
  1322.  
  1323. /**********************/
  1324. /* Function uz_opts() */
  1325. /**********************/
  1326.  
  1327. int uz_opts(__G__ pargc, pargv)
  1328.     __GDEF
  1329.     int *pargc;
  1330.     char ***pargv;
  1331. {
  1332.     char **argv, *s;
  1333.     int argc, c, error=FALSE, negative=0, showhelp=0;
  1334.  
  1335.  
  1336.     argc = *pargc;
  1337.     argv = *pargv;
  1338.  
  1339.     while (++argv, (--argc > 0 && *argv != NULL && **argv == '-')) {
  1340.         s = *argv + 1;
  1341.         while ((c = *s++) != 0) {    /* "!= 0":  prevent Turbo C warning */
  1342. #ifdef CMS_MVS
  1343.             switch (tolower(c))
  1344. #else
  1345.             switch (c)
  1346. #endif
  1347.             {
  1348.                 case ('-'):
  1349.                     ++negative;
  1350.                     break;
  1351. #ifdef RISCOS
  1352.                 case ('/'):
  1353.                     if (negative) {   /* negative not allowed with -/ swap */
  1354.                         Info(slide, 0x401, ((char *)slide,
  1355.                           "error:  must give extensions list"));
  1356.                         return(PK_PARAM);  /* don't extract here by accident */
  1357.                     }
  1358.                     exts2swap = s; /* override Unzip$Exts */
  1359.                     s += strlen(s);
  1360.                     break;
  1361. #endif
  1362.                 case ('a'):
  1363.                     if (negative) {
  1364.                         uO.aflag = MAX(uO.aflag-negative,0);
  1365.                         negative = 0;
  1366.                     } else
  1367.                         ++uO.aflag;
  1368.                     break;
  1369. #if (defined(DLL) && defined(API_DOC))
  1370.                 case ('A'):    /* extended help for API */
  1371.                     APIhelp(__G__ argc, argv);
  1372.                     *pargc = -1;  /* signal to exit successfully */
  1373.                     return 0;
  1374. #endif
  1375.                 case ('b'):
  1376.                     if (negative) {
  1377. #if (defined(TANDEM) || defined(VMS))
  1378.                         uO.bflag = MAX(uO.bflag-negative,0);
  1379. #endif
  1380.                         negative = 0;   /* do nothing:  "-b" is default */
  1381.                     } else {
  1382. #ifdef VMS
  1383.                         if (uO.aflag == 0)
  1384.                            ++uO.bflag;
  1385. #endif
  1386. #ifdef TANDEM
  1387.                         ++uO.bflag;
  1388. #endif
  1389.                         uO.aflag = 0;
  1390.                     }
  1391.                     break;
  1392. #ifdef UNIXBACKUP
  1393.                 case ('B'): /* -B: back up existing files */
  1394.                     if (negative)
  1395.                         uO.B_flag = FALSE, negative = 0;
  1396.                     else
  1397.                         uO.B_flag = TRUE;
  1398.                     break;
  1399. #endif
  1400.                 case ('c'):
  1401.                     if (negative) {
  1402.                         uO.cflag = FALSE, negative = 0;
  1403. #ifdef NATIVE
  1404.                         uO.aflag = 0;
  1405. #endif
  1406.                     } else {
  1407.                         uO.cflag = TRUE;
  1408. #ifdef NATIVE
  1409.                         uO.aflag = 2;   /* so you can read it on the screen */
  1410. #endif
  1411. #ifdef DLL
  1412.                         if (G.redirect_text)
  1413.                             G.redirect_data = 2;
  1414. #endif
  1415.                     }
  1416.                     break;
  1417. #ifndef CMS_MVS
  1418.                 case ('C'):    /* -C:  match filenames case-insensitively */
  1419.                     if (negative)
  1420.                         uO.C_flag = FALSE, negative = 0;
  1421.                     else
  1422.                         uO.C_flag = TRUE;
  1423.                     break;
  1424. #endif /* !CMS_MVS */
  1425. #if (!defined(SFX) || defined(SFX_EXDIR))
  1426.                 case ('d'):
  1427.                     if (negative) {   /* negative not allowed with -d exdir */
  1428.                         Info(slide, 0x401, ((char *)slide,
  1429.                           LoadFarString(MustGiveExdir)));
  1430.                         return(PK_PARAM);  /* don't extract here by accident */
  1431.                     }
  1432.                     if (uO.exdir != (char *)NULL) {
  1433.                         Info(slide, 0x401, ((char *)slide,
  1434.                           LoadFarString(OnlyOneExdir)));
  1435.                         return(PK_PARAM);    /* GRR:  stupid restriction? */
  1436.                     } else {
  1437.                         /* first check for "-dexdir", then for "-d exdir" */
  1438.                         uO.exdir = s;
  1439.                         if (*uO.exdir == '\0') {
  1440.                             if (argc > 1) {
  1441.                                 --argc;
  1442.                                 uO.exdir = *++argv;
  1443.                                 if (*uO.exdir == '-') {
  1444.                                     Info(slide, 0x401, ((char *)slide,
  1445.                                       LoadFarString(MustGiveExdir)));
  1446.                                     return(PK_PARAM);
  1447.                                 }
  1448.                                 /* else uO.exdir points at extraction dir */
  1449.                             } else {
  1450.                                 Info(slide, 0x401, ((char *)slide,
  1451.                                   LoadFarString(MustGiveExdir)));
  1452.                                 return(PK_PARAM);
  1453.                             }
  1454.                         }
  1455.                         /* uO.exdir now points at extraction dir (-dexdir or
  1456.                          *  -d exdir); point s at end of exdir to avoid mis-
  1457.                          *  interpretation of exdir characters as more options
  1458.                          */
  1459.                         if (*s != 0)
  1460.                             while (*++s != 0)
  1461.                                 ;
  1462.                     }
  1463.                     break;
  1464. #endif /* !SFX || SFX_EXDIR */
  1465. #if (!defined(NO_TIMESTAMPS))
  1466.                 case ('D'):    /* -D: Skip restoring dir (or any) timestamp. */
  1467.                     if (negative) {
  1468.                         uO.D_flag = MAX(uO.D_flag-negative,0);
  1469.                         negative = 0;
  1470.                     } else
  1471.                         uO.D_flag++;
  1472.                     break;
  1473. #endif /* (!NO_TIMESTAMPS) */
  1474.                 case ('e'):    /* just ignore -e, -x options (extract) */
  1475.                     break;
  1476. #ifdef MACOS
  1477.                 case ('E'): /* -E [MacOS] display Mac e.f. when restoring */
  1478.                     if( negative ) {
  1479.                         uO.E_flag = FALSE, negative = 0;
  1480.                     } else {
  1481.                         uO.E_flag = TRUE;
  1482.                     }
  1483.                     break;
  1484. #endif /* MACOS */
  1485.                 case ('f'):    /* "freshen" (extract only newer files) */
  1486.                     if (negative)
  1487.                         uO.fflag = uO.uflag = FALSE, negative = 0;
  1488.                     else
  1489.                         uO.fflag = uO.uflag = TRUE;
  1490.                     break;
  1491. #if (defined(RISCOS) || defined(ACORN_FTYPE_NFS))
  1492.                 case ('F'):    /* Acorn filetype & NFS extension handling */
  1493.                     if (negative)
  1494.                         uO.acorn_nfs_ext = FALSE, negative = 0;
  1495.                     else
  1496.                         uO.acorn_nfs_ext = TRUE;
  1497.                     break;
  1498. #endif /* RISCOS || ACORN_FTYPE_NFS */
  1499.                 case ('h'):    /* just print help message and quit */
  1500.                     if (showhelp == 0) {
  1501. #ifndef SFX
  1502.                         if (*s == 'h')
  1503.                             showhelp = 2;
  1504.                         else
  1505. #endif /* !SFX */
  1506.                         {
  1507.                             showhelp = 1;
  1508.                         }
  1509.                     }
  1510.                     break;
  1511. #ifdef MACOS
  1512.                 case ('i'): /* -i [MacOS] ignore filenames stored in Mac ef */
  1513.                     if( negative ) {
  1514.                         uO.i_flag = FALSE, negative = 0;
  1515.                     } else {
  1516.                         uO.i_flag = TRUE;
  1517.                     }
  1518.                     break;
  1519. #endif  /* MACOS */
  1520.                 case ('j'):    /* junk pathnames/directory structure */
  1521.                     if (negative)
  1522.                         uO.jflag = FALSE, negative = 0;
  1523.                     else
  1524.                         uO.jflag = TRUE;
  1525.                     break;
  1526. #if (defined(ATH_BEO) || defined(MACOS))
  1527.                 case ('J'):    /* Junk AtheOS, BeOS or MacOS file attributes */
  1528.                     if( negative ) {
  1529.                         uO.J_flag = FALSE, negative = 0;
  1530.                     } else {
  1531.                         uO.J_flag = TRUE;
  1532.                     }
  1533.                     break;
  1534. #endif /* ATH_BEO || MACOS */
  1535. #ifdef ATH_BEO_UNX
  1536.                 case ('K'):
  1537.                     if (negative) {
  1538.                         uO.K_flag = FALSE, negative = 0;
  1539.                     } else {
  1540.                         uO.K_flag = TRUE;
  1541.                     }
  1542.                     break;
  1543. #endif /* ATH_BEO_UNX */
  1544. #ifndef SFX
  1545.                 case ('l'):
  1546.                     if (negative) {
  1547.                         uO.vflag = MAX(uO.vflag-negative,0);
  1548.                         negative = 0;
  1549.                     } else
  1550.                         ++uO.vflag;
  1551.                     break;
  1552. #endif /* !SFX */
  1553. #ifndef CMS_MVS
  1554.                 case ('L'):    /* convert (some) filenames to lowercase */
  1555.                     if (negative) {
  1556.                         uO.L_flag = MAX(uO.L_flag-negative,0);
  1557.                         negative = 0;
  1558.                     } else
  1559.                         ++uO.L_flag;
  1560.                     break;
  1561. #endif /* !CMS_MVS */
  1562. #ifdef MORE
  1563. #ifdef CMS_MVS
  1564.                 case ('m'):
  1565. #endif
  1566.                 case ('M'):    /* send all screen output through "more" fn. */
  1567. /* GRR:  eventually check for numerical argument => height */
  1568.                     if (negative)
  1569.                         G.M_flag = FALSE, negative = 0;
  1570.                     else
  1571.                         G.M_flag = TRUE;
  1572.                     break;
  1573. #endif /* MORE */
  1574.                 case ('n'):    /* don't overwrite any files */
  1575.                     if (negative)
  1576.                         uO.overwrite_none = FALSE, negative = 0;
  1577.                     else
  1578.                         uO.overwrite_none = TRUE;
  1579.                     break;
  1580. #ifdef AMIGA
  1581.                 case ('N'):    /* restore comments as filenotes */
  1582.                     if (negative)
  1583.                         uO.N_flag = FALSE, negative = 0;
  1584.                     else
  1585.                         uO.N_flag = TRUE;
  1586.                     break;
  1587. #endif /* AMIGA */
  1588.                 case ('o'):    /* OK to overwrite files without prompting */
  1589.                     if (negative) {
  1590.                         uO.overwrite_all = MAX(uO.overwrite_all-negative,0);
  1591.                         negative = 0;
  1592.                     } else
  1593.                         ++uO.overwrite_all;
  1594.                     break;
  1595.                 case ('p'):    /* pipes:  extract to stdout, no messages */
  1596.                     if (negative) {
  1597.                         uO.cflag = FALSE;
  1598.                         uO.qflag = MAX(uO.qflag-999,0);
  1599.                         negative = 0;
  1600.                     } else {
  1601.                         uO.cflag = TRUE;
  1602.                         uO.qflag += 999;
  1603.                     }
  1604.                     break;
  1605. #if CRYPT
  1606.                 /* GRR:  yes, this is highly insecure, but dozens of people
  1607.                  * have pestered us for this, so here we go... */
  1608.                 case ('P'):
  1609.                     if (negative) {   /* negative not allowed with -P passwd */
  1610.                         Info(slide, 0x401, ((char *)slide,
  1611.                           LoadFarString(MustGivePasswd)));
  1612.                         return(PK_PARAM);  /* don't extract here by accident */
  1613.                     }
  1614.                     if (uO.pwdarg != (char *)NULL) {
  1615. /*
  1616.                         GRR:  eventually support multiple passwords?
  1617.                         Info(slide, 0x401, ((char *)slide,
  1618.                           LoadFarString(OnlyOnePasswd)));
  1619.                         return(PK_PARAM);
  1620.  */
  1621.                     } else {
  1622.                         /* first check for "-Ppasswd", then for "-P passwd" */
  1623.                         uO.pwdarg = s;
  1624.                         if (*uO.pwdarg == '\0') {
  1625.                             if (argc > 1) {
  1626.                                 --argc;
  1627.                                 uO.pwdarg = *++argv;
  1628.                                 if (*uO.pwdarg == '-') {
  1629.                                     Info(slide, 0x401, ((char *)slide,
  1630.                                       LoadFarString(MustGivePasswd)));
  1631.                                     return(PK_PARAM);
  1632.                                 }
  1633.                                 /* else pwdarg points at decryption password */
  1634.                             } else {
  1635.                                 Info(slide, 0x401, ((char *)slide,
  1636.                                   LoadFarString(MustGivePasswd)));
  1637.                                 return(PK_PARAM);
  1638.                             }
  1639.                         }
  1640.                         /* pwdarg now points at decryption password (-Ppasswd or
  1641.                          *  -P passwd); point s at end of passwd to avoid mis-
  1642.                          *  interpretation of passwd characters as more options
  1643.                          */
  1644.                         if (*s != 0)
  1645.                             while (*++s != 0)
  1646.                                 ;
  1647.                     }
  1648.                     break;
  1649. #endif /* CRYPT */
  1650.                 case ('q'):    /* quiet:  fewer comments/messages */
  1651.                     if (negative) {
  1652.                         uO.qflag = MAX(uO.qflag-negative,0);
  1653.                         negative = 0;
  1654.                     } else
  1655.                         ++uO.qflag;
  1656.                     break;
  1657. #ifdef QDOS
  1658.                 case ('Q'):   /* QDOS flags */
  1659.                     qlflag ^= strtol(s, &s, 10);
  1660.                     break;    /* we XOR this as we can config qlflags */
  1661. #endif
  1662. #ifdef TANDEM
  1663.                 case ('r'):    /* remove file extensions */
  1664.                     if (negative)
  1665.                         uO.rflag = FALSE, negative = 0;
  1666.                     else
  1667.                         uO.rflag = TRUE;
  1668.                     break;
  1669. #endif /* TANDEM */
  1670. #ifdef DOS_FLX_NLM_OS2_W32
  1671.                 case ('s'):    /* spaces in filenames:  allow by default */
  1672.                     if (negative)
  1673.                         uO.sflag = FALSE, negative = 0;
  1674.                     else
  1675.                         uO.sflag = TRUE;
  1676.                     break;
  1677. #endif /* DOS_FLX_NLM_OS2_W32 */
  1678. #ifdef VMS
  1679.                 /* VMS:  extract "text" files in Stream_LF format (-a[a]) */
  1680.                 case ('S'):
  1681.                     if (negative)
  1682.                         uO.S_flag = FALSE, negative = 0;
  1683.                     else
  1684.                         uO.S_flag = TRUE;
  1685.                     break;
  1686. #endif /* VMS */
  1687.                 case ('t'):
  1688.                     if (negative)
  1689.                         uO.tflag = FALSE, negative = 0;
  1690.                     else
  1691.                         uO.tflag = TRUE;
  1692.                     break;
  1693. #ifdef TIMESTAMP
  1694.                 case ('T'):
  1695.                     if (negative)
  1696.                         uO.T_flag = FALSE, negative = 0;
  1697.                     else
  1698.                         uO.T_flag = TRUE;
  1699.                     break;
  1700. #endif
  1701.                 case ('u'):    /* update (extract only new and newer files) */
  1702.                     if (negative)
  1703.                         uO.uflag = FALSE, negative = 0;
  1704.                     else
  1705.                         uO.uflag = TRUE;
  1706.                     break;
  1707. #ifdef UNICODE_SUPPORT
  1708.                 case ('U'):    /* escape UTF-8, or disable UTF-8 support */
  1709.                     if (negative) {
  1710.                         uO.U_flag = MAX(uO.U_flag-negative,0);
  1711.                         negative = 0;
  1712.                     } else
  1713.                         uO.U_flag++;
  1714.                     break;
  1715. #else /* !UNICODE_SUPPORT */
  1716. #ifndef CMS_MVS
  1717.                 case ('U'):    /* obsolete; to be removed in version 6.0 */
  1718.                     if (negative)
  1719.                         uO.L_flag = TRUE, negative = 0;
  1720.                     else
  1721.                         uO.L_flag = FALSE;
  1722.                     break;
  1723. #endif /* !CMS_MVS */
  1724. #endif /* ?UNICODE_SUPPORT */
  1725. #ifndef SFX
  1726.                 case ('v'):    /* verbose */
  1727.                     if (negative) {
  1728.                         uO.vflag = MAX(uO.vflag-negative,0);
  1729.                         negative = 0;
  1730.                     } else if (uO.vflag)
  1731.                         ++uO.vflag;
  1732.                     else
  1733.                         uO.vflag = 2;
  1734.                     break;
  1735. #endif /* !SFX */
  1736. #ifndef CMS_MVS
  1737.                 case ('V'):    /* Version (retain VMS/DEC-20 file versions) */
  1738.                     if (negative)
  1739.                         uO.V_flag = FALSE, negative = 0;
  1740.                     else
  1741.                         uO.V_flag = TRUE;
  1742.                     break;
  1743. #endif /* !CMS_MVS */
  1744. #ifdef WILD_STOP_AT_DIR
  1745.                 case ('W'):    /* Wildcard interpretation (stop at '/'?) */
  1746.                     if (negative)
  1747.                         uO.W_flag = FALSE, negative = 0;
  1748.                     else
  1749.                         uO.W_flag = TRUE;
  1750.                     break;
  1751. #endif /* WILD_STOP_AT_DIR */
  1752.                 case ('x'):    /* extract:  default */
  1753. #ifdef SFX
  1754.                     /* when 'x' is the only option in this argument, and the
  1755.                      * next arg is not an option, assume this initiates an
  1756.                      * exclusion list (-x xlist):  terminate option-scanning
  1757.                      * and leave uz_opts with argv still pointing to "-x";
  1758.                      * the xlist is processed later
  1759.                      */
  1760.                     if (s - argv[0] == 2 && *s == '\0' &&
  1761.                         argc > 1 && argv[1][0] != '-') {
  1762.                         /* break out of nested loops without "++argv;--argc" */
  1763.                         goto opts_done;
  1764.                     }
  1765. #endif /* SFX */
  1766.                     break;
  1767. #if (defined(RESTORE_UIDGID) || defined(RESTORE_ACL))
  1768.                 case ('X'):   /* restore owner/protection info (need privs?) */
  1769.                     if (negative) {
  1770.                         uO.X_flag = MAX(uO.X_flag-negative,0);
  1771.                         negative = 0;
  1772.                     } else
  1773.                         ++uO.X_flag;
  1774.                     break;
  1775. #endif /* RESTORE_UIDGID || RESTORE_ACL */
  1776. #ifdef VMS
  1777.                 case ('Y'):    /* Treat ".nnn" as ";nnn" version. */
  1778.                     if (negative)
  1779.                         uO.Y_flag = FALSE, negative = 0;
  1780.                     else
  1781.                         uO.Y_flag = TRUE;
  1782.                     break;
  1783. #endif /* VMS */
  1784.                 case ('z'):    /* display only the archive comment */
  1785.                     if (negative) {
  1786.                         uO.zflag = MAX(uO.zflag-negative,0);
  1787.                         negative = 0;
  1788.                     } else
  1789.                         ++uO.zflag;
  1790.                     break;
  1791. #ifndef SFX
  1792.                 case ('Z'):    /* should have been first option (ZipInfo) */
  1793.                     Info(slide, 0x401, ((char *)slide, LoadFarString(Zfirst)));
  1794.                     error = TRUE;
  1795.                     break;
  1796. #endif /* !SFX */
  1797. #ifdef VMS
  1798.                 case ('2'):    /* Force ODS2-compliant names. */
  1799.                     if (negative)
  1800.                         uO.ods2_flag = FALSE, negative = 0;
  1801.                     else
  1802.                         uO.ods2_flag = TRUE;
  1803.                     break;
  1804. #endif /* VMS */
  1805. #ifdef DOS_H68_OS2_W32
  1806.                 case ('$'):
  1807.                     if (negative) {
  1808.                         uO.volflag = MAX(uO.volflag-negative,0);
  1809.                         negative = 0;
  1810.                     } else
  1811.                         ++uO.volflag;
  1812.                     break;
  1813. #endif /* DOS_H68_OS2_W32 */
  1814. #if (!defined(RISCOS) && !defined(CMS_MVS) && !defined(TANDEM))
  1815.                 case (':'):    /* allow "parent dir" path components */
  1816.                     if (negative) {
  1817.                         uO.ddotflag = MAX(uO.ddotflag-negative,0);
  1818.                         negative = 0;
  1819.                     } else
  1820.                         ++uO.ddotflag;
  1821.                     break;
  1822. #endif /* !RISCOS && !CMS_MVS && !TANDEM */
  1823. #ifdef UNIX
  1824.                 case ('^'):    /* allow control chars in filenames */
  1825.                     if (negative) {
  1826.                         uO.cflxflag = MAX(uO.cflxflag-negative,0);
  1827.                         negative = 0;
  1828.                     } else
  1829.                         ++uO.cflxflag;
  1830.                     break;
  1831. #endif /* UNIX */
  1832.                 default:
  1833.                     error = TRUE;
  1834.                     break;
  1835.  
  1836.             } /* end switch */
  1837.         } /* end while (not end of argument string) */
  1838.     } /* end while (not done with switches) */
  1839.  
  1840. /*---------------------------------------------------------------------------
  1841.     Check for nonsensical combinations of options.
  1842.   ---------------------------------------------------------------------------*/
  1843.  
  1844. #ifdef SFX
  1845. opts_done:  /* yes, very ugly...but only used by UnZipSFX with -x xlist */
  1846. #endif
  1847.  
  1848.     if (showhelp > 0) {         /* just print help message and quit */
  1849.         *pargc = -1;
  1850. #ifndef SFX
  1851.         if (showhelp == 2) {
  1852.             help_extended(__G);
  1853.             return PK_OK;
  1854.         } else
  1855. #endif /* !SFX */
  1856.         {
  1857.             return USAGE(PK_OK);
  1858.         }
  1859.     }
  1860.  
  1861.     if ((uO.cflag && (uO.tflag || uO.uflag)) ||
  1862.         (uO.tflag && uO.uflag) || (uO.fflag && uO.overwrite_none))
  1863.     {
  1864.         Info(slide, 0x401, ((char *)slide, LoadFarString(InvalidOptionsMsg)));
  1865.         error = TRUE;
  1866.     }
  1867.     if (uO.aflag > 2)
  1868.         uO.aflag = 2;
  1869. #ifdef VMS
  1870.     if (uO.bflag > 2)
  1871.         uO.bflag = 2;
  1872.     /* Clear -s flag when converting text files. */
  1873.     if (uO.aflag <= 0)
  1874.         uO.S_flag = 0;
  1875. #endif /* VMS */
  1876.     if (uO.overwrite_all && uO.overwrite_none) {
  1877.         Info(slide, 0x401, ((char *)slide, LoadFarString(IgnoreOOptionMsg)));
  1878.         uO.overwrite_all = FALSE;
  1879.     }
  1880. #ifdef MORE
  1881.     if (G.M_flag && !isatty(1))  /* stdout redirected: "more" func. useless */
  1882.         G.M_flag = 0;
  1883. #endif
  1884.  
  1885. #ifdef SFX
  1886.     if (error)
  1887. #else
  1888.     if ((argc-- == 0) || error)
  1889. #endif
  1890.     {
  1891.         *pargc = argc;
  1892.         *pargv = argv;
  1893. #ifndef SFX
  1894.         if (uO.vflag >= 2 && argc == -1) {              /* "unzip -v" */
  1895.             show_version_info(__G);
  1896.             return PK_OK;
  1897.         }
  1898.         if (!G.noargs && !error)
  1899.             error = TRUE;       /* had options (not -h or -v) but no zipfile */
  1900. #endif /* !SFX */
  1901.         return USAGE(error);
  1902.     }
  1903.  
  1904. #ifdef SFX
  1905.     /* print our banner unless we're being fairly quiet */
  1906.     if (uO.qflag < 2)
  1907.         Info(slide, error? 1 : 0, ((char *)slide, LoadFarString(UnzipSFXBanner),
  1908.           UZ_MAJORVER, UZ_MINORVER, UZ_PATCHLEVEL, UZ_BETALEVEL,
  1909.           LoadFarStringSmall(VersionDate)));
  1910. #ifdef BETA
  1911.     /* always print the beta warning:  no unauthorized distribution!! */
  1912.     Info(slide, error? 1 : 0, ((char *)slide, LoadFarString(BetaVersion), "\n",
  1913.       "SFX"));
  1914. #endif
  1915. #endif /* SFX */
  1916.  
  1917.     if (uO.cflag || uO.tflag || uO.vflag || uO.zflag
  1918. #ifdef TIMESTAMP
  1919.                                                      || uO.T_flag
  1920. #endif
  1921.                                                                  )
  1922.         G.extract_flag = FALSE;
  1923.     else
  1924.         G.extract_flag = TRUE;
  1925.  
  1926.     *pargc = argc;
  1927.     *pargv = argv;
  1928.     return PK_OK;
  1929.  
  1930. } /* end function uz_opts() */
  1931.  
  1932.  
  1933.  
  1934.  
  1935. /********************/
  1936. /* Function usage() */
  1937. /********************/
  1938.  
  1939. #ifdef SFX
  1940. #  ifdef VMS
  1941. #    define LOCAL "X.\n\
  1942. (Must quote upper-case options, like \"-V\", unless SET PROC/PARSE=EXTEND.)"
  1943. #  endif
  1944. #  ifdef UNIX
  1945. #    define LOCAL "X"
  1946. #  endif
  1947. #  ifdef DOS_OS2_W32
  1948. #    define LOCAL "s$"
  1949. #  endif
  1950. #  if (defined(FLEXOS) || defined(NLM))
  1951. #    define LOCAL "s"
  1952. #  endif
  1953. #  ifdef AMIGA
  1954. #    define LOCAL "N"
  1955. #  endif
  1956.    /* Default for all other systems: */
  1957. #  ifndef LOCAL
  1958. #    define LOCAL ""
  1959. #  endif
  1960.  
  1961. #  ifndef NO_TIMESTAMP
  1962. #    ifdef MORE
  1963. #      define SFXOPT1 "DM"
  1964. #    else
  1965. #      define SFXOPT1 "D"
  1966. #    endif
  1967. #  else
  1968. #    ifdef MORE
  1969. #      define SFXOPT1 "M"
  1970. #    else
  1971. #      define SFXOPT1 ""
  1972. #    endif
  1973. #  endif
  1974.  
  1975. int usage(__G__ error)   /* return PK-type error code */
  1976.     __GDEF
  1977.     int error;
  1978. {
  1979.     Info(slide, error? 1 : 0, ((char *)slide, LoadFarString(UnzipSFXBanner),
  1980.       UZ_MAJORVER, UZ_MINORVER, UZ_PATCHLEVEL, UZ_BETALEVEL,
  1981.       LoadFarStringSmall(VersionDate)));
  1982.     Info(slide, error? 1 : 0, ((char *)slide, LoadFarString(UnzipSFXOpts),
  1983.       SFXOPT1, LOCAL));
  1984. #ifdef BETA
  1985.     Info(slide, error? 1 : 0, ((char *)slide, LoadFarString(BetaVersion), "\n",
  1986.       "SFX"));
  1987. #endif
  1988.  
  1989.     if (error)
  1990.         return PK_PARAM;
  1991.     else
  1992.         return PK_COOL;     /* just wanted usage screen: no error */
  1993.  
  1994. } /* end function usage() */
  1995.  
  1996.  
  1997.  
  1998.  
  1999.  
  2000. #else /* !SFX */
  2001. #  ifdef VMS
  2002. #    define QUOT '\"'
  2003. #    define QUOTS "\""
  2004. #  else
  2005. #    define QUOT ' '
  2006. #    define QUOTS ""
  2007. #  endif
  2008.  
  2009. int usage(__G__ error)   /* return PK-type error code */
  2010.     __GDEF
  2011.     int error;
  2012. {
  2013.     int flag = (error? 1 : 0);
  2014.  
  2015.  
  2016. /*---------------------------------------------------------------------------
  2017.     Print either ZipInfo usage or UnZip usage, depending on incantation.
  2018.     (Strings must be no longer than 512 bytes for Turbo C, apparently.)
  2019.   ---------------------------------------------------------------------------*/
  2020.  
  2021.     if (uO.zipinfo_mode) {
  2022.  
  2023. #ifndef NO_ZIPINFO
  2024.  
  2025.         Info(slide, flag, ((char *)slide, LoadFarString(ZipInfoUsageLine1),
  2026.           ZI_MAJORVER, ZI_MINORVER, UZ_PATCHLEVEL, UZ_BETALEVEL,
  2027.           LoadFarStringSmall(VersionDate),
  2028.           LoadFarStringSmall2(ZipInfoExample), QUOTS,QUOTS));
  2029.         Info(slide, flag, ((char *)slide, LoadFarString(ZipInfoUsageLine2)));
  2030.         Info(slide, flag, ((char *)slide, LoadFarString(ZipInfoUsageLine3),
  2031.           LoadFarStringSmall(ZipInfoUsageLine4)));
  2032. #ifdef VMS
  2033.         Info(slide, flag, ((char *)slide, "\n\
  2034. You must quote non-lowercase options and filespecs, unless SET PROC/PARSE=EXT.\
  2035. \n"));
  2036. #endif
  2037.  
  2038. #endif /* !NO_ZIPINFO */
  2039.  
  2040.     } else {   /* UnZip mode */
  2041.  
  2042.         Info(slide, flag, ((char *)slide, LoadFarString(UnzipUsageLine1),
  2043.           UZ_MAJORVER, UZ_MINORVER, UZ_PATCHLEVEL, UZ_BETALEVEL,
  2044.           LoadFarStringSmall(VersionDate)));
  2045. #ifdef BETA
  2046.         Info(slide, flag, ((char *)slide, LoadFarString(BetaVersion), "", ""));
  2047. #endif
  2048.  
  2049.         Info(slide, flag, ((char *)slide, LoadFarString(UnzipUsageLine2),
  2050.           ZIPINFO_MODE_OPTION, LoadFarStringSmall(ZipInfoMode)));
  2051. #ifdef VMS
  2052.         if (!error)  /* maybe no command-line tail found; show extra help */
  2053.             Info(slide, flag, ((char *)slide, LoadFarString(VMSusageLine2b)));
  2054. #endif
  2055.  
  2056.         Info(slide, flag, ((char *)slide, LoadFarString(UnzipUsageLine3),
  2057.           LoadFarStringSmall(local1)));
  2058.  
  2059.         Info(slide, flag, ((char *)slide, LoadFarString(UnzipUsageLine4),
  2060.           LoadFarStringSmall(local2), LoadFarStringSmall2(local3)));
  2061.  
  2062.         /* This is extra work for SMALL_MEM, but it will work since
  2063.          * LoadFarStringSmall2 uses the same buffer.  Remember, this
  2064.          * is a hack. */
  2065.         Info(slide, flag, ((char *)slide, LoadFarString(UnzipUsageLine5),
  2066.           LoadFarStringSmall(Example2), LoadFarStringSmall2(Example3),
  2067.           LoadFarStringSmall2(Example3)));
  2068.  
  2069.     } /* end if (uO.zipinfo_mode) */
  2070.  
  2071.     if (error)
  2072.         return PK_PARAM;
  2073.     else
  2074.         return PK_COOL;     /* just wanted usage screen: no error */
  2075.  
  2076. } /* end function usage() */
  2077.  
  2078. #endif /* ?SFX */
  2079.  
  2080.  
  2081.  
  2082.  
  2083. #ifndef SFX
  2084.  
  2085. /* Print extended help to stdout. */
  2086. static void help_extended(__G)
  2087.     __GDEF
  2088. {
  2089.     extent i;             /* counter for help array */
  2090.  
  2091.     /* help array */
  2092.     static ZCONST char *text[] = {
  2093.   "",
  2094.   "Extended Help for UnZip",
  2095.   "",
  2096.   "See the UnZip Manual for more detailed help",
  2097.   "",
  2098.   "",
  2099.   "UnZip lists and extracts files in zip archives.  The default action is to",
  2100.   "extract zipfile entries to the current directory, creating directories as",
  2101.   "needed.  With appropriate options, UnZip lists the contents of archives",
  2102.   "instead.",
  2103.   "",
  2104.   "Basic unzip command line:",
  2105.   "  unzip [-Z] options archive[.zip] [file ...] [-x xfile ...] [-d exdir]",
  2106.   "",
  2107.   "Some examples:",
  2108.   "  unzip -l foo.zip        - list files in short format in archive foo.zip",
  2109.   "",
  2110.   "  unzip -t foo            - test the files in archive foo",
  2111.   "",
  2112.   "  unzip -Z foo            - list files using more detailed zipinfo format",
  2113.   "",
  2114.   "  unzip foo               - unzip the contents of foo in current dir",
  2115.   "",
  2116.   "  unzip -a foo            - unzip foo and convert text files to local OS",
  2117.   "",
  2118.   "If unzip is run in zipinfo mode, a more detailed list of archive contents",
  2119.   "is provided.  The -Z option sets zipinfo mode and changes the available",
  2120.   "options.",
  2121.   "",
  2122.   "Basic zipinfo command line:",
  2123.   "  zipinfo options archive[.zip] [file ...] [-x xfile ...]",
  2124.   "  unzip -Z options archive[.zip] [file ...] [-x xfile ...]",
  2125.   "",
  2126.   "Below, Mac OS refers to Mac OS before Mac OS X.  Mac OS X is a Unix based",
  2127.   "port and is referred to as Unix Apple.",
  2128.   "",
  2129.   "",
  2130.   "unzip options:",
  2131.   "  -Z   Switch to zipinfo mode.  Must be first option.",
  2132.   "  -hh  Display extended help.",
  2133.   "  -A   [OS/2, Unix DLL] Print extended help for DLL.",
  2134.   "  -c   Extract files to stdout/screen.  As -p but include names.  Also,",
  2135.   "         -a allowed and EBCDIC conversions done if needed.",
  2136.   "  -f   Freshen by extracting only if older file on disk.",
  2137.   "  -l   List files using short form.",
  2138.   "  -p   Extract files to pipe (stdout).  Only file data is output and all",
  2139.   "         files extracted in binary mode (as stored).",
  2140.   "  -t   Test archive files.",
  2141.   "  -T   Set timestamp on archive(s) to that of newest file.  Similar to",
  2142.   "       zip -o but faster.",
  2143.   "  -u   Update existing older files on disk as -f and extract new files.",
  2144.   "  -v   Use verbose list format.  If given alone as unzip -v show version",
  2145.   "         information.  Also can be added to other list commands for more",
  2146.   "         verbose output.",
  2147.   "  -z   Display only archive comment.",
  2148.   "",
  2149.   "unzip modifiers:",
  2150.   "  -a   Convert text files to local OS format.  Convert line ends, EOF",
  2151.   "         marker, and from or to EBCDIC character set as needed.",
  2152.   "  -b   Treat all files as binary.  [Tandem] Force filecode 180 ('C').",
  2153.   "         [VMS] Autoconvert binary files.  -bb forces convert of all files.",
  2154.   "  -B   [UNIXBACKUP compile option enabled] Save a backup copy of each",
  2155.   "         overwritten file in foo~ or foo~99999 format.",
  2156.   "  -C   Use case-insensitive matching.",
  2157.   "  -D   Skip restoration of timestamps for extracted directories.  On VMS this",
  2158.   "         is on by default and -D essentially becames -DD.",
  2159.   "  -DD  Skip restoration of timestamps for all entries.",
  2160.   "  -E   [MacOS (not Unix Apple)]  Display contents of MacOS extra field during",
  2161.   "         restore.",
  2162.   "  -F   [Acorn] Suppress removal of NFS filetype extension.  [Non-Acorn if",
  2163.   "         ACORN_FTYPE_NFS] Translate filetype and append to name.",
  2164.   "  -i   [MacOS] Ignore filenames in MacOS extra field.  Instead, use name in",
  2165.   "         standard header.",
  2166.   "  -j   Junk paths and deposit all files in extraction directory.",
  2167.   "  -J   [BeOS] Junk file attributes.  [MacOS] Ignore MacOS specific info.",
  2168.   "  -K   [AtheOS, BeOS, Unix] Restore SUID/SGID/Tacky file attributes.",
  2169.   "  -L   Convert to lowercase any names from uppercase only file system.",
  2170.   "  -LL  Convert all files to lowercase.",
  2171.   "  -M   Pipe all output through internal pager similar to Unix more(1).",
  2172.   "  -n   Never overwrite existing files.  Skip extracting that file, no prompt.",
  2173.   "  -N   [Amiga] Extract file comments as Amiga filenotes.",
  2174.   "  -o   Overwrite existing files without prompting.  Useful with -f.  Use with",
  2175.   "         care.",
  2176.   "  -P p Use password p to decrypt files.  THIS IS INSECURE!  Some OS show",
  2177.   "         command line to other users.",
  2178.   "  -q   Perform operations quietly.  The more q (as in -qq) the quieter.",
  2179.   "  -s   [OS/2, NT, MS-DOS] Convert spaces in filenames to underscores.",
  2180.   "  -S   [VMS] Convert text files (-a, -aa) into Stream_LF format.",
  2181.   "  -U   [UNICODE enabled] Show non-local characters as #Uxxxx or #Lxxxxxx ASCII",
  2182.   "         text escapes where x is hex digit.  [Old] -U used to leave names",
  2183.   "         uppercase if created on MS-DOS, VMS, etc.  See -L.",
  2184.   "  -UU  [UNICODE enabled] Disable use of stored UTF-8 paths.  Note that UTF-8",
  2185.   "         paths stored as native local paths are still processed as Unicode.",
  2186.   "  -V   Retain VMS file version numbers.",
  2187.   "  -W   [Only if WILD_STOP_AT_DIR] Modify pattern matching so ? and * do not",
  2188.   "         match directory separator /, but ** does.  Allows matching at specific",
  2189.   "         directory levels.",
  2190.   "  -X   [VMS, Unix, OS/2, NT, Tandem] Restore UICs and ACL entries under VMS,",
  2191.   "         or UIDs/GIDs under Unix, or ACLs under certain network-enabled",
  2192.   "         versions of OS/2, or security ACLs under Windows NT.  Can require",
  2193.   "         user privileges.",
  2194.   "  -XX  [NT] Extract NT security ACLs after trying to enable additional",
  2195.   "         system privileges.",
  2196.   "  -Y   [VMS] Treat archived name endings of .nnn as VMS version numbers.",
  2197.   "  -$   [MS-DOS, OS/2, NT] Restore volume label if extraction medium is",
  2198.   "         removable.  -$$ allows fixed media (hard drives) to be labeled.",
  2199.   "  -/ e [Acorn] Use e as extension list.",
  2200.   "  -:   [All but Acorn, VM/CMS, MVS, Tandem] Allow extract archive members into",
  2201.   "         locations outside of current extraction root folder.  This allows",
  2202.   "         paths such as ../foo to be extracted above the current extraction",
  2203.   "         directory, which can be a security problem.",
  2204.   "  -^   [Unix] Allow control characters in names of extracted entries.  Usually",
  2205.   "         this is not a good thing and should be avoided.",
  2206.   "  -2   [VMS] Force unconditional conversion of names to ODS-compatible names.",
  2207.   "         Default is to exploit destination file system, preserving cases and",
  2208.   "         extended name characters on ODS5 and applying ODS2 filtering on ODS2.",
  2209.   "",
  2210.   "",
  2211.   "Wildcards:",
  2212.   "  Internally unzip supports the following wildcards:",
  2213.   "    ?       (or %% or #, depending on OS) matches any single character",
  2214.   "    *       matches any number of characters, including zero",
  2215.   "    [list]  matches char in list (regex), can do range [ac-f], all but [!bf]",
  2216.   "  If port supports [], must escape [ as [[]",
  2217.   "  For shells that expand wildcards, escape (\\* or \"*\") so unzip can recurse.",
  2218.   "",
  2219.   "Include and Exclude:",
  2220.   "  -i pattern pattern ...   include files that match a pattern",
  2221.   "  -x pattern pattern ...   exclude files that match a pattern",
  2222.   "  Patterns are paths with optional wildcards and match paths as stored in",
  2223.   "  archive.  Exclude and include lists end at next option or end of line.",
  2224.   "    unzip archive -x pattern pattern ...",
  2225.   "",
  2226.   "Multi-part (split) archives (archives created as a set of split files):",
  2227.   "  Currently split archives are not readable by unzip.  A workaround is",
  2228.   "  to use zip to convert the split archive to a single-file archive and",
  2229.   "  use unzip on that.  See the manual page for Zip 3.0 or later.",
  2230.   "",
  2231.   "Streaming (piping into unzip):",
  2232.   "  Currently unzip does not support streaming.  The funzip utility can be",
  2233.   "  used to process the first entry in a stream.",
  2234.   "    cat archive | funzip",
  2235.   "",
  2236.   "Testing archives:",
  2237.   "  -t        test contents of archive",
  2238.   "  This can be modified using -q for quieter operation, and -qq for even",
  2239.   "  quieter operation.",
  2240.   "",
  2241.   "Unicode:",
  2242.   "  If compiled with Unicode support, unzip automatically handles archives",
  2243.   "  with Unicode entries.  Currently Unicode on Win32 systems is limited.",
  2244.   "  Characters not in the current character set are shown as ASCII escapes",
  2245.   "  in the form #Uxxxx where the Unicode character number fits in 16 bits,",
  2246.   "  or #Lxxxxxx where it doesn't, where x is the ASCII character for a hex",
  2247.   "  digit.",
  2248.   "",
  2249.   "",
  2250.   "zipinfo options (these are used in zipinfo mode (unzip -Z ...)):",
  2251.   "  -1  List names only, one per line.  No headers/trailers.  Good for scripts.",
  2252.   "  -2  List names only as -1, but include headers, trailers, and comments.",
  2253.   "  -s  List archive entries in short Unix ls -l format.  Default list format.",
  2254.   "  -m  List in long Unix ls -l format.  As -s, but includes compression %.",
  2255.   "  -l  List in long Unix ls -l format.  As -m, but compression in bytes.",
  2256.   "  -v  List zipfile information in verbose, multi-page format.",
  2257.   "  -h  List header line.  Includes archive name, actual size, total files.",
  2258.   "  -M  Pipe all output through internal pager similar to Unix more(1) command.",
  2259.   "  -t  List totals for files listed or for all files.  Includes uncompressed",
  2260.   "        and compressed sizes, and compression factors.",
  2261.   "  -T  Print file dates and times in a sortable decimal format (yymmdd.hhmmss)",
  2262.   "        Default date and time format is a more human-readable version.",
  2263.   "  -U  [UNICODE] If entry has a UTF-8 Unicode path, display any characters",
  2264.   "        not in current character set as text #Uxxxx and #Lxxxxxx escapes",
  2265.   "        representing the Unicode character number of the character in hex.",
  2266.   "  -UU [UNICODE]  Disable use of any UTF-8 path information.",
  2267.   "  -z  Include archive comment if any in listing.",
  2268.   "",
  2269.   "",
  2270.   "funzip stream extractor:",
  2271.   "  funzip extracts the first member in an archive to stdout.  Typically",
  2272.   "  used to unzip the first member of a stream or pipe.  If a file argument",
  2273.   "  is given, read from that file instead of stdin.",
  2274.   "",
  2275.   "funzip command line:",
  2276.   "  funzip [-password] [input[.zip|.gz]]",
  2277.   "",
  2278.   "",
  2279.   "unzipsfx self extractor:",
  2280.   "  Self-extracting archives made with unzipsfx are no more (or less)",
  2281.   "  portable across different operating systems than unzip executables.",
  2282.   "  In general, a self-extracting archive made on a particular Unix system,",
  2283.   "  for example, will only self-extract under the same flavor of Unix.",
  2284.   "  Regular unzip may still be used to extract embedded archive however.",
  2285.   "",
  2286.   "unzipsfx command line:",
  2287.   "  <unzipsfx+archive_filename>  [-options] [file(s) ... [-x xfile(s) ...]]",
  2288.   "",
  2289.   "unzipsfx options:",
  2290.   "  -c, -p - Output to pipe.  (See above for unzip.)",
  2291.   "  -f, -u - Freshen and Update, as for unzip.",
  2292.   "  -t     - Test embedded archive.  (Can be used to list contents.)",
  2293.   "  -z     - Print archive comment.  (See unzip above.)",
  2294.   "",
  2295.   "unzipsfx modifiers:",
  2296.   "  Most unzip modifiers are supported.  These include",
  2297.   "  -a     - Convert text files.",
  2298.   "  -n     - Never overwrite.",
  2299.   "  -o     - Overwrite without prompting.",
  2300.   "  -q     - Quiet operation.",
  2301.   "  -C     - Match names case-insensitively.",
  2302.   "  -j     - Junk paths.",
  2303.   "  -V     - Keep version numbers.",
  2304.   "  -s     - Convert spaces to underscores.",
  2305.   "  -$     - Restore volume label.",
  2306.   "",
  2307.   "If unzipsfx compiled with SFX_EXDIR defined, -d option also available:",
  2308.   "  -d exd - Extract to directory exd.",
  2309.   "By default, all files extracted to current directory.  This option",
  2310.   "forces extraction to specified directory.",
  2311.   "",
  2312.   "See unzipsfx manual page for more information.",
  2313.   ""
  2314.     };
  2315.  
  2316.     for (i = 0; i < sizeof(text)/sizeof(char *); i++)
  2317.     {
  2318.         Info(slide, 0, ((char *)slide, "%s\n", text[i]));
  2319.     }
  2320. } /* end function help_extended() */
  2321.  
  2322.  
  2323.  
  2324.  
  2325. #ifndef _WIN32_WCE /* Win CE does not support environment variables */
  2326. #if (!defined(MODERN) || defined(NO_STDLIB_H))
  2327. /* Declare getenv() to be sure (might be missing in some environments) */
  2328. extern char *getenv();
  2329. #endif
  2330. #endif
  2331.  
  2332. /********************************/
  2333. /* Function show_version_info() */
  2334. /********************************/
  2335.  
  2336. static void show_version_info(__G)
  2337.     __GDEF
  2338. {
  2339.     if (uO.qflag > 3)                           /* "unzip -vqqqq" */
  2340.         Info(slide, 0, ((char *)slide, "%d\n",
  2341.           (UZ_MAJORVER*100 + UZ_MINORVER*10 + UZ_PATCHLEVEL)));
  2342.     else {
  2343. #ifndef _WIN32_WCE /* Win CE does not support environment variables */
  2344.         char *envptr;
  2345. #endif
  2346.         int numopts = 0;
  2347.  
  2348.         Info(slide, 0, ((char *)slide, LoadFarString(UnzipUsageLine1v),
  2349.           UZ_MAJORVER, UZ_MINORVER, UZ_PATCHLEVEL, UZ_BETALEVEL,
  2350.           LoadFarStringSmall(VersionDate)));
  2351.         Info(slide, 0, ((char *)slide,
  2352.           LoadFarString(UnzipUsageLine2v)));
  2353.         version(__G);
  2354.         Info(slide, 0, ((char *)slide, LoadFarString(CompileOptions)));
  2355. #ifdef ACORN_FTYPE_NFS
  2356.         Info(slide, 0, ((char *)slide, LoadFarString(CompileOptFormat),
  2357.           LoadFarStringSmall(AcornFtypeNFS)));
  2358.         ++numopts;
  2359. #endif
  2360. #ifdef ASM_CRC
  2361.         Info(slide, 0, ((char *)slide, LoadFarString(CompileOptFormat),
  2362.           LoadFarStringSmall(AsmCRC)));
  2363.         ++numopts;
  2364. #endif
  2365. #ifdef ASM_INFLATECODES
  2366.         Info(slide, 0, ((char *)slide, LoadFarString(CompileOptFormat),
  2367.           LoadFarStringSmall(AsmInflateCodes)));
  2368.         ++numopts;
  2369. #endif
  2370. #ifdef CHECK_VERSIONS
  2371.         Info(slide, 0, ((char *)slide, LoadFarString(CompileOptFormat),
  2372.           LoadFarStringSmall(Check_Versions)));
  2373.         ++numopts;
  2374. #endif
  2375. #ifdef COPYRIGHT_CLEAN
  2376.         Info(slide, 0, ((char *)slide, LoadFarString(CompileOptFormat),
  2377.           LoadFarStringSmall(Copyright_Clean)));
  2378.         ++numopts;
  2379. #endif
  2380. #ifdef DEBUG
  2381.         Info(slide, 0, ((char *)slide, LoadFarString(CompileOptFormat),
  2382.           LoadFarStringSmall(UDebug)));
  2383.         ++numopts;
  2384. #endif
  2385. #ifdef DEBUG_TIME
  2386.         Info(slide, 0, ((char *)slide, LoadFarString(CompileOptFormat),
  2387.           LoadFarStringSmall(DebugTime)));
  2388.         ++numopts;
  2389. #endif
  2390. #ifdef DLL
  2391.         Info(slide, 0, ((char *)slide, LoadFarString(CompileOptFormat),
  2392.           LoadFarStringSmall(Dll)));
  2393.         ++numopts;
  2394. #endif
  2395. #ifdef DOSWILD
  2396.         Info(slide, 0, ((char *)slide, LoadFarString(CompileOptFormat),
  2397.           LoadFarStringSmall(DosWild)));
  2398.         ++numopts;
  2399. #endif
  2400. #ifdef LZW_CLEAN
  2401.         Info(slide, 0, ((char *)slide, LoadFarString(CompileOptFormat),
  2402.           LoadFarStringSmall(LZW_Clean)));
  2403.         ++numopts;
  2404. #endif
  2405. #ifndef MORE
  2406.         Info(slide, 0, ((char *)slide, LoadFarString(CompileOptFormat),
  2407.           LoadFarStringSmall(No_More)));
  2408.         ++numopts;
  2409. #endif
  2410. #ifdef NO_ZIPINFO
  2411.         Info(slide, 0, ((char *)slide, LoadFarString(CompileOptFormat),
  2412.           LoadFarStringSmall(No_ZipInfo)));
  2413.         ++numopts;
  2414. #endif
  2415. #ifdef NTSD_EAS
  2416.         Info(slide, 0, ((char *)slide, LoadFarString(CompileOptFormat),
  2417.           LoadFarStringSmall(NTSDExtAttrib)));
  2418.         ++numopts;
  2419. #endif
  2420. #if defined(WIN32) && defined(NO_W32TIMES_IZFIX)
  2421.         Info(slide, 0, ((char *)slide, LoadFarString(CompileOptFormat),
  2422.           LoadFarStringSmall(W32NoIZTimeFix)));
  2423.         ++numopts;
  2424. #endif
  2425. #ifdef OLD_THEOS_EXTRA
  2426.         Info(slide, 0, ((char *)slide, LoadFarString(CompileOptFormat),
  2427.           LoadFarStringSmall(OldTheosExtra)));
  2428.         ++numopts;
  2429. #endif
  2430. #ifdef OS2_EAS
  2431.         Info(slide, 0, ((char *)slide, LoadFarString(CompileOptFormat),
  2432.           LoadFarStringSmall(OS2ExtAttrib)));
  2433.         ++numopts;
  2434. #endif
  2435. #ifdef QLZIP
  2436.         Info(slide, 0, ((char *)slide, LoadFarString(CompileOptFormat),
  2437.           LoadFarStringSmall(SMSExFldOnUnix)));
  2438.         ++numopts;
  2439. #endif
  2440. #ifdef REENTRANT
  2441.         Info(slide, 0, ((char *)slide, LoadFarString(CompileOptFormat),
  2442.           LoadFarStringSmall(Reentrant)));
  2443.         ++numopts;
  2444. #endif
  2445. #ifdef REGARGS
  2446.         Info(slide, 0, ((char *)slide, LoadFarString(CompileOptFormat),
  2447.           LoadFarStringSmall(RegArgs)));
  2448.         ++numopts;
  2449. #endif
  2450. #ifdef RETURN_CODES
  2451.         Info(slide, 0, ((char *)slide, LoadFarString(CompileOptFormat),
  2452.           LoadFarStringSmall(Return_Codes)));
  2453.         ++numopts;
  2454. #endif
  2455. #ifdef SET_DIR_ATTRIB
  2456.         Info(slide, 0, ((char *)slide, LoadFarString(CompileOptFormat),
  2457.           LoadFarStringSmall(SetDirAttrib)));
  2458.         ++numopts;
  2459. #endif
  2460. #ifdef SYMLINKS
  2461.         Info(slide, 0, ((char *)slide, LoadFarString(CompileOptFormat),
  2462.           LoadFarStringSmall(SymLinkSupport)));
  2463.         ++numopts;
  2464. #endif
  2465. #ifdef TIMESTAMP
  2466.         Info(slide, 0, ((char *)slide, LoadFarString(CompileOptFormat),
  2467.           LoadFarStringSmall(TimeStamp)));
  2468.         ++numopts;
  2469. #endif
  2470. #ifdef UNIXBACKUP
  2471.         Info(slide, 0, ((char *)slide, LoadFarString(CompileOptFormat),
  2472.           LoadFarStringSmall(UnixBackup)));
  2473.         ++numopts;
  2474. #endif
  2475. #ifdef USE_EF_UT_TIME
  2476.         Info(slide, 0, ((char *)slide, LoadFarString(CompileOptFormat),
  2477.           LoadFarStringSmall(Use_EF_UT_time)));
  2478.         ++numopts;
  2479. #endif
  2480. #ifndef COPYRIGHT_CLEAN
  2481.         Info(slide, 0, ((char *)slide, LoadFarString(CompileOptFormat),
  2482.           LoadFarStringSmall(Use_Smith_Code)));
  2483.         ++numopts;
  2484. #endif
  2485. #ifndef LZW_CLEAN
  2486.         Info(slide, 0, ((char *)slide, LoadFarString(CompileOptFormat),
  2487.           LoadFarStringSmall(Use_Unshrink)));
  2488.         ++numopts;
  2489. #endif
  2490. #ifdef USE_DEFLATE64
  2491.         Info(slide, 0, ((char *)slide, LoadFarString(CompileOptFormat),
  2492.           LoadFarStringSmall(Use_Deflate64)));
  2493.         ++numopts;
  2494. #endif
  2495. #ifdef UNICODE_SUPPORT
  2496. # ifdef UTF8_MAYBE_NATIVE
  2497.         sprintf((char *)(slide+256), LoadFarStringSmall(Use_Unicode),
  2498.           LoadFarStringSmall2(G.native_is_utf8 ? SysChUTF8 : SysChOther));
  2499.         Info(slide, 0, ((char *)slide, LoadFarString(CompileOptFormat),
  2500.           (char *)(slide+256)));
  2501. # else
  2502.         Info(slide, 0, ((char *)slide, LoadFarString(CompileOptFormat),
  2503.           LoadFarStringSmall(Use_Unicode)));
  2504. # endif
  2505.         ++numopts;
  2506. #endif
  2507. #ifdef _MBCS
  2508.         sprintf((char *)(slide+256), LoadFarStringSmall(Have_MBCS_Support),
  2509.           (unsigned int)MB_CUR_MAX);
  2510.         Info(slide, 0, ((char *)slide, LoadFarString(CompileOptFormat),
  2511.           (char *)(slide+256)));
  2512.         ++numopts;
  2513. #endif
  2514. #ifdef MULT_VOLUME
  2515.         Info(slide, 0, ((char *)slide, LoadFarString(CompileOptFormat),
  2516.           LoadFarStringSmall(Use_MultiVol)));
  2517.         ++numopts;
  2518. #endif
  2519. #ifdef LARGE_FILE_SUPPORT
  2520.         Info(slide, 0, ((char *)slide, LoadFarString(CompileOptFormat),
  2521.           LoadFarStringSmall(Use_LFS)));
  2522.         ++numopts;
  2523. #endif
  2524. #ifdef ZIP64_SUPPORT
  2525.         Info(slide, 0, ((char *)slide, LoadFarString(CompileOptFormat),
  2526.           LoadFarStringSmall(Use_Zip64)));
  2527.         ++numopts;
  2528. #endif
  2529. #if (defined(__DJGPP__) && (__DJGPP__ >= 2))
  2530. #  ifdef USE_DJGPP_ENV
  2531.         Info(slide, 0, ((char *)slide, LoadFarString(CompileOptFormat),
  2532.           LoadFarStringSmall(Use_DJGPP_Env)));
  2533.         ++numopts;
  2534. #  endif
  2535. #  ifdef USE_DJGPP_GLOB
  2536.         Info(slide, 0, ((char *)slide, LoadFarString(CompileOptFormat),
  2537.           LoadFarStringSmall(Use_DJGPP_Glob)));
  2538.         ++numopts;
  2539. #  endif
  2540. #endif /* __DJGPP__ && (__DJGPP__ >= 2) */
  2541. #ifdef USE_VFAT
  2542.         Info(slide, 0, ((char *)slide, LoadFarString(CompileOptFormat),
  2543.           LoadFarStringSmall(Use_VFAT_support)));
  2544.         ++numopts;
  2545. #endif
  2546. #ifdef USE_ZLIB
  2547.         sprintf((char *)(slide+256), LoadFarStringSmall(UseZlib),
  2548.           ZLIB_VERSION, zlibVersion());
  2549.         Info(slide, 0, ((char *)slide, LoadFarString(CompileOptFormat),
  2550.           (char *)(slide+256)));
  2551.         ++numopts;
  2552. #endif
  2553. #ifdef USE_BZIP2
  2554.         sprintf((char *)(slide+256), LoadFarStringSmall(UseBZip2),
  2555.           BZ2_bzlibVersion());
  2556.         Info(slide, 0, ((char *)slide, LoadFarString(CompileOptFormat),
  2557.           (char *)(slide+256)));
  2558.         ++numopts;
  2559. #endif
  2560. #ifdef VMS_TEXT_CONV
  2561.         Info(slide, 0, ((char *)slide, LoadFarString(CompileOptFormat),
  2562.           LoadFarStringSmall(VmsTextConv)));
  2563.         ++numopts;
  2564. #endif
  2565. #ifdef VMSCLI
  2566.         Info(slide, 0, ((char *)slide, LoadFarString(CompileOptFormat),
  2567.           LoadFarStringSmall(VmsCLI)));
  2568.         ++numopts;
  2569. #endif
  2570. #ifdef VMSWILD
  2571.         Info(slide, 0, ((char *)slide, LoadFarString(CompileOptFormat),
  2572.           LoadFarStringSmall(VmsWild)));
  2573.         ++numopts;
  2574. #endif
  2575. #ifdef WILD_STOP_AT_DIR
  2576.         Info(slide, 0, ((char *)slide, LoadFarString(CompileOptFormat),
  2577.           LoadFarStringSmall(WildStopAtDir)));
  2578.         ++numopts;
  2579. #endif
  2580. #if CRYPT
  2581. # ifdef PASSWD_FROM_STDIN
  2582.         Info(slide, 0, ((char *)slide, LoadFarString(CompileOptFormat),
  2583.           LoadFarStringSmall(PasswdStdin)));
  2584. # endif
  2585.         Info(slide, 0, ((char *)slide, LoadFarString(Decryption),
  2586.           CR_MAJORVER, CR_MINORVER, CR_BETA_VER,
  2587.           LoadFarStringSmall(CryptDate)));
  2588.         ++numopts;
  2589. #endif /* CRYPT */
  2590.         if (numopts == 0)
  2591.             Info(slide, 0, ((char *)slide,
  2592.               LoadFarString(CompileOptFormat),
  2593.               LoadFarStringSmall(None)));
  2594.  
  2595. #ifndef _WIN32_WCE /* Win CE does not support environment variables */
  2596.         Info(slide, 0, ((char *)slide, LoadFarString(EnvOptions)));
  2597.         envptr = getenv(LoadFarStringSmall(EnvUnZip));
  2598.         Info(slide, 0, ((char *)slide, LoadFarString(EnvOptFormat),
  2599.           LoadFarStringSmall(EnvUnZip),
  2600.           (envptr == (char *)NULL || *envptr == 0)?
  2601.           LoadFarStringSmall2(None) : envptr));
  2602.         envptr = getenv(LoadFarStringSmall(EnvUnZip2));
  2603.         Info(slide, 0, ((char *)slide, LoadFarString(EnvOptFormat),
  2604.           LoadFarStringSmall(EnvUnZip2),
  2605.           (envptr == (char *)NULL || *envptr == 0)?
  2606.           LoadFarStringSmall2(None) : envptr));
  2607.         envptr = getenv(LoadFarStringSmall(EnvZipInfo));
  2608.         Info(slide, 0, ((char *)slide, LoadFarString(EnvOptFormat),
  2609.           LoadFarStringSmall(EnvZipInfo),
  2610.           (envptr == (char *)NULL || *envptr == 0)?
  2611.           LoadFarStringSmall2(None) : envptr));
  2612.         envptr = getenv(LoadFarStringSmall(EnvZipInfo2));
  2613.         Info(slide, 0, ((char *)slide, LoadFarString(EnvOptFormat),
  2614.           LoadFarStringSmall(EnvZipInfo2),
  2615.           (envptr == (char *)NULL || *envptr == 0)?
  2616.           LoadFarStringSmall2(None) : envptr));
  2617. #ifndef __RSXNT__
  2618. #ifdef __EMX__
  2619.         envptr = getenv(LoadFarStringSmall(EnvEMX));
  2620.         Info(slide, 0, ((char *)slide, LoadFarString(EnvOptFormat),
  2621.           LoadFarStringSmall(EnvEMX),
  2622.           (envptr == (char *)NULL || *envptr == 0)?
  2623.           LoadFarStringSmall2(None) : envptr));
  2624.         envptr = getenv(LoadFarStringSmall(EnvEMXOPT));
  2625.         Info(slide, 0, ((char *)slide, LoadFarString(EnvOptFormat),
  2626.           LoadFarStringSmall(EnvEMXOPT),
  2627.           (envptr == (char *)NULL || *envptr == 0)?
  2628.           LoadFarStringSmall2(None) : envptr));
  2629. #endif /* __EMX__ */
  2630. #if (defined(__GO32__) && (!defined(__DJGPP__) || (__DJGPP__ < 2)))
  2631.         envptr = getenv(LoadFarStringSmall(EnvGO32));
  2632.         Info(slide, 0, ((char *)slide, LoadFarString(EnvOptFormat),
  2633.           LoadFarStringSmall(EnvGO32),
  2634.           (envptr == (char *)NULL || *envptr == 0)?
  2635.           LoadFarStringSmall2(None) : envptr));
  2636.         envptr = getenv(LoadFarStringSmall(EnvGO32TMP));
  2637.         Info(slide, 0, ((char *)slide, LoadFarString(EnvOptFormat),
  2638.           LoadFarStringSmall(EnvGO32TMP),
  2639.           (envptr == (char *)NULL || *envptr == 0)?
  2640.           LoadFarStringSmall2(None) : envptr));
  2641. #endif /* __GO32__ && !(__DJGPP__ >= 2) */
  2642. #endif /* !__RSXNT__ */
  2643. #ifdef RISCOS
  2644.         envptr = getenv(LoadFarStringSmall(EnvUnZipExts));
  2645.         Info(slide, 0, ((char *)slide, LoadFarString(EnvOptFormat),
  2646.           LoadFarStringSmall(EnvUnZipExts),
  2647.           (envptr == (char *)NULL || *envptr == 0)?
  2648.           LoadFarStringSmall2(None) : envptr));
  2649. #endif /* RISCOS */
  2650. #endif /* !_WIN32_WCE */
  2651.     }
  2652. } /* end function show_version() */
  2653.  
  2654. #endif /* !SFX */
  2655. #endif /* !WINDLL */
  2656.