www.pudn.com > FileGuard.zip > IniFile.cpp


// IniFile.cpp: implementation of the CIniFile class. 
// 
////////////////////////////////////////////////////////////////////// 
 
#include "stdafx.h" 
#include "FileGuardApp.h" 
#include "IniFile.h" 
#include "FileGuard.h" 
#include "FGDevice.h" 
 
#ifdef _DEBUG 
#undef THIS_FILE 
static char THIS_FILE[]=__FILE__; 
#define new DEBUG_NEW 
#endif 
 
////////////////////////////////////////////////////////////////////// 
// Construction/Destruction 
////////////////////////////////////////////////////////////////////// 
 
CIniFile::CIniFile() 
{ 
	m_findIndex=0; 
	bIsOpen=FALSE; 
} 
 
 
CIniFile::CIniFile(LPCTSTR lpszIniFilePath) 
{ 
	m_findIndex=0; 
	bIsOpen=FALSE; 
 
	if(Open(lpszIniFilePath)) 
		bIsOpen=TRUE; 
} 
 
CIniFile::~CIniFile() 
{ 
	if(bIsOpen) 
		m_iniFile.Close(); 
} 
 
BOOL CIniFile::Open(LPCTSTR lpszIniFilePath) 
{ 
	//Be careful of CFile::shareDenyWrite.  
	//avoid conflition with device. 
	bIsOpen=FALSE; 
 
	if(m_iniFile.Open(lpszIniFilePath,CFile::modeNoTruncate | CFile::modeReadWrite | CFile::shareDenyNone)) 
	{ 
		bIsOpen=TRUE; 
		return TRUE; 
	} 
	else	return FALSE; 
} 
 
BOOL CIniFile::TruncateFile() 
{ 
	if(!bIsOpen) 
		return FALSE; 
 
	m_iniFile.SetLength(0); 
	return TRUE; 
} 
 
BOOL CIniFile::AddOneItem(PROTECTED_FILE * const pProtFile) 
{ 
	if(pProtFile==NULL || !bIsOpen) 
		return FALSE; 
 
	m_iniFile.SeekToEnd(); 
 
	//INI file format: each record consist of a '@' followed by length of the path 
	//(4 char, including a whitespace),a '#' followed by protection type(3 char, 
	//including a whitespace) and anther '#' followed 
	//by the path of a file under protection. 
	char buf[MAX_PATH+12]; 
	//!!! 
	UINT stringLen=sprintf(buf,"@ %3u, %2u,%s\0\n",lstrlen(pProtFile->PF_pPath),pProtFile->PF_type,pProtFile->PF_pPath); 
	stringLen++;   //add the final char '\0'. 
	 
 
	try 
	{ 
		m_iniFile.Write(buf, stringLen); 
	} 
	catch(CFileException * e) 
	{ 
		e->Delete(); 
		return FALSE; 
	} 
 
	return TRUE; 
} 
 
 
//Read one item of protected file information from ini file( return in pProtFile), 
//must pass in a valid poiter. 
//Return the offset of the item in ini file if success, otherwise -1. 
int CIniFile::ReadOneItem(PROTECTED_FILE * const pProtFile, UINT beginPos) 
{ 
	if(pProtFile==NULL || !bIsOpen) 
		return -1; 
 
	if(beginPos>=m_iniFile.GetLength())		//pass the end of the file. 
		return -1; 
 
	const UINT ReadLen=MAX_PATH * 4; 
	char buf[ReadLen];       
	UINT nBytesRead;	// bytes read from the ini file. 
	UINT nSeekBack;	//bytes to seek back. 
	UINT pos;	//pos of the item in buf. 
	UINT nItemOffset;	//position of the item in  ini file. 
 
	m_iniFile.Seek(beginPos, CFile::begin); 
 
	for(UINT i=0; i<=ReadLen-1; i++) 
		buf[ReadLen]=0; 
 
	try 
	{ 
		nBytesRead=m_iniFile.Read(buf, ReadLen); 
	} 
	catch(CFileException * e) 
	{ 
		e->Delete(); 
		return -1; 
	} 
 
	nSeekBack=nBytesRead; 
 
	//find first '@': 
	pos=0; 
	while(*(buf+pos)!='@' && pos<=ReadLen-1) 
		pos++; 
	nItemOffset=m_iniFile.GetPosition()+pos;	//zero-based??? 
 
	//Read from file in the specific format. 
	char path[MAX_PATH+1]; 
	BOOL bReadSuccess=TRUE; 
	if(StringToFileInfo(buf+pos, pProtFile, path)!=1) 
		bReadSuccess=FALSE; 
	else 
	{ 
		//reading success. 
		char *pProtFilePath=(char *)malloc((lstrlen(path)+1) * sizeof(char)); 
		lstrcpy(pProtFilePath, path); 
		pProtFile->PF_pPath=pProtFilePath; 
 
		nSeekBack-=pos+1+lstrlen(path)+RECORD_LEN;	//zero-based??? 
		bReadSuccess=TRUE; 
	} 
 
 
	m_iniFile.Seek( -((int)nSeekBack), CFile::current);   //will negative number as lOff do? 
 
	if(bReadSuccess) 
		return (int) nItemOffset; 
	else return -1; 
} 
 
//must pass in a valid pointer. 
//return the offset of the item in the ini file if an item have found, 
//else return -1. 
int CIniFile::FindFirstItem(PROTECTED_FILE * const pProtFile) 
{ 
	if(pProtFile==NULL || !bIsOpen) 
		return -1; 
 
	m_findIndex=0; 
 
	//position pointer of the file will be changed in ReadOneItem(), so retain it. 
	UINT nOldPos=m_iniFile.GetPosition(); 
 
	int ret=ReadOneItem(pProtFile, 0); 
	if(ret==-1) 
		m_findIndex=0; 
	else 
		m_findIndex=m_iniFile.GetPosition()-1; 
 
	m_iniFile.Seek(nOldPos, CFile::begin); 
	 
	return ret; 
} 
 
//must pass in a valid pointer. 
//return the offset of the item in the ini file if an item have found, 
//else return -1. 
int CIniFile::FindNextItem(PROTECTED_FILE * const pProtFile) 
{ 
	if(pProtFile==NULL || !bIsOpen) 
		return -1; 
 
	//position pointer of the file will be changed in ReadOneItem(), so retain it. 
	UINT nOldPos=m_iniFile.GetPosition(); 
 
	int ret=ReadOneItem(pProtFile, m_findIndex); 
	if(ret==-1) 
		m_findIndex=0; 
	else 
		m_findIndex=m_iniFile.GetPosition()-1; 
 
	m_iniFile.Seek(nOldPos, CFile::begin); 
	 
	return ret; 
} 
 
BOOL CIniFile::RemoveOneItem(LPCTSTR lpszProtFilePath) 
{ 
	if(!bIsOpen) 
		return FALSE; 
 
	PROTECTED_FILE protFile; 
	UINT ItemPos; 
	if((ItemPos=FindFirstItem(&protFile))==-1) 
		return FALSE; 
	else 
		if(lstrcmp(lpszProtFilePath, protFile.PF_pPath)==0) 
		{ 
			RemoveOneItem(ItemPos, &protFile); 
			return TRUE; 
		} 
 
	while((ItemPos=FindNextItem(&protFile))!=-1) 
	{ 
		if(lstrcmp(lpszProtFilePath, protFile.PF_pPath)==0) 
		{ 
			RemoveOneItem(ItemPos, &protFile); 
			return TRUE; 
		} 
	} 
 
	return FALSE; 
} 
 
BOOL CIniFile::RemoveOneItem(UINT offset, PROTECTED_FILE *pProtFile) 
{ 
	if(pProtFile==NULL || !bIsOpen) 
		return FALSE; 
 
	UINT nOldOffset=m_iniFile.GetPosition(); 
	m_iniFile.Seek(offset, CFile::begin); 
 
	UINT ItemLen=lstrlen(pProtFile->PF_pPath)+9; 
	char *buf=new char[ItemLen]; 
	if(!buf) 
		return FALSE; 
	for(UINT i=0; i<=ItemLen-1; i++) 
		buf[i]=0; 
	try 
	{ 
		m_iniFile.Write(buf, ItemLen); 
	} 
	catch(CFileException *e) 
	{ 
		delete buf; 
		e->Delete(); 
		return FALSE; 
	} 
 
	m_iniFile.Seek(nOldOffset, CFile::begin); 
	delete buf; 
	return TRUE; 
} 
 
//Is a path in ini file(case unsensity): 
BOOL CIniFile::IsAPathIn(LPCTSTR lpszFilePath) 
{ 
	if(!bIsOpen) 
		return FALSE; 
 
	if(!lpszFilePath) 
		return TRUE;	 
 
	PROTECTED_FILE protFile; 
	CString strFilePath=lpszFilePath; 
 
	FGFormatPath(strFilePath, FALSE); 
 
	if((FindFirstItem(&protFile)==-1)) 
		return FALSE; 
	else 
		if(!lstrcmp(protFile.PF_pPath, strFilePath))   
			return TRUE; 
 
	while(FindNextItem(&protFile)!=-1) 
		if(!lstrcmp(protFile.PF_pPath, strFilePath)) 
			return TRUE; 
 
	return FALSE; 
} 
 
BOOL CIniFile::CreateFile(LPCTSTR lpszIniFilePath) 
{ 
	if(bIsOpen) 
		return TruncateFile(); 
	 
	if(m_iniFile.Open(lpszIniFilePath, CFile::modeCreate | CFile::modeReadWrite |CFile::shareDenyNone)) 
		return bIsOpen=TRUE; 
 
	TRACE("Open ini file error: %d", GetLastError()); 
	return FALSE; 
}