cmemorylockerimpdrv98.cpp

来自「PGP8.0源码 请认真阅读您的文件包然后写出其具体功能」· C++ 代码 · 共 178 行

CPP
178
字号
/*____________________________________________________________________________
		Copyright (C) 2002 PGP Corporation
        All rights reserved.

        $Id: CMemoryLockerImpDrv98.cpp,v 1.2 2002/08/06 20:09:30 dallen Exp $
____________________________________________________________________________*/

#include "pgpClassesConfig.h"

#include "UDebug.h"
#include "CMemoryLockerImpDrv98.h"

_USING_PGP

// Macros

#define	INTEL_PAGE_SIZE		0x1000L
#define	INTEL_PAGE_SHIFT	12

#define INTEL_ADDRESS_PAGE(Va) ((ULONG)(Va) >> INTEL_PAGE_SHIFT)

#define INTEL_ADDRESS_AND_SIZE_TO_SPAN_PAGES(Va,Size) \
   ((((ULONG)((ULONG)(Size) - 1L) >> INTEL_PAGE_SHIFT) + \
   (((((ULONG)(Size-1)&(PAGE_SIZE-1)) + \
   ((ULONG)Va & (INTEL_PAGE_SIZE -1)))) >> INTEL_PAGE_SHIFT)) + 1L)

#define INTEL_BYTE_OFFSET(Va) ((ULONG)(Va) & (INTEL_PAGE_SIZE - 1))


// Types

struct CMemoryLockerImpDrv98::LockedMemInfo : 
	public CListableObject<CMemoryLockerImpDrv98::LockedMemInfo>
{
	const void	*pMem;			// original memory block
	const void	*pMappedMem;	// block mapped to linear memory
	PGPUInt32	sizeMem;		// size of memory block
};


// Class CMemoryLockerImpDrv98 member functions

CMemoryLockerImpDrv98::CMemoryLockerImpDrv98()
{
	Status() = mLMIAllocator.Status();

	if (Status().IsntError())
		Status() = mLMIListLock.Status();
}

CComboError 
CMemoryLockerImpDrv98::LockMemory(
	const void	*pMem, 
	PGPUInt32	sizeMem, 
	void		**ppMappedMem)
{
	CComboError	error;
	PGPBoolean	mapMemory	= IsntNull(ppMappedMem);

	LockedMemInfo	*pLMI;
	error = mLMIAllocator.Allocate(pLMI);

	if (error.IsntError())
	{
		pLMI->pMem = pMem;
		pLMI->sizeMem = sizeMem;

		PGPUInt32	pageIndex	= INTEL_ADDRESS_PAGE(pMem);
		PGPUInt32	numPages	= INTEL_ADDRESS_AND_SIZE_TO_SPAN_PAGES(
			pMem, sizeMem);

		// Try to lock down and map the memory.
		void	*pMappedPages	= reinterpret_cast<void *>(_LinPageLock(
			pageIndex, numPages, mapMemory ? PAGEMAPGLOBAL : 0));

		if (IsNull(pMappedPages))
			error.pgpErr = kPGPError_MemoryOpFailed;

		// Keep track of the memory.
		if (error.IsntError())
		{
			if (mapMemory)
			{
				pLMI->pMappedMem = *ppMappedMem = 
					reinterpret_cast<PGPUInt8 *>(pMappedPages) + 
					INTEL_BYTE_OFFSET(pMem);
			}
			else
			{
				pLMI->pMappedMem = NULL;
			}

			mLMIListLock.StartWriting();
			mLMIList.AddHead(pLMI);
			mLMIListLock.StopWriting();
		}

		if (error.IsError())
			mLMIAllocator.Free(pLMI);
	}

	return error;
}

CComboError 
CMemoryLockerImpDrv98::UnlockMemory(const void *pMem)
{
	CComboError	error;

	mLMIListLock.StartWriting();

	LockedMemInfo	*pLMI			= mLMIList.Head();
	PGPBoolean		foundMemInfo	= FALSE;

	// Find the info structure for this memory.
	while (IsntNull(pLMI))
	{
		// Check BOTH original user address and mapped system address.
		if ((pLMI->pMem == pMem) || (pLMI->pMappedMem == pMem))
		{
			foundMemInfo = TRUE;
			break;
		}
		else
		{
			pLMI = mLMIList.Next(pLMI);
		}
	}

	if (!foundMemInfo)
		error.pgpErr = kPGPError_BadParams;

	// Unlock the memory and free the list entry.
	if (error.IsntError())
	{
		PGPUInt32	pageIndex	= INTEL_ADDRESS_PAGE(pLMI->pMappedMem);
		PGPUInt32	numPages	= INTEL_ADDRESS_AND_SIZE_TO_SPAN_PAGES(
			pLMI->pMappedMem, pLMI->sizeMem);
		PGPBoolean	wasMapped	= IsntNull(pLMI->pMappedMem);

		if (!_LinPageUnLock(pageIndex, numPages, 
			wasMapped ? PAGEMAPGLOBAL : 0))
		{
			error.pgpErr = kPGPError_MemoryOpFailed;
		}

		mLMIList.Remove(pLMI);
		mLMIAllocator.Free(pLMI);
	}

	mLMIListLock.StopWriting();

	return error;
}

void 
CMemoryLockerImpDrv98::Shutdown()
{
	mLMIListLock.StartWriting();

	while (mLMIList.Count() > 0)
	{
		LockedMemInfo	*pLMI	= mLMIList.Remove(mLMIList.Head());

		UDebug::DebugOut("PGPdisk: CMemoryLockerImpDrv98::"
			"~CMemoryLockerImpDrv98: Mapped memory being forcibly unmapped.");

		PGPUInt32	pageIndex	= INTEL_ADDRESS_PAGE(pLMI->pMappedMem);
		PGPUInt32	numPages	= INTEL_ADDRESS_AND_SIZE_TO_SPAN_PAGES(
			pLMI->pMappedMem, pLMI->sizeMem);

		_LinPageUnLock(pageIndex, numPages, PAGEMAPGLOBAL);		
		mLMIAllocator.Free(pLMI);
	}

	mLMIListLock.StopWriting();
}

⌨️ 快捷键说明

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