home *** CD-ROM | disk | FTP | other *** search
/ OS/2 Shareware BBS: 9 Archive / 09-Archive.zip / unzip540.zip / windll / example.c < prev    next >
C/C++ Source or Header  |  1998-11-02  |  11KB  |  400 lines

  1. /*
  2.    This is a very simplistic example of how to load and make a call into the
  3.    dll. This has been compiled and tested for a 32-bit console version, but
  4.    not under 16-bit windows. However, the #ifdef's have been left in for the
  5.    16-bit code, simply as an example.
  6.  
  7.  */
  8.  
  9. #ifndef WIN32   /* this code is currently only tested for 32-bit console */
  10. #  define WIN32
  11. #endif
  12.  
  13. #if defined(__WIN32__) && !defined(WIN32)
  14. #  define WIN32
  15. #endif
  16.  
  17. #include <sys/types.h>
  18. #include <sys/stat.h>
  19. #include <time.h>
  20. #include <string.h>
  21. #include "example.h"
  22. #include "unzver.h"
  23. #ifdef WIN32
  24. #  ifdef __RSXNT__
  25. #    include <winversi.h>
  26. #  else
  27. #    include <winver.h>
  28. #  endif
  29. #else
  30. #  include <ver.h>
  31. #endif
  32.  
  33. #ifdef WIN32
  34. #define UNZ_DLL_NAME "UNZIP32.DLL\0"
  35. #else
  36. #define UNZ_DLL_NAME "UNZIP16.DLL\0"
  37. #endif
  38.  
  39. #define DLL_WARNING "Cannot find %s."\
  40.             " The Dll must be in the application directory, the path, "\
  41.             "the Windows directory or the Windows System directory."
  42. #define DLL_VERSION_WARNING "%s has the wrong version number."\
  43.             " Insure that you have the correct dll's installed, and that "\
  44.             "an older dll is not in your path or Windows System directory."
  45.  
  46. int hFile;              /* file handle */
  47.  
  48. LPUSERFUNCTIONS lpUserFunctions;
  49. HANDLE hUF = (HANDLE)NULL;
  50. LPDCL lpDCL = NULL;
  51. HANDLE hDCL = (HANDLE)NULL;
  52. HINSTANCE hUnzipDll;
  53. HANDLE hZCL = (HANDLE)NULL;
  54. #ifdef WIN32
  55. DWORD dwPlatformId = 0xFFFFFFFF;
  56. #endif
  57.  
  58.  
  59. /* Forward References */
  60. int WINAPI DisplayBuf(LPSTR, unsigned long);
  61. int WINAPI GetReplaceDlgRetVal(char *);
  62. int WINAPI password(char *, int, const char *, const char *);
  63. void WINAPI ReceiveDllMessage(unsigned long, unsigned long, unsigned,
  64.     unsigned, unsigned, unsigned, unsigned, unsigned,
  65.     char, LPSTR, LPSTR, unsigned long, char);
  66. _DLL_UNZIP Wiz_SingleEntryUnzip;
  67. _USER_FUNCTIONS Wiz_Init;
  68. void FreeUpMemory(void);
  69. #ifdef WIN32
  70. BOOL IsNT(VOID);
  71. #endif
  72.  
  73. int main(int argc, char **argv)
  74. {
  75. int exfc, infc;
  76. char **exfv, **infv;
  77. char *x_opt;
  78. DWORD dwVerInfoSize;
  79. DWORD dwVerHnd;
  80. char szFullPath[PATH_MAX];
  81. int retcode;
  82. #ifdef WIN32
  83. char *ptr;
  84. #else
  85. HFILE hfile;
  86. OFSTRUCT ofs;
  87. #endif
  88. HANDLE  hMem;         /* handle to mem alloc'ed */
  89.  
  90. if (argc < 2)   /* We must have an archive to unzip */
  91.    {
  92.    printf("usage: %s <zipfile> [entry1 [entry2 [...]]] [-x xentry1 [...]]",
  93.           "example");
  94.    return 0;
  95.    }
  96.  
  97. hDCL = GlobalAlloc( GPTR, (DWORD)sizeof(DCL));
  98. if (!hDCL)
  99.    {
  100.    return 0;
  101.    }
  102. lpDCL = (LPDCL)GlobalLock(hDCL);
  103. if (!lpDCL)
  104.    {
  105.    GlobalFree(hDCL);
  106.    return 0;
  107.    }
  108.  
  109. hUF = GlobalAlloc( GPTR, (DWORD)sizeof(USERFUNCTIONS));
  110. if (!hUF)
  111.    {
  112.    GlobalUnlock(hDCL);
  113.    GlobalFree(hDCL);
  114.    return 0;
  115.    }
  116. lpUserFunctions = (LPUSERFUNCTIONS)GlobalLock(hUF);
  117.  
  118. if (!lpUserFunctions)
  119.    {
  120.    GlobalUnlock(hDCL);
  121.    GlobalFree(hDCL);
  122.    GlobalFree(hUF);
  123.    return 0;
  124.    }
  125.  
  126. lpUserFunctions->password = password;
  127. lpUserFunctions->print = DisplayBuf;
  128. lpUserFunctions->sound = NULL;
  129. lpUserFunctions->replace = GetReplaceDlgRetVal;
  130. lpUserFunctions->SendApplicationMessage = ReceiveDllMessage;
  131.  
  132. /* First we go look for the unzip dll */
  133. #ifdef WIN32
  134. if (SearchPath(
  135.     NULL,               /* address of search path               */
  136.     UNZ_DLL_NAME,       /* address of filename                  */
  137.     NULL,               /* address of extension                 */
  138.     PATH_MAX,           /* size, in characters, of buffer       */
  139.     szFullPath,         /* address of buffer for found filename */
  140.     &ptr                /* address of pointer to file component */
  141.    ) == 0)
  142. #else
  143. hfile = OpenFile(UNZ_DLL_NAME,  &ofs, OF_SEARCH);
  144. if (hfile == HFILE_ERROR)
  145. #endif
  146.    {
  147.    char str[256];
  148.    wsprintf (str, DLL_WARNING, UNZ_DLL_NAME);
  149.    printf("%s\n", str);
  150.    FreeUpMemory();
  151.    return 0;
  152.    }
  153. #ifndef WIN32
  154. else
  155.    lstrcpy(szFullPath, ofs.szPathName);
  156. _lclose(hfile);
  157. #endif
  158.  
  159. /* Now we'll check the unzip dll version information. Note that this is
  160.    not the same information as is returned from a call to UzpVersion()
  161.  */
  162. dwVerInfoSize =
  163.     GetFileVersionInfoSize(szFullPath, &dwVerHnd);
  164.  
  165. if (dwVerInfoSize)
  166.    {
  167.    BOOL  fRet, fRetName;
  168.    char str[256];
  169.    LPSTR   lpstrVffInfo; /* Pointer to block to hold info */
  170.    LPSTR lszVer = NULL;
  171.    LPSTR lszVerName = NULL;
  172. #ifdef __RSXNT__
  173.    ULONG cchVer = 0;
  174. #else
  175.    UINT  cchVer = 0;
  176. #endif
  177.  
  178.    /* Get a block big enough to hold the version information */
  179.    hMem          = GlobalAlloc(GMEM_MOVEABLE, dwVerInfoSize);
  180.    lpstrVffInfo  = GlobalLock(hMem);
  181.  
  182.    /* Get the version information */
  183.    if (GetFileVersionInfo(szFullPath, 0L, dwVerInfoSize, lpstrVffInfo))
  184.       {
  185.       fRet = VerQueryValue(lpstrVffInfo,
  186.                TEXT("\\StringFileInfo\\040904E4\\FileVersion"),
  187.               (LPVOID)&lszVer,
  188.               &cchVer);
  189.       fRetName = VerQueryValue(lpstrVffInfo,
  190.                TEXT("\\StringFileInfo\\040904E4\\CompanyName"),
  191.                (LPVOID)&lszVerName,
  192.                &cchVer);
  193.       if (!fRet || !fRetName ||
  194.          (lstrcmpi(lszVer, UNZ_DLL_VERSION) != 0) ||
  195.          (lstrcmpi(lszVerName, COMPANY_NAME) != 0))
  196.          {
  197.          wsprintf (str, DLL_VERSION_WARNING, UNZ_DLL_NAME);
  198.          printf("%s\n", str);
  199.          FreeUpMemory();
  200.          GlobalUnlock(hMem);
  201.          GlobalFree(hMem);
  202.          return 0;
  203.          }
  204.       }
  205.       /* free memory */
  206.    GlobalUnlock(hMem);
  207.    GlobalFree(hMem);
  208.    }
  209. else
  210.    {
  211.    char str[256];
  212.    wsprintf (str, DLL_VERSION_WARNING, UNZ_DLL_NAME);
  213.    printf("%s\n", str);
  214.    FreeUpMemory();
  215.    return 0;
  216.    }
  217. /* Okay, now we know that the dll exists, and has the proper version
  218.  * information in it. We can go ahead and load it.
  219.  */
  220. hUnzipDll = LoadLibrary(UNZ_DLL_NAME);
  221. #ifndef WIN32
  222. if (hUnzipDll > HINSTANCE_ERROR)
  223. #else
  224. if (hUnzipDll != NULL)
  225. #endif
  226.    {
  227.    (_DLL_UNZIP)Wiz_SingleEntryUnzip =
  228.      (_DLL_UNZIP)GetProcAddress(hUnzipDll, "Wiz_SingleEntryUnzip");
  229.    }
  230. else
  231.    {
  232.    char str[256];
  233.    wsprintf (str, "Could not load %s", UNZ_DLL_NAME);
  234.    printf("%s\n", str);
  235.    FreeUpMemory();
  236.    return 0;
  237.    }
  238.  
  239. /*
  240.    Here is where the actual extraction process begins. First we set up the
  241.    flags to be passed into the dll.
  242.  */
  243. lpDCL->ncflag = 0; /* Write to stdout if true */
  244. lpDCL->fQuiet = 0; /* We want all messages.
  245.                       1 = fewer messages,
  246.                       2 = no messages */
  247. lpDCL->ntflag = 0; /* test zip file if true */
  248. lpDCL->nvflag = 0; /* give a verbose listing if true */
  249. lpDCL->nUflag = 0; /* Do not extract only newer */
  250. lpDCL->nzflag = 0; /* display a zip file comment if true */
  251. lpDCL->ndflag = 1; /* Recreate directories if true */
  252. lpDCL->noflag = 1; /* Over-write all files if true */
  253. lpDCL->naflag = 0; /* Do not convert CR to CRLF */
  254. lpDCL->lpszZipFN = argv[1]; /* The archive name */
  255. lpDCL->lpszExtractDir = NULL; /* The directory to extract to. This is set
  256.                                  to NULL if you are extracting to the
  257.                                  current directory.
  258.                                */
  259. /*
  260.    As this is a quite short example, intended primarily to show how to
  261.    load and call in to the dll, the command-line parameters are only
  262.    parsed in a very simplistic way:
  263.    We assume that the command-line parameters after the zip archive
  264.    make up a list of file patterns:
  265.    " [file_i1] [file_i2] ... [file_iN] [-x file_x1 [file_x2] ...]".
  266.    We scan for an argument "-x"; all arguments in front are
  267.    "include file patterns", all arguments after are "exclude file patterns".
  268.    If no more arguments are given, we extract ALL files.
  269.  
  270.    In summary, the example program should be run like:
  271.    example <archive.name> [files to include] [-x files to exclude]
  272.    ("<...> denotes mandatory arguments, "[...]" optional arguments)
  273.  */
  274. x_opt = NULL;
  275. if (argc > 2) {
  276.   infv = &argv[2];
  277.   for (infc = 0; infc < argc-2; infc++)
  278.     if (!strcmp("-x", infv[infc])) {
  279.         x_opt = infv[infc];
  280.         infv[infc] = NULL;
  281.         break;
  282.     }
  283.   exfc = argc - infc - 3;
  284.   if (exfc > 0)
  285.     exfv = &argv[infc+3];
  286.   else {
  287.     exfc = 0;
  288.     exfv = NULL;
  289.   }
  290. } else {
  291.   infc = exfc = 0;
  292.   infv = exfv = NULL;
  293. }
  294. retcode = (*Wiz_SingleEntryUnzip)(infc, infv, exfc, exfv, lpDCL,
  295.                                   lpUserFunctions);
  296. if (x_opt) {
  297.   infv[infc] = x_opt;
  298.   x_opt = NULL;
  299. }
  300.  
  301. if (retcode != 0)
  302.    printf("Error unzipping...\n");
  303.  
  304. FreeUpMemory();
  305. FreeLibrary(hUnzipDll);
  306. return 1;
  307. }
  308.  
  309. int WINAPI GetReplaceDlgRetVal(char *filename)
  310. {
  311. /* This is where you will decide if you want to replace, rename etc existing
  312.    files.
  313.  */
  314. return 1;
  315. }
  316.  
  317. void FreeUpMemory(void)
  318. {
  319. if (hDCL)
  320.    {
  321.    GlobalUnlock(hDCL);
  322.    GlobalFree(hDCL);
  323.    }
  324. if (hUF)
  325.    {
  326.    GlobalUnlock(hUF);
  327.    GlobalFree(hUF);
  328.    }
  329. }
  330.  
  331. /* This simply determines if we are running on NT or Windows 95 */
  332. #ifdef WIN32
  333. BOOL IsNT(VOID)
  334. {
  335. if(dwPlatformId != 0xFFFFFFFF)
  336.    return dwPlatformId;
  337. else
  338. /* note: GetVersionEx() doesn't exist on WinNT 3.1 */
  339.    {
  340.    if(GetVersion() < 0x80000000)
  341.       {
  342.       (BOOL)dwPlatformId = TRUE;
  343.       }
  344.    else
  345.       {
  346.       (BOOL)dwPlatformId = FALSE;
  347.       }
  348.     }
  349. return dwPlatformId;
  350. }
  351. #endif
  352.  
  353. /* This is a very stripped down version of what is done in Wiz. Essentially
  354.    what this function is for is to do a listing of an archive contents. It
  355.    is actually never called in this example, but a dummy procedure had to
  356.    be put in, so this was used.
  357.  */
  358. void WINAPI ReceiveDllMessage(unsigned long ucsize, unsigned long csiz,
  359.     unsigned cfactor,
  360.     unsigned mo, unsigned dy, unsigned yr, unsigned hh, unsigned mm,
  361.     char c, LPSTR filename, LPSTR methbuf, unsigned long crc, char fCrypt)
  362. {
  363. char psLBEntry[PATH_MAX];
  364. char LongHdrStats[] =
  365.           "%7lu  %7lu %4s  %02u-%02u-%02u  %02u:%02u  %c%s";
  366. char CompFactorStr[] = "%c%d%%";
  367. char CompFactor100[] = "100%%";
  368. char szCompFactor[10];
  369. char sgn;
  370.  
  371. if (csiz > ucsize)
  372.    sgn = '-';
  373. else
  374.    sgn = ' ';
  375. if (cfactor == 100)
  376.    lstrcpy(szCompFactor, CompFactor100);
  377. else
  378.    sprintf(szCompFactor, CompFactorStr, sgn, cfactor);
  379.    wsprintf(psLBEntry, LongHdrStats,
  380.       ucsize, csiz, szCompFactor, mo, dy, yr, hh, mm, c, filename);
  381.  
  382. printf("%s\n", psLBEntry);
  383. }
  384.  
  385. /* Password entry routine - see password.c in the wiz directory for how
  386.    this is actually implemented in WiZ. If you have an encrypted file,
  387.    this will probably give you great pain.
  388.  */
  389. int WINAPI password(char *p, int n, const char *m, const char *name)
  390. {
  391. return 1;
  392. }
  393.  
  394. /* Dummy "print" routine that simply outputs what is sent from the dll */
  395. int WINAPI DisplayBuf(LPSTR buf, unsigned long size)
  396. {
  397. printf("%s", (char *)buf);
  398. return (unsigned int) size;
  399. }
  400.