#include "stdafx.h"
#include "MemoryComm.h"
#include "MemoryDef.h"

CMemoryComm::CMemoryComm(void) :m_hLock(NULL),
m_hFileMap(NULL),
m_pMemory(NULL)
{

}

CMemoryComm::~CMemoryComm(void)
{
	Close();
	if (m_hLock != NULL)
	{
		CloseHandle(m_hLock);
	}
}


CMemoryComm::CMemoryComm(const CMemoryComm& other)
{
	//if ( this != other)
	//{
	//	m_hLock = other.m_hLock;
	//	m_hFileMap = other.m_hFileMap;
	//	m_pMemory = other.m_pMemory;
	//}
}

CMemoryComm& CMemoryComm::operator=(const CMemoryComm& other)
{
	// TODO: 在此处插入 return 语句
	//if (this != other)
	//{
	//	m_hLock = other.m_hLock;
	//	m_hFileMap = other.m_hFileMap;
	//	m_pMemory = other.m_pMemory;
	//}

	return *this;
}


void CMemoryComm::Unmap()
{
	if (m_pMemory)
	{
		::UnmapViewOfFile(m_pMemory);
		m_pMemory = NULL;
	}
}


// 锁定共享内存
BOOL CMemoryComm::Lock(DWORD dwTime)
{
	// 如果还没有创建锁就先创建一个
	if (!m_hLock)
	{
		// 初始化的时候不被任何线程占用
		m_hLock = ::CreateMutex(NULL, FALSE, MEMERY_NAME);
		if (!m_hLock)
			return FALSE;
	}

	// 哪个线程最先调用等待函数就最先占用这个互斥量
	DWORD dwRet = ::WaitForSingleObject(m_hLock, dwTime);
	return (dwRet == WAIT_OBJECT_0 || dwRet == WAIT_ABANDONED);
}

void CMemoryComm::Unlock()
{
	if (m_hLock)
	{
		::ReleaseMutex(m_hLock);
	}
}

void CMemoryComm::Close()
{
	Unmap();

	if (m_hFileMap)
	{
		::CloseHandle(m_hFileMap);
		m_hFileMap = NULL;
	}
}

/************************************************************************/
/*  函数：[7/3/2018 Wang];
/*  描述：初始化共享内存，若已创建内存则打开;
/*  参数：;
/*  	[IN] ：;
/*  	[OUT] ：;
/*  	[IN/OUT] ：;
/*  返回：void;
/*  注意：;
/*  示例：;
/*
/*  修改：;
/*  日期：;
/*  内容：;
/************************************************************************/
BOOL CMemoryComm::InitMemery(DWORD dwOffset /* = 0*/)
{
	if (m_hFileMap == NULL)
	{
		// 创建共享内存;
		m_hFileMap = ::CreateFileMapping(INVALID_HANDLE_VALUE, NULL, PAGE_READWRITE, 0, MEMERY_SIZE, MEMERY_NAME);
		if (ERROR_ALREADY_EXISTS == GetLastError())
		{
			CloseHandle(m_hFileMap);
			m_hFileMap = NULL;

			// 打开共享内存;
			m_hFileMap = ::OpenFileMapping(FILE_MAP_ALL_ACCESS, FALSE, MEMERY_NAME);
			if (!m_hFileMap)
				return FALSE;
		}
	}

	// 将内存映射出来;
	if (m_pMemory == NULL)
	{
		ULARGE_INTEGER ui;
		ui.QuadPart = static_cast<ULONGLONG>(dwOffset);
		m_pMemory = ::MapViewOfFile(m_hFileMap, FILE_MAP_ALL_ACCESS, ui.HighPart, ui.LowPart, MEMERY_SIZE);
		if (m_pMemory == NULL)
		{
			//ShowSystemErrorInfo(_T("映射内存失败"), GetLastError());
			return FALSE;
		}
	}

	return TRUE;
}
