📄 cabinet.cpp
字号:
//---------------------------------------------------------------------------
// Copyright (C) 1998, Interscope Ltd. All rights reserved.
// Reproduction or distribution of this program, or any portion of it,
// is permitted only if this header is kept as it is.
// For more information, contact:
//
// Interscope Ltd., 5 Culturii St., 5th floor, 4800 Baia Mare, Romania
// Phone/Fax: +40-62-215023
// E-mail: office@interscope.ro
//
// $Author: Levente Farkas $
// $Date: 5/12/98 11:49p $
// $Modtime: 4/27/98 6:50a $
// $Revision: 68 $
// $Archive: /Interscope/Thebe/InstallMaster/Cabinet.cpp $
// $Workfile: Cabinet.cpp $
//-----------------------------------------------------------------------
#ifdef __STDAFX__
#include "StdAfx.H"
#endif
#include <Sys/Stat.H>
#include <IO.H>
#include <FCntl.H>
#include <DOS.H>
#include <TypeInfo.H>
#ifndef __MFC__
#include "Trace.H"
#endif
#include "AssertX.H"
#include "Reminder.Hpp"
#include "Cabinet.Hpp"
//--- Debugee --------------------------------------------------------------
#ifdef _DEBUG
#undef THIS_FILE
static char THIS_FILE[] = __FILE__;
#ifdef __MFC__
#define new DEBUG_NEW
#endif // __MFC__
#endif // _DEBUG
//-------------------------------------------------------------------------
// Pre :
// Post :
// Globals :
// I/O :
// Task : Allocate memory
//-------------------------------------------------------------------------
void HUGE * FAR DIAMONDAPI CCabinetBase::MemAlloc(ULONG cbSize)
{
#ifdef __TRACE_CAB_MEMORY__
TRACEFN(_T("CCabinetBase::MemAlloc(%lu)"),cbSize);
#endif
return malloc(cbSize);
}
//-------------------------------------------------------------------------
// Pre :
// Post :
// Globals :
// I/O :
// Task : Free allocated memory
//-------------------------------------------------------------------------
void FAR DIAMONDAPI CCabinetBase::MemFree(void HUGE *ptrMemory)
{
#ifdef __TRACE_CAB_MEMORY__
TRACEFN(_T("CCabinetBase::MemFree(0x%lx)\n"),ptrMemory);
#endif
free(ptrMemory);
}
//-------------------------------------------------------------------------
// Pre : If not NULL, the wild parameter pv is a pointer 2 an instance
// of a class CCabinetBase
// Post :
// Globals :
// I/O :
// Task : Open a file
//-------------------------------------------------------------------------
int FAR DIAMONDAPI CCabinetBase::FileOpen(char FAR *pszFile, int oFlag, int pMode, int FAR *ptrErr, void FAR *pv)
{
#if defined(__TRACE_CAB_COMPRESSION__) || defined(__TRACE_CAB_EXTRACTION__)
TRACEFN(_T("CCabinetBase::FileOpen(%s,0x%04x,0x%04x)\n"),pszFile,oFlag,pMode);
#endif
// No error yet
ASSERTX(ptrErr);
*ptrErr =NOERROR;
// Text-mode files are not supported, everything is
// considered 2 be raw binary
if((oFlag & _O_TEXT) == _O_TEXT)
{
ASSERTX(FALSE);
*ptrErr =EINVAL;
return -1;
}
// Extract access mode from oFlag
DWORD dwDesiredAccess =GENERIC_READ;
if((oFlag & _O_WRONLY) == _O_WRONLY)
dwDesiredAccess =GENERIC_WRITE;
else if((oFlag & _O_RDWR) == _O_RDWR)
dwDesiredAccess |=GENERIC_WRITE;
if(dwDesiredAccess == GENERIC_READ)
// When we only want 2 read from a file, make sure
// we open it with share-read, otherwise we won't be
// able 2 read from files which are in use by Windows
pMode |=_S_IREAD;
// Extract creation mode from oFlag
DWORD dwCreateMode;
if((oFlag & _O_CREAT) == _O_CREAT)
{
// Creating a file
if((oFlag & _O_EXCL) == _O_EXCL)
dwCreateMode =CREATE_NEW;
else if((oFlag & _O_TRUNC) == _O_TRUNC)
dwCreateMode =CREATE_ALWAYS;
else
dwCreateMode =OPEN_ALWAYS;
}
else
{
// Opening a file
if((oFlag & _O_TRUNC) == _O_TRUNC)
dwCreateMode =TRUNCATE_EXISTING;
else
dwCreateMode =OPEN_EXISTING;
}
// Extract other flags from oFlag
DWORD dwFlagsAttrs =FILE_ATTRIBUTE_NORMAL;
if((oFlag & _O_RANDOM) == _O_RANDOM)
dwFlagsAttrs |=FILE_FLAG_RANDOM_ACCESS;
if((oFlag & _O_SEQUENTIAL) == _O_SEQUENTIAL)
dwFlagsAttrs |=FILE_FLAG_SEQUENTIAL_SCAN;
if((oFlag & _O_CREAT) == _O_CREAT)
{
// Thease are valid only when creating a new file
if((oFlag & _O_SHORT_LIVED) == _O_SHORT_LIVED)
dwFlagsAttrs |=FILE_ATTRIBUTE_TEMPORARY;
if((oFlag & _O_TEMPORARY) == _O_TEMPORARY)
dwFlagsAttrs |=FILE_FLAG_DELETE_ON_CLOSE;
}
// Converting share mode
DWORD dwShareMode =0;
if((pMode & _S_IREAD) == _S_IREAD)
dwShareMode |=FILE_SHARE_READ;
if((pMode & _S_IWRITE) == _S_IWRITE)
dwShareMode |=FILE_SHARE_WRITE;
HANDLE hFile =CreateFile(pszFile,dwDesiredAccess,dwShareMode,NULL,dwCreateMode,dwFlagsAttrs,NULL);
BOOL bResult =(hFile != INVALID_HANDLE_VALUE);
if(bResult)
{
if((oFlag & _O_APPEND) == _O_APPEND)
// Move file pointer 2 the end of the file first
SetFilePointer(hFile,0,NULL,FILE_END);
}
else
{
// Store the error code
DWORD dwError =GetLastError();
switch(dwError)
{
case ERROR_ACCESS_DENIED:
case ERROR_LOCK_VIOLATION:
case ERROR_SHARING_VIOLATION:
*ptrErr =EACCES;
break;
case ERROR_INVALID_PARAMETER:
*ptrErr =EINVAL;
break;
case ERROR_FILE_EXISTS:
case ERROR_ALREADY_EXISTS:
*ptrErr =EEXIST;
break;
case ERROR_TOO_MANY_OPEN_FILES:
*ptrErr =EMFILE;
break;
case ERROR_FILE_NOT_FOUND:
case ERROR_PATH_NOT_FOUND:
*ptrErr =ENOENT;
break;
default:
*ptrErr =(int)dwError;
}
}
return bResult ? (int)hFile : -1;
}
//-------------------------------------------------------------------------
// Pre : If not NULL, the wild parameter pv is a pointer 2 an instance
// of a class CCabinetBase
// Post :
// Globals :
// I/O :
// Task : Read cbRead bytes from file specified by handle into buffer ptrBuffer
//-------------------------------------------------------------------------
UINT FAR DIAMONDAPI CCabinetBase::FileRead(int hFile, void FAR *ptrBuffer, UINT cbRead, int FAR *ptrErr, void FAR *pv)
{
#if defined(__TRACE_CAB_COMPRESSION__) || defined(__TRACE_CAB_EXTRACTION__)
TRACEFN(_T("CCabinetBase::FileRead(%d,0x%p,%u)\n"),hFile,ptrBuffer,cbRead);
#endif
// No error yet
ASSERTX(ptrErr);
*ptrErr =NOERROR;
DWORD dwBytesRead;
BOOL bResult =ReadFile((HANDLE)hFile,ptrBuffer,cbRead,&dwBytesRead,NULL);
// Check 4 end-of-file condition
if(bResult && (dwBytesRead == 0))
// EOF
return 0;
if(!bResult)
// Store the error code
*ptrErr =EBADF;
return bResult ? (UINT)dwBytesRead : (UINT)-1;
}
//-------------------------------------------------------------------------
// Pre : If not NULL, the wild parameter pv is a pointer 2 an instance
// of a class CCabinetBase
// Post :
// Globals :
// I/O :
// Task : Write cbWrite bytes from buffer ptrBuffer int file specified by handle
//-------------------------------------------------------------------------
UINT FAR DIAMONDAPI CCabinetBase::FileWrite(int hFile, void FAR *ptrBuffer, UINT cbWrite, int FAR *ptrErr, void FAR *pv)
{
#if defined(__TRACE_CAB_COMPRESSION__) || defined(__TRACE_CAB_EXTRACTION__)
TRACEFN(_T("CCabinetBase::FileWrite(%d,0x%p,%u)\n"),hFile,ptrBuffer,cbWrite);
#endif
// No error yet
ASSERTX(ptrErr);
*ptrErr =NOERROR;
DWORD dwBytesWritten;
BOOL bResult =WriteFile((HANDLE)hFile,ptrBuffer,cbWrite,&dwBytesWritten,NULL);
if(!bResult)
{
// Store the error code
DWORD dwError =GetLastError();
switch(dwError)
{
case ERROR_HANDLE_DISK_FULL:
case ERROR_DISK_FULL:
*ptrErr =ENOSPC;
break;
default:
*ptrErr =EBADF;
}
}
return bResult ? (UINT)dwBytesWritten : (UINT)-1;
}
//-------------------------------------------------------------------------
// Pre : If not NULL, the wild parameter pv is a pointer 2 an instance
// of a class CCabinetBase
// Post :
// Globals :
// I/O :
// Task : Seek the file pointer
//-------------------------------------------------------------------------
long FAR DIAMONDAPI CCabinetBase::FileSeek(int hFile, long offset, int seekType, int FAR *ptrErr, void FAR *pv)
{
#if defined(__TRACE_CAB_COMPRESSION__) || defined(__TRACE_CAB_EXTRACTION__)
TRACEFN(_T("CCabinetBase::FileSeek(%d,%ld,%d)\n"),hFile,offset,seekType);
#endif
// No error yet
ASSERTX(ptrErr);
*ptrErr =NOERROR;
// Convert seek type
DWORD dwMoveMethod;
switch(seekType)
{
case SEEK_SET:
dwMoveMethod =FILE_BEGIN;
break;
case SEEK_CUR:
dwMoveMethod =FILE_CURRENT;
break;
case SEEK_END:
dwMoveMethod =FILE_END;
break;
default:
// This should never happen
ASSERTX(FALSE);
*ptrErr =EINVAL;
return -1;
}
DWORD dwNewOffset =SetFilePointer((HANDLE)hFile,offset,NULL,dwMoveMethod);
BOOL bResult =(dwNewOffset != (DWORD)-1);
if(!bResult)
{
// Store the error code
DWORD dwError =GetLastError();
switch(dwError)
{
case ERROR_INVALID_PARAMETER:
*ptrErr =EINVAL;
break;
default:
*ptrErr =EBADF;
}
}
return bResult ? (long)dwNewOffset : -1;
}
//-------------------------------------------------------------------------
// Pre : If not NULL, the wild parameter pv is a pointer 2 an instance
// of a class CCabinetBase
// Post :
// Globals :
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -