|
|
/*++
Copyright (c) 1999 Microsoft Corporation
Module Name:
cablib.c
Abstract:
Implements wrappers for cabinet APIs
Author:
Calin Negreanu (calinn) 27-Apr-2000
Revision History:
<alias> <date> <comments>
--*/
#include "pch.h"
#include <cablib.h>
#include <fci.h>
#include <fdi.h>
#include <fcntl.h>
#include <crt\sys\stat.h>
//
// Includes
//
// None
#define DBG_CABLIB "CabLib"
//
// Strings
//
// None
//
// Constants
//
#define VERIFY_HANDLE ((HANDLE) (-2))
//
// Macros
//
// None
//
// Types
//
typedef struct { PCSTR CabPath; PCSTR CabFileFormat; PCSTR CabDiskFormat; PCABGETCABINETNAMESA CabGetCabinetNames; HFCI FciHandle; ERF FciErrorStruct; CCAB FciCabParams; UINT FileCount; UINT CabCount; LONGLONG FileSize; LONGLONG CompressedSize; } FCI_CAB_HANDLEA, *PFCI_CAB_HANDLEA;
typedef struct { PCWSTR CabPath; PCWSTR CabFileFormat; PCWSTR CabDiskFormat; PCABGETCABINETNAMESW CabGetCabinetNames; HFCI FciHandle; ERF FciErrorStruct; CCAB FciCabParams; UINT FileCount; UINT CabCount; LONGLONG FileSize; LONGLONG CompressedSize; } FCI_CAB_HANDLEW, *PFCI_CAB_HANDLEW;
typedef struct { PCSTR CabPath; PCSTR CabFile; HFDI FdiHandle; ERF FdiErrorStruct; FDICABINETINFO FdiCabinetInfo; } FDI_CAB_HANDLEA, *PFDI_CAB_HANDLEA;
typedef struct { PCWSTR CabPath; PCWSTR CabFile; HFDI FdiHandle; ERF FdiErrorStruct; FDICABINETINFO FdiCabinetInfo; } FDI_CAB_HANDLEW, *PFDI_CAB_HANDLEW;
typedef struct { PCSTR ExtractPath; PCABNOTIFICATIONA CabNotificationA; } CAB_DATAA, *PCAB_DATAA;
typedef struct { PCWSTR ExtractPath; PCABNOTIFICATIONW CabNotificationW; BOOL VerifyMode; } CAB_DATAW, *PCAB_DATAW;
//
// Globals
//
// None
//
// Macro expansion list
//
// None
//
// Private function prototypes
//
// None
//
// Macro expansion definition
//
// None
//
// Code
//
INT DIAMONDAPI pCabFilePlacedA ( IN PCCAB FciCabParams, IN PSTR FileName, IN LONG FileSize, IN BOOL Continuation, IN PVOID Context )
/*++
Routine Description:
Callback for cabinet compression/decompression. For more information see fci.h/fdi.h
--*/
{ PFCI_CAB_HANDLEA cabHandle;
cabHandle = (PFCI_CAB_HANDLEA) Context; if (!cabHandle) { return 0; }
cabHandle->FileCount++; cabHandle->FileSize += FileSize;
return 0; }
INT DIAMONDAPI pCabFilePlacedW ( IN PCCAB FciCabParams, IN PSTR FileName, IN LONG FileSize, IN BOOL Continuation, IN PVOID Context )
/*++
Routine Description:
Callback for cabinet compression/decompression. For more information see fci.h/fdi.h
--*/
{ PFCI_CAB_HANDLEW cabHandle;
cabHandle = (PFCI_CAB_HANDLEW) Context; if (!cabHandle) { return 0; }
cabHandle->FileCount++; cabHandle->FileSize += FileSize;
return 0; }
PVOID DIAMONDAPI pCabAlloc ( IN ULONG Size )
/*++
Routine Description:
Callback for cabinet compression/decompression. For more information see fci.h/fdi.h
--*/
{ return MemAlloc (g_hHeap, 0, Size); }
VOID DIAMONDAPI pCabFree ( IN PVOID Memory )
/*++
Routine Description:
Callback for cabinet compression/decompression. For more information see fci.h/fdi.h
--*/
{ MemFree (g_hHeap, 0, Memory); }
INT_PTR DIAMONDAPI pCabOpenA ( IN PSTR FileName, IN INT oFlag, IN INT pMode, OUT PINT Error, IN PVOID Context )
/*++
Routine Description:
Callback for cabinet compression/decompression. For more information see fci.h/fdi.h
--*/
{ HANDLE fileHandle;
// oFlag and pMode are prepared for using _open. We won't do that
// and it's a terrible waste of time to check each individual flags
// We'll just assert these values.
MYASSERT ((oFlag == (_O_CREAT | _O_TRUNC | _O_BINARY | _O_RDWR)) || (oFlag == (_O_CREAT | _O_EXCL | _O_BINARY | _O_RDWR))); MYASSERT (pMode == (_S_IREAD | _S_IWRITE));
fileHandle = CreateFileA ( FileName, GENERIC_READ | GENERIC_WRITE, 0, NULL, CREATE_ALWAYS, FILE_ATTRIBUTE_ARCHIVE, NULL ); if (fileHandle == INVALID_HANDLE_VALUE) { *Error = GetLastError (); return -1; } *Error = 0; return (INT_PTR)fileHandle; }
INT_PTR DIAMONDAPI pCabOpen1A ( IN PSTR FileName, IN INT oFlag, IN INT pMode )
/*++
Routine Description:
Callback for cabinet compression/decompression. For more information see fci.h/fdi.h
--*/
{ HANDLE fileHandle;
// oFlag and pMode are prepared for using _open. We won't do that
// and it's a terrible waste of time to check each individual flags
// We'll just assert these values.
MYASSERT (oFlag == _O_BINARY);
fileHandle = CreateFileA ( FileName, GENERIC_READ, FILE_SHARE_READ, NULL, OPEN_EXISTING, FILE_ATTRIBUTE_ARCHIVE, NULL ); if (fileHandle == INVALID_HANDLE_VALUE) { return -1; } return (INT_PTR)fileHandle; }
UINT DIAMONDAPI pCabRead ( IN INT_PTR FileHandle, IN PVOID Buffer, IN UINT Size, OUT PINT Error, IN PVOID Context )
/*++
Routine Description:
Callback for cabinet compression/decompression. For more information see fci.h/fdi.h
--*/
{ BOOL result; UINT bytesRead;
result = ReadFile ((HANDLE)FileHandle, Buffer, Size, &bytesRead, NULL); if (!result) { *Error = GetLastError (); return ((UINT)(-1)); } *Error = 0; return bytesRead; }
UINT DIAMONDAPI pCabRead1 ( IN INT_PTR FileHandle, IN PVOID Buffer, IN UINT Size )
/*++
Routine Description:
Callback for cabinet compression/decompression. For more information see fci.h/fdi.h
--*/
{ BOOL result; UINT bytesRead;
result = ReadFile ((HANDLE)FileHandle, Buffer, Size, &bytesRead, NULL); if (!result) { return ((UINT)(-1)); } return bytesRead; }
UINT DIAMONDAPI pCabWrite ( IN INT_PTR FileHandle, IN PVOID Buffer, IN UINT Size, OUT PINT Error, IN PVOID Context )
/*++
Routine Description:
Callback for cabinet compression/decompression. For more information see fci.h/fdi.h
--*/
{ BOOL result; DWORD dontCare;
if (FileHandle == (INT_PTR) VERIFY_HANDLE) { return Size; }
result = WriteFile ((HANDLE)FileHandle, Buffer, Size, &dontCare, NULL); if (!result) { *Error = GetLastError (); return ((UINT)(-1)); } *Error = 0; return Size; }
UINT DIAMONDAPI pCabWrite1 ( IN INT_PTR FileHandle, IN PVOID Buffer, IN UINT Size )
/*++
Routine Description:
Callback for cabinet compression/decompression. For more information see fci.h/fdi.h
--*/
{ BOOL result; DWORD dontCare;
if (FileHandle == (INT_PTR) VERIFY_HANDLE) { return Size; }
result = WriteFile ((HANDLE)FileHandle, Buffer, Size, &dontCare, NULL); if (!result) { return ((UINT)(-1)); } return Size; }
INT DIAMONDAPI pCabClose ( IN INT_PTR FileHandle, OUT PINT Error, IN PVOID Context )
/*++
Routine Description:
Callback for cabinet compression/decompression. For more information see fci.h/fdi.h
--*/
{ CloseHandle ((HANDLE)FileHandle); *Error = 0; return 0; }
INT DIAMONDAPI pCabClose1 ( IN INT_PTR FileHandle )
/*++
Routine Description:
Callback for cabinet compression/decompression. For more information see fci.h/fdi.h
--*/
{ CloseHandle ((HANDLE)FileHandle); return 0; }
LONG DIAMONDAPI pCabSeek ( IN INT_PTR FileHandle, IN LONG Distance, IN INT SeekType, OUT PINT Error, IN PVOID Context )
/*++
Routine Description:
Callback for cabinet compression/decompression. For more information see fci.h/fdi.h
--*/
{ DWORD result; DWORD seekType = FILE_BEGIN;
switch (SeekType) { case SEEK_SET: seekType = FILE_BEGIN; break; case SEEK_CUR: seekType = FILE_CURRENT; break; case SEEK_END: seekType = FILE_END; break; }
result = SetFilePointer ((HANDLE)FileHandle, Distance, NULL, seekType);
if (result == INVALID_SET_FILE_POINTER) { *Error = GetLastError (); return -1; } *Error = 0; return ((LONG)(result)); }
LONG DIAMONDAPI pCabSeek1 ( IN INT_PTR FileHandle, IN LONG Distance, IN INT SeekType )
/*++
Routine Description:
Callback for cabinet compression/decompression. For more information see fci.h/fdi.h
--*/
{ DWORD result; DWORD seekType = FILE_BEGIN;
switch (SeekType) { case SEEK_SET: seekType = FILE_BEGIN; break; case SEEK_CUR: seekType = FILE_CURRENT; break; case SEEK_END: seekType = FILE_END; break; }
result = SetFilePointer ((HANDLE)FileHandle, Distance, NULL, seekType);
if (result == INVALID_SET_FILE_POINTER) { return -1; } return ((LONG)(result)); }
INT DIAMONDAPI pCabDeleteA ( IN PSTR FileName, OUT PINT Error, IN PVOID Context )
/*++
Routine Description:
Callback for cabinet compression/decompression. For more information see fci.h/fdi.h
--*/
{ if (!DeleteFileA (FileName)) { *Error = GetLastError (); return -1; } *Error = 0; return 0; }
BOOL DIAMONDAPI pCabGetTempFileA ( OUT PSTR FileName, IN INT FileNameLen, IN PVOID Context )
/*++
Routine Description:
Callback for cabinet compression/decompression. For more information see fci.h/fdi.h
--*/
{ CHAR tempPath[MAX_PATH]; PSTR p;
if (!GetTempPathA (ARRAYSIZE(tempPath), tempPath)) { return FALSE; }
p = _mbsrchr (tempPath, '\\'); if (p && !p[1]) { *p = 0; }
if (!DoesFileExistA (tempPath)) { CreateDirectoryA (tempPath, NULL); }
if (!GetTempFileNameA (tempPath, "cab", 0, FileName)) { return FALSE; }
return TRUE; }
BOOL DIAMONDAPI pCabGetNextCabinetA ( IN PCCAB FciCabParams, IN ULONG PrevCabinetSize, IN PVOID Context )
/*++
Routine Description:
Callback for cabinet compression/decompression. For more information see fci.h/fdi.h
--*/
{ PFCI_CAB_HANDLEA cabHandle; CHAR cabFile [1024]; CHAR cabDisk [1024];
cabHandle = (PFCI_CAB_HANDLEA) Context; if (!cabHandle) { return FALSE; } if (cabHandle->CabGetCabinetNames) { return cabHandle->CabGetCabinetNames ( FciCabParams->szCabPath, CB_MAX_CAB_PATH, FciCabParams->szCab, CB_MAX_CABINET_NAME, FciCabParams->szDisk, CB_MAX_DISK_NAME, FciCabParams->iCab, &FciCabParams->iDisk ); } else { FciCabParams->iDisk = FciCabParams->iCab; if (cabHandle->CabFileFormat) { wsprintfA (cabFile, cabHandle->CabFileFormat, FciCabParams->iCab); StringCopyByteCountA (FciCabParams->szCab, cabFile, CB_MAX_CABINET_NAME * sizeof (CHAR)); } if (cabHandle->CabDiskFormat) { wsprintfA (cabDisk, cabHandle->CabDiskFormat, FciCabParams->iDisk); StringCopyByteCountA (FciCabParams->szDisk, cabDisk, CB_MAX_DISK_NAME * sizeof (CHAR)); } } return TRUE; }
BOOL DIAMONDAPI pCabGetNextCabinetW ( IN PCCAB FciCabParams, IN ULONG PrevCabinetSize, IN PVOID Context )
/*++
Routine Description:
Callback for cabinet compression/decompression. For more information see fci.h/fdi.h
--*/
{ PFCI_CAB_HANDLEW cabHandle; WCHAR cabPath [1024]; WCHAR cabFile [1024]; WCHAR cabDisk [1024]; BOOL result;
cabHandle = (PFCI_CAB_HANDLEW) Context; if (!cabHandle) { return FALSE; } if (cabHandle->CabGetCabinetNames) { result = cabHandle->CabGetCabinetNames ( cabPath, CB_MAX_CAB_PATH, cabFile, CB_MAX_CABINET_NAME, cabDisk, CB_MAX_DISK_NAME, FciCabParams->iCab, &FciCabParams->iDisk ); if (result) { KnownSizeUnicodeToDbcs (FciCabParams->szCabPath, cabPath); KnownSizeUnicodeToDbcs (FciCabParams->szCab, cabFile); KnownSizeUnicodeToDbcs (FciCabParams->szDisk, cabDisk); return TRUE; } return FALSE; } else { FciCabParams->iDisk = FciCabParams->iCab; if (cabHandle->CabFileFormat) { wsprintfW (cabFile, cabHandle->CabFileFormat, FciCabParams->iCab); KnownSizeUnicodeToDbcs (FciCabParams->szCab, cabFile); } if (cabHandle->CabDiskFormat) { wsprintfW (cabDisk, cabHandle->CabDiskFormat, FciCabParams->iDisk); KnownSizeUnicodeToDbcs (FciCabParams->szDisk, cabDisk); } } return TRUE; }
LONG DIAMONDAPI pCabStatusA ( IN UINT StatusType, IN ULONG Size1, IN ULONG Size2, IN PVOID Context )
/*++
Routine Description:
Callback for cabinet compression/decompression. For more information see fci.h/fdi.h
--*/
{ PFCI_CAB_HANDLEA cabHandle;
if (StatusType == statusCabinet) {
cabHandle = (PFCI_CAB_HANDLEA) Context; if (!cabHandle) { return 0; }
cabHandle->CabCount++; cabHandle->CompressedSize += (LONGLONG) Size2; }
return 0; }
LONG DIAMONDAPI pCabStatusW ( IN UINT StatusType, IN ULONG Size1, IN ULONG Size2, IN PVOID Context )
/*++
Routine Description:
Callback for cabinet compression/decompression. For more information see fci.h/fdi.h
--*/
{ PFCI_CAB_HANDLEW cabHandle;
if (StatusType == statusCabinet) {
cabHandle = (PFCI_CAB_HANDLEW) Context; if (!cabHandle) { return 0; }
cabHandle->CabCount++; cabHandle->CompressedSize += (LONGLONG) Size2; }
return 0; }
INT_PTR DIAMONDAPI pCabGetOpenInfoA ( IN PSTR FileName, OUT USHORT *Date, OUT USHORT *Time, OUT USHORT *Attributes, OUT PINT Error, IN PVOID Context )
/*++
Routine Description:
Callback for cabinet compression/decompression. For more information see fci.h/fdi.h
--*/
{ WIN32_FIND_DATAA findData; FILETIME fileTime; HANDLE fileHandle;
if (DoesFileExistExA (FileName, &findData)) {
FileTimeToLocalFileTime (&findData.ftLastWriteTime, &fileTime); FileTimeToDosDateTime (&fileTime, Date, Time);
/*
* Mask out all other bits except these four, since other * bits are used by the cabinet format to indicate a * special meaning. */ *Attributes = (USHORT) (findData.dwFileAttributes & (FILE_ATTRIBUTE_READONLY | FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN | FILE_ATTRIBUTE_ARCHIVE));
fileHandle = CreateFileA ( FileName, GENERIC_READ, FILE_SHARE_READ|FILE_SHARE_WRITE, NULL, OPEN_EXISTING, FILE_ATTRIBUTE_NORMAL, NULL ); if (fileHandle == INVALID_HANDLE_VALUE) { *Error = GetLastError (); return -1; } *Error = 0; return (INT_PTR)fileHandle; } else { *Error = GetLastError (); return -1; } }
BOOL pIsFullPathA ( IN PCSTR PathToTest ) { MBCHAR ch1; MBCHAR ch2;
ch1 = _mbsnextc (PathToTest); _mbsinc (PathToTest); ch2 = _mbsnextc (PathToTest);
if ((ch1 == '\\' && ch2 == '\\') || (isalpha (ch1) && ch2 == '\\') ) { return TRUE; }
return FALSE; }
BOOL pIsFullPathW ( IN PCWSTR PathToTest ) { WCHAR ch1; WCHAR ch2;
ch1 = *PathToTest++; ch2 = *PathToTest;
if ((ch1 == '\\' && ch2 == '\\') || (isalpha (ch1) && ch2 == '\\') ) { return TRUE; }
return FALSE; }
PCSTR pComputeDestPathA ( IN PCSTR ExtractPath, OPTIONAL IN PCSTR PathStoredInCab ) { PCSTR destFile;
//
// If ExtractPath is NULL, then use the path stored in the cab.
// If the path stored in the cab is a full path, use only the file name.
// Otherwise join ExtractPath with PathStoredInCab.
//
if (!ExtractPath) {
destFile = DuplicatePathStringA (PathStoredInCab, 0);
} else if (pIsFullPathA (PathStoredInCab)) {
destFile = JoinPathsA (ExtractPath, GetFileNameFromPathA (PathStoredInCab));
} else {
destFile = JoinPathsA (ExtractPath, PathStoredInCab);
}
return destFile; }
PCWSTR pComputeDestPathW ( IN PCWSTR ExtractPath, OPTIONAL IN PCWSTR PathStoredInCab ) { PCWSTR destFile;
//
// If ExtractPath is NULL, then use the path stored in the cab.
// If the path stored in the cab is a full path, use only the file name.
// Otherwise join ExtractPath with PathStoredInCab.
//
if (!ExtractPath) {
destFile = DuplicatePathStringW (PathStoredInCab, 0);
} else if (pIsFullPathW (PathStoredInCab)) {
destFile = JoinPathsW (ExtractPath, GetFileNameFromPathW (PathStoredInCab));
} else {
destFile = JoinPathsW (ExtractPath, PathStoredInCab);
}
return destFile; }
INT_PTR DIAMONDAPI pCabNotificationA ( IN FDINOTIFICATIONTYPE FdiNotificationType, IN OUT PFDINOTIFICATION FdiNotification )
/*++
Routine Description:
Callback for cabinet compression/decompression. For more information see fci.h/fdi.h
--*/
{ PCSTR destFile = NULL; HANDLE destHandle = NULL; DWORD attributes; FILETIME localFileTime; FILETIME fileTime; PCAB_DATAA cabData; INT createFlag;
switch (FdiNotificationType) { case fdintCABINET_INFO: // General information about cabinet
return 0; case fdintCOPY_FILE: // File to be copied
cabData = (PCAB_DATAA)FdiNotification->pv;
destFile = pComputeDestPathA (cabData->ExtractPath, FdiNotification->psz1); createFlag = TRUE;
if (cabData->CabNotificationA) { createFlag = cabData->CabNotificationA (destFile); }
if(-1 == createFlag){ FreePathStringA (destFile); return -1; }
if (createFlag) { MakeSurePathExistsA (FdiNotification->psz1, FALSE);
SetFileAttributesA (destFile, FILE_ATTRIBUTE_NORMAL); destHandle = CreateFileA ( destFile, GENERIC_READ|GENERIC_WRITE, 0, NULL, CREATE_ALWAYS, FILE_ATTRIBUTE_NORMAL, NULL ); } FreePathStringA (destFile); return (INT_PTR)destHandle; case fdintCLOSE_FILE_INFO: // close the file, set relevant info
cabData = (PCAB_DATAA)FdiNotification->pv; if (DosDateTimeToFileTime (FdiNotification->date, FdiNotification->time, &localFileTime)) { if (LocalFileTimeToFileTime (&localFileTime, &fileTime)) { SetFileTime ((HANDLE)FdiNotification->hf, &fileTime, &fileTime, &fileTime); } }
destFile = pComputeDestPathA (cabData->ExtractPath, FdiNotification->psz1);
CloseHandle ((HANDLE)FdiNotification->hf); attributes = (FdiNotification->attribs & (FILE_ATTRIBUTE_READONLY | FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN | FILE_ATTRIBUTE_ARCHIVE)); SetFileAttributesA (destFile, attributes); FreePathStringA (destFile); return TRUE; case fdintPARTIAL_FILE: // First file in cabinet is continuation
return 0; case fdintENUMERATE: // Enumeration status
return 0; case fdintNEXT_CABINET: // File continued to next cabinet
return 0; } return 0; }
INT_PTR DIAMONDAPI pCabNotificationW ( IN FDINOTIFICATIONTYPE FdiNotificationType, IN OUT PFDINOTIFICATION FdiNotification )
/*++
Routine Description:
Callback for cabinet compression/decompression. For more information see fci.h/fdi.h
--*/
{ PCWSTR destFile = NULL; HANDLE destHandle = NULL; DWORD attributes; FILETIME localFileTime; FILETIME fileTime; PCAB_DATAW cabData; INT createFlag; PCWSTR cabFileSpecW;
switch (FdiNotificationType) { case fdintCABINET_INFO: // General information about cabinet
return 0; case fdintCOPY_FILE: // File to be copied
cabFileSpecW = ConvertAtoW (FdiNotification->psz1); cabData = (PCAB_DATAW)FdiNotification->pv;
destFile = pComputeDestPathW (cabData->ExtractPath, cabFileSpecW);
FreeConvertedStr (cabFileSpecW); createFlag = TRUE;
if (cabData->CabNotificationW) { createFlag = cabData->CabNotificationW (destFile); }
if(-1 == createFlag){ FreePathStringW (destFile); return -1; }
if (createFlag) { if (!cabData->VerifyMode) { MakeSurePathExistsW (cabFileSpecW, FALSE);
SetFileAttributesW (destFile, FILE_ATTRIBUTE_NORMAL); destHandle = CreateFileW ( destFile, GENERIC_READ|GENERIC_WRITE, 0, NULL, CREATE_ALWAYS, FILE_ATTRIBUTE_NORMAL, NULL ); } else { destHandle = VERIFY_HANDLE; } }
FreePathStringW (destFile); return (INT_PTR)destHandle; case fdintCLOSE_FILE_INFO: // close the file, set relevant info
cabData = (PCAB_DATAW)FdiNotification->pv; if (DosDateTimeToFileTime (FdiNotification->date, FdiNotification->time, &localFileTime)) { if (LocalFileTimeToFileTime (&localFileTime, &fileTime)) { SetFileTime ((HANDLE)FdiNotification->hf, &fileTime, &fileTime, &fileTime); } }
cabFileSpecW = ConvertAtoW (FdiNotification->psz1); destFile = pComputeDestPathW (cabData->ExtractPath, cabFileSpecW); FreeConvertedStr (cabFileSpecW);
CloseHandle ((HANDLE)FdiNotification->hf); attributes = (FdiNotification->attribs & (FILE_ATTRIBUTE_READONLY | FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN | FILE_ATTRIBUTE_ARCHIVE)); SetFileAttributesW (destFile, attributes); FreePathStringW (destFile); return TRUE; case fdintPARTIAL_FILE: // First file in cabinet is continuation
return 0; case fdintENUMERATE: // Enumeration status
return 0; case fdintNEXT_CABINET: // File continued to next cabinet
return 0; } return 0; }
CCABHANDLE CabCreateCabinetA ( IN PCSTR CabPath, IN PCSTR CabFileFormat, IN PCSTR CabDiskFormat, IN LONG MaxFileSize )
/*++
Routine Description:
Creates a cabinet context. Caller may use this context for subsequent calls to CabAddFile.
Arguments:
CabPath - Specifies the path where the new cabinet file will be.
CabFileFormat - Specifies (as for wsprintf) the format of the cabinet file name.
CabDiskFormat - Specifies (as for wsprintf) the format of the cabinet disk name.
MaxFileSize - Specifies maximum size of the cabinet file (limited to 2GB). if 0 => 2GB
Return Value:
a valid CCABHANDLE if successful, NULL otherwise.
--*/
{ PFCI_CAB_HANDLEA cabHandle; CHAR cabFile [1024]; CHAR cabDisk [1024];
if (!CabFileFormat) { return NULL; }
if (MaxFileSize < 0) { return NULL; }
if (MaxFileSize == 0) { MaxFileSize = 0x7FFFFFFF; }
cabHandle = (PFCI_CAB_HANDLEA) MemAlloc (g_hHeap, 0, sizeof (FCI_CAB_HANDLEA)); ZeroMemory (cabHandle, sizeof (FCI_CAB_HANDLEA)); if (CabPath) { cabHandle->CabPath = DuplicatePathStringA (CabPath, 0); } cabHandle->CabFileFormat = DuplicatePathStringA (CabFileFormat, 0); if (CabDiskFormat) { cabHandle->CabDiskFormat = DuplicatePathStringA (CabDiskFormat, 0); }
// fill out the CCAB structure
cabHandle->FciCabParams.cb = MaxFileSize; cabHandle->FciCabParams.cbFolderThresh = MaxFileSize; cabHandle->FciCabParams.cbReserveCFHeader = 0; cabHandle->FciCabParams.cbReserveCFFolder = 0; cabHandle->FciCabParams.cbReserveCFData = 0; cabHandle->FciCabParams.iCab = 1; cabHandle->FciCabParams.iDisk = 1; cabHandle->FciCabParams.setID = 0; if (CabPath) { StringCopyByteCountA (cabHandle->FciCabParams.szCabPath, CabPath, CB_MAX_CAB_PATH - 1); AppendWackA (cabHandle->FciCabParams.szCabPath); } if (CabDiskFormat) { wsprintfA (cabDisk, CabDiskFormat, cabHandle->FciCabParams.iDisk); StringCopyByteCountA (cabHandle->FciCabParams.szDisk, cabDisk, CB_MAX_DISK_NAME * sizeof (CHAR)); } wsprintfA (cabFile, CabFileFormat, cabHandle->FciCabParams.iCab); StringCopyByteCountA (cabHandle->FciCabParams.szCab, cabFile, CB_MAX_CABINET_NAME * sizeof (CHAR));
cabHandle->FciHandle = FCICreate ( &cabHandle->FciErrorStruct, pCabFilePlacedA, pCabAlloc, pCabFree, pCabOpenA, pCabRead, pCabWrite, pCabClose, pCabSeek, pCabDeleteA, pCabGetTempFileA, &cabHandle->FciCabParams, cabHandle ); if (!cabHandle->FciHandle) { if (cabHandle->CabPath) { FreePathStringA (cabHandle->CabPath); } if (cabHandle->CabFileFormat) { FreePathStringA (cabHandle->CabFileFormat); } if (cabHandle->CabDiskFormat) { FreePathStringA (cabHandle->CabDiskFormat); } MemFree (g_hHeap, 0, cabHandle); return NULL; } return ((CCABHANDLE)(cabHandle)); }
CCABHANDLE CabCreateCabinetW ( IN PCWSTR CabPath, IN PCWSTR CabFileFormat, IN PCWSTR CabDiskFormat, IN LONG MaxFileSize )
/*++
Routine Description:
Creates a cabinet context. Caller may use this context for subsequent calls to CabAddFile.
Arguments:
CabPath - Specifies the path where the new cabinet file will be.
CabFileFormat - Specifies (as for wsprintf) the format of the cabinet file name.
CabDiskFormat - Specifies (as for wsprintf) the format of the cabinet disk name.
MaxFileSize - Specifies maximum size of the cabinet file (limited to 2GB). if 0 => 2GB
Return Value:
a valid CCABHANDLE if successful, NULL otherwise.
--*/
{ PFCI_CAB_HANDLEW cabHandle; WCHAR cabFile [1024]; WCHAR cabDisk [1024];
if (!CabFileFormat) { return NULL; }
if (MaxFileSize < 0) { return NULL; }
if (MaxFileSize == 0) { MaxFileSize = 0x7FFFFFFF; }
cabHandle = (PFCI_CAB_HANDLEW) MemAlloc (g_hHeap, 0, sizeof (FCI_CAB_HANDLEW)); ZeroMemory (cabHandle, sizeof (FCI_CAB_HANDLEW)); if (CabPath) { cabHandle->CabPath = DuplicatePathStringW (CabPath, 0); } cabHandle->CabFileFormat = DuplicatePathStringW (CabFileFormat, 0); if (CabDiskFormat) { cabHandle->CabDiskFormat = DuplicatePathStringW (CabDiskFormat, 0); }
// fill out the CCAB structure
cabHandle->FciCabParams.cb = MaxFileSize; cabHandle->FciCabParams.cbFolderThresh = MaxFileSize; cabHandle->FciCabParams.cbReserveCFHeader = 0; cabHandle->FciCabParams.cbReserveCFFolder = 0; cabHandle->FciCabParams.cbReserveCFData = 0; cabHandle->FciCabParams.iCab = 1; cabHandle->FciCabParams.iDisk = 1; cabHandle->FciCabParams.setID = 0; if (CabPath) { KnownSizeUnicodeToDbcs (cabHandle->FciCabParams.szCabPath, CabPath); AppendWackA (cabHandle->FciCabParams.szCabPath); } if (CabDiskFormat) { wsprintfW (cabDisk, CabDiskFormat, cabHandle->FciCabParams.iDisk); KnownSizeUnicodeToDbcs (cabHandle->FciCabParams.szDisk, cabDisk); } wsprintfW (cabFile, CabFileFormat, cabHandle->FciCabParams.iCab); KnownSizeUnicodeToDbcs (cabHandle->FciCabParams.szCab, cabFile);
cabHandle->FciHandle = FCICreate ( &cabHandle->FciErrorStruct, pCabFilePlacedW, pCabAlloc, pCabFree, pCabOpenA, pCabRead, pCabWrite, pCabClose, pCabSeek, pCabDeleteA, pCabGetTempFileA, &cabHandle->FciCabParams, cabHandle ); if (!cabHandle->FciHandle) { if (cabHandle->CabPath) { FreePathStringW (cabHandle->CabPath); } if (cabHandle->CabFileFormat) { FreePathStringW (cabHandle->CabFileFormat); } if (cabHandle->CabDiskFormat) { FreePathStringW (cabHandle->CabDiskFormat); } MemFree (g_hHeap, 0, cabHandle); return NULL; } return ((CCABHANDLE)(cabHandle)); }
CCABHANDLE CabCreateCabinetExA ( IN PCABGETCABINETNAMESA CabGetCabinetNames, IN LONG MaxFileSize )
/*++
Routine Description:
Creates a cabinet context. Caller may use this context for subsequent calls to CabAddFile.
Arguments:
CabGetCabinetNames - Specifies a callback used to decide cabinet path, cabinet name and disk name.
MaxFileSize - Specifies maximum size of the cabinet file (limited to 2GB). if 0 => 2GB
Return Value:
a valid CCABHANDLE if successful, NULL otherwise.
--*/
{ PFCI_CAB_HANDLEA cabHandle;
if (!CabGetCabinetNames) { return NULL; }
if (MaxFileSize < 0) { return NULL; }
if (MaxFileSize == 0) { MaxFileSize = 0x80000000; }
cabHandle = MemAlloc (g_hHeap, 0, sizeof (FCI_CAB_HANDLEA)); ZeroMemory (cabHandle, sizeof (FCI_CAB_HANDLEA)); cabHandle->CabGetCabinetNames = CabGetCabinetNames;
// fill out the CCAB structure
cabHandle->FciCabParams.cb = MaxFileSize; cabHandle->FciCabParams.cbFolderThresh = MaxFileSize; cabHandle->FciCabParams.cbReserveCFHeader = 0; cabHandle->FciCabParams.cbReserveCFFolder = 0; cabHandle->FciCabParams.cbReserveCFData = 0; cabHandle->FciCabParams.iCab = 1; cabHandle->FciCabParams.iDisk = 1; cabHandle->FciCabParams.setID = 0; if (!CabGetCabinetNames ( cabHandle->FciCabParams.szCabPath, CB_MAX_CAB_PATH, cabHandle->FciCabParams.szCab, CB_MAX_CABINET_NAME, cabHandle->FciCabParams.szDisk, CB_MAX_DISK_NAME, cabHandle->FciCabParams.iCab, &cabHandle->FciCabParams.iDisk )) { return NULL; } cabHandle->FciHandle = FCICreate ( &cabHandle->FciErrorStruct, pCabFilePlacedA, pCabAlloc, pCabFree, pCabOpenA, pCabRead, pCabWrite, pCabClose, pCabSeek, pCabDeleteA, pCabGetTempFileA, &cabHandle->FciCabParams, cabHandle ); if (!cabHandle->FciHandle) { if (cabHandle->CabPath) { FreePathStringA (cabHandle->CabPath); } if (cabHandle->CabFileFormat) { FreePathStringA (cabHandle->CabFileFormat); } if (cabHandle->CabDiskFormat) { FreePathStringA (cabHandle->CabDiskFormat); } MemFree (g_hHeap, 0, cabHandle); return NULL; } return ((CCABHANDLE)(cabHandle)); }
CCABHANDLE CabCreateCabinetExW ( IN PCABGETCABINETNAMESW CabGetCabinetNames, IN LONG MaxFileSize )
/*++
Routine Description:
Creates a cabinet context. Caller may use this context for subsequent calls to CabAddFile.
Arguments:
CabGetCabinetNames - Specifies a callback used to decide cabinet path, cabinet name and disk name.
MaxFileSize - Specifies maximum size of the cabinet file (limited to 2GB). if 0 => 2GB
Return Value:
a valid CCABHANDLE if successful, NULL otherwise.
--*/
{ PFCI_CAB_HANDLEW cabHandle; WCHAR cabPath [1024]; WCHAR cabFile [1024]; WCHAR cabDisk [1024];
if (!CabGetCabinetNames) { return NULL; }
if (MaxFileSize < 0) { return NULL; }
if (MaxFileSize == 0) { MaxFileSize = 0x80000000; }
cabHandle = MemAlloc (g_hHeap, 0, sizeof (FCI_CAB_HANDLEW)); ZeroMemory (cabHandle, sizeof (FCI_CAB_HANDLEW)); cabHandle->CabGetCabinetNames = CabGetCabinetNames;
// fill out the CCAB structure
cabHandle->FciCabParams.cb = MaxFileSize; cabHandle->FciCabParams.cbFolderThresh = MaxFileSize; cabHandle->FciCabParams.cbReserveCFHeader = 0; cabHandle->FciCabParams.cbReserveCFFolder = 0; cabHandle->FciCabParams.cbReserveCFData = 0; cabHandle->FciCabParams.iCab = 1; cabHandle->FciCabParams.iDisk = 1; cabHandle->FciCabParams.setID = 0; if (!CabGetCabinetNames ( cabPath, CB_MAX_CAB_PATH, cabFile, CB_MAX_CABINET_NAME, cabDisk, CB_MAX_DISK_NAME, cabHandle->FciCabParams.iCab, &cabHandle->FciCabParams.iDisk )) { return NULL; } KnownSizeUnicodeToDbcs (cabHandle->FciCabParams.szCabPath, cabPath); KnownSizeUnicodeToDbcs (cabHandle->FciCabParams.szCab, cabFile); KnownSizeUnicodeToDbcs (cabHandle->FciCabParams.szDisk, cabDisk); cabHandle->FciHandle = FCICreate ( &cabHandle->FciErrorStruct, pCabFilePlacedW, pCabAlloc, pCabFree, pCabOpenA, pCabRead, pCabWrite, pCabClose, pCabSeek, pCabDeleteA, pCabGetTempFileA, &cabHandle->FciCabParams, cabHandle ); if (!cabHandle->FciHandle) { if (cabHandle->CabPath) { FreePathStringW (cabHandle->CabPath); } if (cabHandle->CabFileFormat) { FreePathStringW (cabHandle->CabFileFormat); } if (cabHandle->CabDiskFormat) { FreePathStringW (cabHandle->CabDiskFormat); } MemFree (g_hHeap, 0, cabHandle); return NULL; } return ((CCABHANDLE)(cabHandle)); }
BOOL CabAddFileToCabinetA ( IN CCABHANDLE CabHandle, IN PCSTR FileName, IN PCSTR StoredName )
/*++
Routine Description:
Compresses and adds a file to a cabinet context.
Arguments:
CabHandle - Specifies cabinet context.
FileName - Specifies the file to be added.
StoredName - Specifies the name to be stored in the cabinet file.
Return Value:
TRUE if successful, FALSE otherwise.
--*/
{ PFCI_CAB_HANDLEA cabHandle;
cabHandle = (PFCI_CAB_HANDLEA) CabHandle; if (cabHandle == NULL) { return FALSE; } if (cabHandle->FciHandle == NULL) { return FALSE; }
return FCIAddFile ( cabHandle->FciHandle, (PSTR)FileName, (PSTR)StoredName, FALSE, pCabGetNextCabinetA, pCabStatusA, pCabGetOpenInfoA, tcompTYPE_MSZIP ); }
BOOL CabAddFileToCabinetW ( IN CCABHANDLE CabHandle, IN PCWSTR FileName, IN PCWSTR StoredName )
/*++
Routine Description:
Compresses and adds a file to a cabinet context.
Arguments:
CabHandle - Specifies cabinet context.
FileName - Specifies the file to be added.
StoredName - Specifies the name to be stored in the cabinet file.
FileCount - Specifies a count of files, receives the updated count when cabinet files are created
FileSize - Specifies the number of bytes used by the file, receives the updated size
Return Value:
TRUE if successful, FALSE otherwise.
--*/
{ PFCI_CAB_HANDLEW cabHandle; CHAR ansiFileName [1024]; CHAR ansiStoredName [1024];
cabHandle = (PFCI_CAB_HANDLEW) CabHandle; if (cabHandle == NULL) { return FALSE; } if (cabHandle->FciHandle == NULL) { return FALSE; } KnownSizeUnicodeToDbcs (ansiFileName, FileName); KnownSizeUnicodeToDbcs (ansiStoredName, StoredName);
return FCIAddFile ( cabHandle->FciHandle, ansiFileName, ansiStoredName, FALSE, pCabGetNextCabinetW, pCabStatusW, pCabGetOpenInfoA, tcompTYPE_MSZIP ); }
BOOL CabFlushAndCloseCabinetExA ( IN CCABHANDLE CabHandle, OUT PUINT FileCount, OPTIONAL OUT PLONGLONG FileSize, OPTIONAL OUT PUINT CabFileCount, OPTIONAL OUT PLONGLONG CabFileSize OPTIONAL )
/*++
Routine Description:
Completes a cabinet file and closes its context.
Arguments:
CabHandle - Specifies cabinet context.
FileCount - Receives the number of files added to the cab
FileSize - Receives the size of all files before compression
CabFileCount - Receives the number of cabinet files created
CabFileSize - Receives the size of all cabinet files
Return Value:
TRUE if successful, FALSE otherwise.
--*/
{ PFCI_CAB_HANDLEA cabHandle; BOOL result = FALSE;
cabHandle = (PFCI_CAB_HANDLEA) CabHandle; if (cabHandle == NULL) { return FALSE; } if (cabHandle->FciHandle == NULL) { return FALSE; } if (FCIFlushCabinet ( cabHandle->FciHandle, FALSE, pCabGetNextCabinetA, pCabStatusA )) { if (cabHandle->CabPath) { FreePathStringA (cabHandle->CabPath); } if (cabHandle->CabFileFormat) { FreePathStringA (cabHandle->CabFileFormat); } if (cabHandle->CabDiskFormat) { FreePathStringA (cabHandle->CabDiskFormat); } result = FCIDestroy (cabHandle->FciHandle);
if (FileCount) { *FileCount = cabHandle->FileCount; }
if (FileSize) { *FileSize = cabHandle->FileSize; }
if (CabFileCount) { *CabFileCount = cabHandle->CabCount; }
if (CabFileSize) { *CabFileSize = cabHandle->CompressedSize; }
MemFree (g_hHeap, 0, cabHandle); }
return result; }
BOOL CabFlushAndCloseCabinetExW ( IN CCABHANDLE CabHandle, OUT PUINT FileCount, OPTIONAL OUT PLONGLONG FileSize, OPTIONAL OUT PUINT CabFileCount, OPTIONAL OUT PLONGLONG CabFileSize OPTIONAL )
/*++
Routine Description:
Completes a cabinet file and closes its context.
Arguments:
CabHandle - Specifies cabinet context.
FileCount - Receives the number of files added to the cab
FileSize - Receives the size of all files before compression
CabFileCount - Receives the number of cabinet files created
CabFileSize - Receives the size of all cabinet files
Return Value:
TRUE if successful, FALSE otherwise.
--*/
{ PFCI_CAB_HANDLEW cabHandle; BOOL result = FALSE;
cabHandle = (PFCI_CAB_HANDLEW) CabHandle; if (cabHandle == NULL) { return FALSE; } if (cabHandle->FciHandle == NULL) { return FALSE; } if (FCIFlushCabinet ( cabHandle->FciHandle, FALSE, pCabGetNextCabinetW, pCabStatusW )) { if (cabHandle->CabPath) { FreePathStringW (cabHandle->CabPath); } if (cabHandle->CabFileFormat) { FreePathStringW (cabHandle->CabFileFormat); } if (cabHandle->CabDiskFormat) { FreePathStringW (cabHandle->CabDiskFormat); } result = FCIDestroy (cabHandle->FciHandle);
if (FileCount) { *FileCount = cabHandle->FileCount; }
if (FileSize) { *FileSize = cabHandle->FileSize; }
if (CabFileCount) { *CabFileCount = cabHandle->CabCount; }
if (CabFileSize) { *CabFileSize = cabHandle->CompressedSize; }
MemFree (g_hHeap, 0, cabHandle); } return result; }
OCABHANDLE CabOpenCabinetA ( IN PCSTR FileName )
/*++
Routine Description:
Creates a cabinet context for an existent cabinet file.
Arguments:
FileName - Specifies cabinet file name.
Return Value:
a valid OCABHANDLE if successful, NULL otherwise.
--*/
{ PFDI_CAB_HANDLEA cabHandle; PSTR filePtr; HANDLE fileHandle; PCSTR fileName;
cabHandle = (PFDI_CAB_HANDLEA) MemAlloc (g_hHeap, 0, sizeof (FDI_CAB_HANDLEA)); ZeroMemory (cabHandle, sizeof (FDI_CAB_HANDLEA)); cabHandle->FdiHandle = FDICreate ( pCabAlloc, pCabFree, pCabOpen1A, pCabRead1, pCabWrite1, pCabClose1, pCabSeek1, cpuUNKNOWN, &cabHandle->FdiErrorStruct ); if (!cabHandle->FdiHandle) { MemFree (g_hHeap, 0, cabHandle); return NULL; } fileName = DuplicatePathStringA (FileName, 0); fileHandle = CreateFileA ( fileName, GENERIC_READ|GENERIC_WRITE, 0, NULL, OPEN_EXISTING, FILE_ATTRIBUTE_NORMAL, NULL ); if (fileHandle == INVALID_HANDLE_VALUE) { FreePathStringA (fileName); MemFree (g_hHeap, 0, cabHandle); return NULL; } if (!FDIIsCabinet (cabHandle->FdiHandle, (INT_PTR)fileHandle, &cabHandle->FdiCabinetInfo)) { FreePathStringA (fileName); CloseHandle (fileHandle); MemFree (g_hHeap, 0, cabHandle); return NULL; } CloseHandle (fileHandle); filePtr = (PSTR)GetFileNameFromPathA (fileName); if (!filePtr) { FreePathStringA (fileName); MemFree (g_hHeap, 0, cabHandle); return NULL; } cabHandle->CabFile = DuplicatePathStringA (filePtr, 0); *filePtr = 0; cabHandle->CabPath = DuplicatePathStringA (fileName, 0); FreePathStringA (fileName); return ((CCABHANDLE)(cabHandle)); }
OCABHANDLE CabOpenCabinetW ( IN PCWSTR FileName )
/*++
Routine Description:
Creates a cabinet context for an existent cabinet file.
Arguments:
FileName - Specifies cabinet file name.
Return Value:
a valid OCABHANDLE if successful, NULL otherwise.
--*/
{ PFDI_CAB_HANDLEW cabHandle; PWSTR filePtr; HANDLE fileHandle; PCWSTR fileName;
cabHandle = (PFDI_CAB_HANDLEW) MemAlloc (g_hHeap, 0, sizeof (FDI_CAB_HANDLEW)); ZeroMemory (cabHandle, sizeof (FDI_CAB_HANDLEW)); cabHandle->FdiHandle = FDICreate ( pCabAlloc, pCabFree, pCabOpen1A, pCabRead1, pCabWrite1, pCabClose1, pCabSeek1, cpuUNKNOWN, &cabHandle->FdiErrorStruct ); if (!cabHandle->FdiHandle) { MemFree (g_hHeap, 0, cabHandle); return NULL; } fileName = DuplicatePathStringW (FileName, 0); fileHandle = CreateFileW ( fileName, GENERIC_READ|GENERIC_WRITE, 0, NULL, OPEN_EXISTING, FILE_ATTRIBUTE_NORMAL, NULL ); if (fileHandle == INVALID_HANDLE_VALUE) { FreePathStringW (fileName); MemFree (g_hHeap, 0, cabHandle); return NULL; } if (!FDIIsCabinet (cabHandle->FdiHandle, (INT_PTR)fileHandle, &cabHandle->FdiCabinetInfo)) { FreePathStringW (fileName); CloseHandle (fileHandle); MemFree (g_hHeap, 0, cabHandle); return NULL; } CloseHandle (fileHandle); filePtr = (PWSTR)GetFileNameFromPathW (fileName); if (!filePtr) { FreePathStringW (fileName); MemFree (g_hHeap, 0, cabHandle); return NULL; } cabHandle->CabFile = DuplicatePathStringW (filePtr, 0); *filePtr = 0; cabHandle->CabPath = DuplicatePathStringW (fileName, 0); FreePathStringW (fileName); return ((CCABHANDLE)(cabHandle)); }
BOOL CabExtractAllFilesExA ( IN OCABHANDLE CabHandle, IN PCSTR ExtractPath, OPTIONAL IN PCABNOTIFICATIONA CabNotification OPTIONAL )
/*++
Routine Description:
Extracts all files from a cabinet file.
Arguments:
CabHandle - Specifies cabinet context.
ExtractPath - Specifies the path to extract the files to.
Return Value:
TRUE if successful, FALSE otherwise.
--*/
{ PFDI_CAB_HANDLEA cabHandle; CAB_DATAA cabData;
cabHandle = (PFDI_CAB_HANDLEA)CabHandle; if (!cabHandle) { return FALSE; } if (!cabHandle->FdiHandle) { return FALSE; } cabData.ExtractPath = ExtractPath; cabData.CabNotificationA = CabNotification;
return FDICopy ( cabHandle->FdiHandle, (PSTR)cabHandle->CabFile, (PSTR)cabHandle->CabPath, 0, pCabNotificationA, NULL, (PVOID)(&cabData) ); }
BOOL pCabExtractAllFilesExWorkerW ( IN OCABHANDLE CabHandle, IN PCWSTR ExtractPath, OPTIONAL IN PCABNOTIFICATIONW CabNotificationW, OPTIONAL IN BOOL VerifyMode )
/*++
Routine Description:
Extracts all files from a cabinet file.
Arguments:
CabHandle - Specifies cabinet context.
ExtractPath - Specifies the path to extract the files to.
CabNotification - Specifies the notification callback function that is called for every file in the cab
VerifyMode - Specifies TRUE if the cab should be verified, FALSE if it should be extracted
Return Value:
TRUE if successful, FALSE otherwise.
--*/
{ PFDI_CAB_HANDLEW cabHandle; CAB_DATAW cabData; BOOL result; PCSTR cabFileAnsi; PCSTR cabPathAnsi;
cabHandle = (PFDI_CAB_HANDLEW)CabHandle; if (!cabHandle) { return FALSE; } if (!cabHandle->FdiHandle) { return FALSE; } cabData.ExtractPath = ExtractPath; cabData.CabNotificationW = CabNotificationW; cabData.VerifyMode = VerifyMode;
cabFileAnsi = ConvertWtoA (cabHandle->CabFile); cabPathAnsi = ConvertWtoA (cabHandle->CabPath);
result = FDICopy ( cabHandle->FdiHandle, (PSTR) cabFileAnsi, (PSTR) cabPathAnsi, 0, pCabNotificationW, NULL, (PVOID)(&cabData) );
FreeConvertedStr (cabFileAnsi); FreeConvertedStr (cabPathAnsi);
return result; }
BOOL CabExtractAllFilesExW ( IN OCABHANDLE CabHandle, IN PCWSTR ExtractPath, OPTIONAL IN PCABNOTIFICATIONW CabNotificationW OPTIONAL ) { return pCabExtractAllFilesExWorkerW (CabHandle, ExtractPath, CabNotificationW, FALSE); }
BOOL CabVerifyCabinet ( IN OCABHANDLE CabHandle ) { return pCabExtractAllFilesExWorkerW (CabHandle, NULL, NULL, TRUE);
}
BOOL CabCloseCabinetA ( IN OCABHANDLE CabHandle )
/*++
Routine Description:
Closes a cabinet file context.
Arguments:
CabHandle - Specifies cabinet context.
Return Value:
TRUE if successful, FALSE otherwise.
--*/
{ PFDI_CAB_HANDLEA cabHandle;
cabHandle = (PFDI_CAB_HANDLEA) CabHandle; if (!cabHandle) { return FALSE; } if (!cabHandle->FdiHandle) { return FALSE; } if (FDIDestroy (cabHandle->FdiHandle)) { if (cabHandle->CabPath) { FreePathStringA (cabHandle->CabPath); } if (cabHandle->CabFile) { FreePathStringA (cabHandle->CabFile); } MemFree (g_hHeap, 0, cabHandle); return TRUE; } return FALSE; }
BOOL CabCloseCabinetW ( IN OCABHANDLE CabHandle )
/*++
Routine Description:
Closes a cabinet file context.
Arguments:
CabHandle - Specifies cabinet context.
Return Value:
TRUE if successful, FALSE otherwise.
--*/
{ PFDI_CAB_HANDLEW cabHandle;
cabHandle = (PFDI_CAB_HANDLEW) CabHandle; if (!cabHandle) { return FALSE; } if (!cabHandle->FdiHandle) { return FALSE; } if (FDIDestroy (cabHandle->FdiHandle)) { if (cabHandle->CabPath) { FreePathStringW (cabHandle->CabPath); } if (cabHandle->CabFile) { FreePathStringW (cabHandle->CabFile); } MemFree (g_hHeap, 0, cabHandle); return TRUE; } return FALSE; }
|