⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 documentblowfish.cpp

📁 BlowFish算法的压缩源码
💻 CPP
字号:
/**********************************************************************
 * Developed by;
 *	Neal Horman - neal@wanlink.com - http://www.wanlink.com
 *	Copyright (c) 2002 Neal Horman, All Rights Reserved
 *
 * This file/code may be used, modified, and distributed, for any 
 * purpose providing that this notice and the copyright notice above
 * is left fully intact, unaltered, and any modifications, additions, 
 * or bug fixes are clearly marked as such.
 *
 * This file/code is provided "as is" with no express or implied 
 * warranty of any kind whatsoever. The author expressly accepts no 
 * liability for any possible damages incurred as a result of it's use.
 * Use it at your own risk.
 *
 * Expect bugs.
 *
 * Portions Copyright (C) Microsoft Corporation
 *
 *		RCSID:  $Id$
 *
 * DESCRIPTION:
 *		application:	BlowFishDocView Demo
 *		source module:	DocumentBlowFish.cpp
 *
 **********************************************************************/

// DocumentBlowFish.cpp: implementation of the CDocumentBlowFish and CMirrorFileBlowFish class.
//
//////////////////////////////////////////////////////////////////////

#include "stdafx.h"
#include "DocumentBlowFish.h"
#include "FileBlowFish.h"
#include <afxpriv.h>

#ifdef _DEBUG
#undef THIS_FILE
static char THIS_FILE[]=__FILE__;
#define new DEBUG_NEW
#endif

/////////////////////////////////////////////////////////////////////////////
// File operations (default uses CDocument::Serialize)

// *** Cut and paste from MFC\SRC\AFXIMPL.H
void AFX_CDECL AfxTimeToFileTime(const CTime& time, LPFILETIME pFileTime);
void AFXAPI AfxGetRoot(LPCTSTR lpszPath, CString& strRoot);


// *** Cut and paste from MFC\SRC\doccore.cpp
CString CMirrorFileBlowFish::GetTempName(LPCTSTR lpszOriginalFile, BOOL bCreate)
{
	CString str;

	// get the directory for the file

	TCHAR szPath[_MAX_PATH];
	LPTSTR lpszName;
	GetFullPathName(lpszOriginalFile, _MAX_PATH, szPath, &lpszName);
	*lpszName = NULL;

	// let's create a temporary file name, and create
	// a file too!

	GetTempFileName(szPath, _T("MFC"), 0,
		str.GetBuffer(_MAX_PATH+1));
	str.ReleaseBuffer();

	// delete the file if the user just wants a name

	if (!bCreate)
		CFile::Remove(str);

	return str;
}

// *** Cut and paste from MFC\SRC\doccore.cpp and modified to use CFileBlowFish
BOOL CMirrorFileBlowFish::Open(LPCTSTR lpszFileName, UINT nOpenFlags, CFileException* pError)
{
	ASSERT(lpszFileName != NULL);
	m_strMirrorName.Empty();

	CFileStatus status;
	if (nOpenFlags & CFile::modeCreate) //opened for writing
	{
		if (CFile::GetStatus(lpszFileName, status))
		{
			CString strRoot;
			AfxGetRoot(lpszFileName, strRoot);

			DWORD dwSecPerClus, dwBytesPerSec, dwFreeClus, dwTotalClus;
			DWORD nBytes = 0;
			if (GetDiskFreeSpace(strRoot, &dwSecPerClus, &dwBytesPerSec, &dwFreeClus,
				&dwTotalClus))
			{
				nBytes = dwFreeClus * dwSecPerClus * dwBytesPerSec;
			}
			if (nBytes > 2 * DWORD(status.m_size)) // at least 2x free space avail
			{
				m_strMirrorName = GetTempName(lpszFileName, TRUE);
			}
		}
	}

	if (!m_strMirrorName.IsEmpty() &&
		CFileBlowFish::Open(m_strMirrorName, nOpenFlags, pError))	// *** Modified line
	{
		m_strFileName = lpszFileName;
		FILETIME ftCreate, ftAccess, ftModify;
		if (::GetFileTime((HANDLE)m_hFile, &ftCreate, &ftAccess, &ftModify))
		{
			AfxTimeToFileTime(status.m_ctime, &ftCreate);
			SetFileTime((HANDLE)m_hFile, &ftCreate, &ftAccess, &ftModify);
		}

		DWORD dwLength = 0;
		PSECURITY_DESCRIPTOR pSecurityDescriptor = NULL;
		if (GetFileSecurity(lpszFileName, DACL_SECURITY_INFORMATION,
			NULL, dwLength, &dwLength))
		{
			pSecurityDescriptor = (PSECURITY_DESCRIPTOR) new BYTE[dwLength];
			if (::GetFileSecurity(lpszFileName, DACL_SECURITY_INFORMATION,
				pSecurityDescriptor, dwLength, &dwLength))
			{
				SetFileSecurity(m_strMirrorName, DACL_SECURITY_INFORMATION, pSecurityDescriptor);
			}
			delete[] (BYTE*)pSecurityDescriptor;
		}
		return TRUE;
	}
	m_strMirrorName.Empty();
	return CFileBlowFish::Open(lpszFileName, nOpenFlags, pError);	// *** Modified line
}

// *** Cut and paste from MFC\SRC\doccore.cpp and modified to use CFileBlowFish
void CMirrorFileBlowFish::Abort()
{
	CFileBlowFish::Abort();	// *** Modified line
	if (!m_strMirrorName.IsEmpty())
		CFile::Remove(m_strMirrorName);
}

// *** Cut and paste from MFC\SRC\doccore.cpp - begin
//WINBUG: these will be in a public header, some day.

typedef BOOL (WINAPI* ReplaceAPIPtr)(LPCWSTR, LPCWSTR, LPCWSTR,	DWORD, LPVOID, LPVOID);
#ifndef REPLACEFILE_WRITE_THROUGH
#define REPLACEFILE_WRITE_THROUGH 0x00000001
#endif
#ifndef REPLACEFILE_IGNORE_MERGE_ERRORS
#define REPLACEFILE_IGNORE_MERGE_ERRORS 0x00000002
#endif

#ifndef ERROR_UNABLE_TO_MOVE_REPLACEMENT
#define ERROR_UNABLE_TO_MOVE_REPLACEMENT 1176L
#endif
#ifndef ERROR_UNABLE_TO_MOVE_REPLACEMENT_2
#define ERROR_UNABLE_TO_MOVE_REPLACEMENT_2 1177L
#endif
// *** Cut and paste from MFC\SRC\doccore.cpp - end

// *** Cut and paste from MFC\SRC\doccore.cpp
void CMirrorFileBlowFish::Close()
{
	CString m_strName = m_strFileName; //file close empties string
	CFile::Close();
	if (!m_strMirrorName.IsEmpty())
	{
		BOOL bWorked = FALSE;
		DWORD dwResult = 0;
		ReplaceAPIPtr pfn = NULL;
		CString strBackupName;

		OSVERSIONINFO	osvi;
		memset(&osvi,0,sizeof(OSVERSIONINFO));
		osvi.dwOSVersionInfoSize = sizeof(OSVERSIONINFO);
		GetVersionEx(&osvi);

		if (osvi.dwPlatformId == VER_PLATFORM_WIN32_NT)
		{
			HMODULE hModule = GetModuleHandleA("KERNEL32");
			ASSERT(hModule != NULL);

	      pfn = (ReplaceAPIPtr) GetProcAddress(hModule, "ReplaceFile");

			if (pfn != NULL)
			{
				USES_CONVERSION;

				strBackupName = GetTempName(m_strMirrorName, FALSE);

				// this NT API handles copying all attributes for us

				bWorked = (pfn)(T2W((LPTSTR)(LPCTSTR)m_strName),
                            T2W((LPTSTR)(LPCTSTR)m_strMirrorName),
                            T2W((LPTSTR)(LPCTSTR)strBackupName),
					REPLACEFILE_WRITE_THROUGH | REPLACEFILE_IGNORE_MERGE_ERRORS,
					NULL, NULL);

				if (!bWorked)
				   dwResult = GetLastError();
			}
		}

		if (!bWorked)
		{
			if (dwResult == ERROR_UNABLE_TO_MOVE_REPLACEMENT || dwResult == 0)
				CFile::Remove(m_strName);

			if (dwResult == ERROR_UNABLE_TO_MOVE_REPLACEMENT_2)
			   CFile::Remove(strBackupName);

			CFile::Rename(m_strMirrorName, m_strName);
		}
      else if (pfn != NULL)
      {
         CFile::Remove(strBackupName);
      }
	}
}

//////////////////////////////////////////////////////////////////////
// Construction/Destruction
//////////////////////////////////////////////////////////////////////

IMPLEMENT_DYNCREATE(CDocumentBlowFish,CDocument);

CDocumentBlowFish::CDocumentBlowFish()
{
}

CDocumentBlowFish::~CDocumentBlowFish()
{
}

// *** Cut and paste from MFC\SRC\doccore.cpp and modified to use CFileBlowFish
CFile* CDocumentBlowFish::GetFile(LPCTSTR lpszFileName, UINT nOpenFlags, CFileException* pError)
{
	CMirrorFileBlowFish* pFile = new CMirrorFileBlowFish;
	ASSERT(pFile != NULL);
	if (!pFile->Open(lpszFileName, nOpenFlags, pError))
	{
		delete pFile;
		pFile = NULL;
	}
	return pFile;
}

// *** Cut and paste from MFC\SRC\STDAFX.h - begin
// special exception handling just for MFC library implementation
#ifndef _AFX_OLD_EXCEPTIONS

// MFC does not rely on auto-delete semantics of the TRY..CATCH macros,
//  therefore those macros are mapped to something closer to the native
//  C++ exception handling mechanism when building MFC itself.

#define DELETE_EXCEPTION(e) do { e->Delete(); } while (0)
#define NO_CPP_EXCEPTION(expr)

#else   //!_AFX_OLD_EXCEPTIONS

// In this case, the TRY..CATCH macros provide auto-delete semantics, so
//  it is not necessary to explicitly delete exception objects at the catch site.

#define DELETE_EXCEPTION(e)
#define NO_CPP_EXCEPTION(expr) expr

#endif  //_AFX_OLD_EXCEPTIONS
// *** Cut and paste from MFC\SRC\STDAFX.h - end

// *** Cut and paste from MFC\SRC\doccore.cpp and modified to use CFileBlowFish
BOOL CDocumentBlowFish::OnOpenDocument(LPCTSTR lpszPathName)
{
	if (IsModified())
		TRACE0("Warning: OnOpenDocument replaces an unsaved document.\n");

	CFileException fe;
	CFileBlowFish* pFile = (CFileBlowFish *)GetFile(lpszPathName, CFile::modeRead|CFile::shareDenyWrite, &fe);	// *** Modified line

	if (pFile == NULL)
	{
		ReportSaveLoadException(lpszPathName, &fe,
			FALSE, AFX_IDP_FAILED_TO_OPEN_DOC);
		return FALSE;
	}

	DeleteContents();
	SetModifiedFlag();  // dirty during de-serialize

	CArchive loadArchive(pFile, CArchive::load | CArchive::bNoFlushOnDelete);
	loadArchive.m_pDocument = this;
	loadArchive.m_bForceFlat = FALSE;
	TRY
	{
		CWaitCursor wait;
		if (pFile->GetLength() != 0)
			Serialize(loadArchive);     // load me
		loadArchive.Close();
		ReleaseFile(pFile, FALSE);
	}
	CATCH_ALL(e)
	{
		ReleaseFile(pFile, TRUE);
		DeleteContents();   // remove failed contents

		TRY
		{
			ReportSaveLoadException(lpszPathName, e,
				FALSE, AFX_IDP_FAILED_TO_OPEN_DOC);
		}
		END_TRY
		DELETE_EXCEPTION(e);
		return FALSE;
	}
	END_CATCH_ALL

	SetModifiedFlag(FALSE);     // start off with unmodified

	return TRUE;
}

// *** Cut and paste from MFC\SRC\doccore.cpp and modified to use CFileBlowFish
BOOL CDocumentBlowFish::OnSaveDocument(LPCTSTR lpszPathName)
{
	CFileException fe;
	CFileBlowFish* pFile = (CFileBlowFish *)GetFile(lpszPathName, CFile::modeCreate | CFile::modeReadWrite | CFile::shareExclusive, &fe);	// *** Modified line

	if (pFile == NULL)
	{
		ReportSaveLoadException(lpszPathName, &fe,
			TRUE, AFX_IDP_INVALID_FILENAME);
		return FALSE;
	}

	CArchive saveArchive(pFile, CArchive::store | CArchive::bNoFlushOnDelete);
	saveArchive.m_pDocument = this;
	saveArchive.m_bForceFlat = FALSE;
	TRY
	{
		CWaitCursor wait;
		Serialize(saveArchive);     // save me
		saveArchive.Close();
		ReleaseFile(pFile, FALSE);
	}
	CATCH_ALL(e)
	{
		ReleaseFile(pFile, TRUE);

		TRY
		{
			ReportSaveLoadException(lpszPathName, e,
				TRUE, AFX_IDP_FAILED_TO_SAVE_DOC);
		}
		END_TRY
		DELETE_EXCEPTION(e);
		return FALSE;
	}
	END_CATCH_ALL

	SetModifiedFlag(FALSE);     // back to unmodified

	return TRUE;        // success
}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -