227 lines
6 KiB
C++
227 lines
6 KiB
C++
/*******************************************************************************
|
|
*
|
|
* (C) COPYRIGHT MICROSOFT CORPORATION, 1998
|
|
*
|
|
* TITLE: SHMEMSEC.H
|
|
*
|
|
* VERSION: 1.0
|
|
*
|
|
* AUTHOR: ShaunIv
|
|
*
|
|
* DATE: 9/30/1999
|
|
*
|
|
* DESCRIPTION: Simple shared memory section template. Don't use it for classes!
|
|
* Basically, simple objects only. structs are ok. Nothing with a
|
|
* vtable.
|
|
*
|
|
*******************************************************************************/
|
|
#ifndef __SHMEMSEC_H_INCLUDED
|
|
#define __SHMEMSEC_H_INCLUDED
|
|
|
|
#include <windows.h>
|
|
#include <simstr.h>
|
|
#include <miscutil.h>
|
|
|
|
template <class T>
|
|
class CSharedMemorySection
|
|
{
|
|
public:
|
|
enum COpenResult
|
|
{
|
|
SmsFailed,
|
|
SmsCreated,
|
|
SmsOpened
|
|
};
|
|
|
|
private:
|
|
HANDLE m_hMutex;
|
|
HANDLE m_hFileMapping;
|
|
T *m_pMappedSection;
|
|
|
|
private:
|
|
//
|
|
// Not implemented
|
|
//
|
|
CSharedMemorySection( const CSharedMemorySection & );
|
|
CSharedMemorySection &operator=( const CSharedMemorySection & );
|
|
|
|
public:
|
|
CSharedMemorySection( LPCTSTR pszName=NULL, bool bAllowCreate=true )
|
|
: m_hFileMapping(NULL),
|
|
m_pMappedSection(NULL),
|
|
m_hMutex(NULL)
|
|
{
|
|
WIA_PUSHFUNCTION(TEXT("CSharedMemorySection::CSharedMemorySection"));
|
|
Open(pszName,bAllowCreate);
|
|
}
|
|
~CSharedMemorySection(void)
|
|
{
|
|
WIA_PUSHFUNCTION(TEXT("CSharedMemorySection::~CSharedMemorySection"));
|
|
Close();
|
|
}
|
|
bool OK(void)
|
|
{
|
|
return(m_pMappedSection != NULL);
|
|
}
|
|
T *Lock(void)
|
|
{
|
|
T *pResult = NULL;
|
|
if (OK())
|
|
{
|
|
if (WiaUiUtil::MsgWaitForSingleObject( m_hMutex, INFINITE ))
|
|
{
|
|
pResult = m_pMappedSection;
|
|
}
|
|
}
|
|
return pResult;
|
|
}
|
|
void Release(void)
|
|
{
|
|
if (OK())
|
|
{
|
|
ReleaseMutex(m_hMutex);
|
|
}
|
|
}
|
|
COpenResult Open( LPCTSTR pszName, bool bAllowCreate=true )
|
|
{
|
|
//
|
|
// Close any previous instances
|
|
//
|
|
Close();
|
|
|
|
//
|
|
// Assume failure
|
|
//
|
|
COpenResult orResult = SmsFailed;
|
|
|
|
//
|
|
// Make sure we have a valid name
|
|
//
|
|
if (pszName && *pszName)
|
|
{
|
|
//
|
|
// Save the name
|
|
//
|
|
CSimpleString strSectionName = pszName;
|
|
|
|
//
|
|
// Replace any invalid characters
|
|
//
|
|
for (int i=0;i<(int)strSectionName.Length();i++)
|
|
{
|
|
if (strSectionName[i] == TEXT('\\'))
|
|
{
|
|
strSectionName[i] = TEXT('-');
|
|
}
|
|
}
|
|
|
|
//
|
|
// Create the mutex name
|
|
//
|
|
CSimpleString strMutex(strSectionName);
|
|
strMutex += TEXT("-Mutex");
|
|
|
|
//
|
|
// Try to create the mutex
|
|
//
|
|
m_hMutex = CreateMutex( NULL, FALSE, strMutex );
|
|
if (m_hMutex)
|
|
{
|
|
//
|
|
// Take ownership of the mutex
|
|
//
|
|
if (WiaUiUtil::MsgWaitForSingleObject( m_hMutex, INFINITE ))
|
|
{
|
|
//
|
|
// If this file mapping already exists, open it.
|
|
//
|
|
m_hFileMapping = OpenFileMapping( FILE_MAP_ALL_ACCESS, FALSE, strSectionName );
|
|
if (m_hFileMapping)
|
|
{
|
|
m_pMappedSection = reinterpret_cast<T*>(MapViewOfFile( m_hFileMapping, FILE_MAP_ALL_ACCESS, 0, 0, sizeof(T) ));
|
|
orResult = SmsOpened;
|
|
}
|
|
else if (bAllowCreate)
|
|
{
|
|
//
|
|
// Create the file mapping
|
|
//
|
|
m_hFileMapping = CreateFileMapping( INVALID_HANDLE_VALUE, NULL, PAGE_READWRITE, 0, sizeof(T), strSectionName );
|
|
if (m_hFileMapping)
|
|
{
|
|
//
|
|
// Try to acquire the file mapping
|
|
//
|
|
m_pMappedSection = reinterpret_cast<T*>(MapViewOfFile( m_hFileMapping, FILE_MAP_ALL_ACCESS, 0, 0, sizeof(T) ));
|
|
if (m_pMappedSection)
|
|
{
|
|
//
|
|
// Initialize the data
|
|
//
|
|
ZeroMemory( m_pMappedSection, sizeof(T) );
|
|
orResult = SmsCreated;
|
|
}
|
|
}
|
|
}
|
|
//
|
|
// Release the mutex
|
|
//
|
|
ReleaseMutex(m_hMutex);
|
|
}
|
|
}
|
|
}
|
|
//
|
|
// If we weren't able to map the file mapping section, we need to clean up
|
|
//
|
|
if (!m_pMappedSection)
|
|
{
|
|
Close();
|
|
}
|
|
return(orResult);
|
|
}
|
|
void Close(void)
|
|
{
|
|
//
|
|
// First, try to delete it safely.
|
|
//
|
|
if (m_hMutex)
|
|
{
|
|
if (WiaUiUtil::MsgWaitForSingleObject( m_hMutex, INFINITE ))
|
|
{
|
|
if (m_pMappedSection)
|
|
{
|
|
UnmapViewOfFile(m_pMappedSection);
|
|
m_pMappedSection = NULL;
|
|
}
|
|
if (m_hFileMapping)
|
|
{
|
|
CloseHandle(m_hFileMapping);
|
|
m_hFileMapping = NULL;
|
|
}
|
|
ReleaseMutex(m_hMutex);
|
|
}
|
|
}
|
|
|
|
//
|
|
// Then, just clean up
|
|
//
|
|
if (m_pMappedSection)
|
|
{
|
|
UnmapViewOfFile(m_pMappedSection);
|
|
m_pMappedSection = NULL;
|
|
}
|
|
if (m_hFileMapping)
|
|
{
|
|
CloseHandle(m_hFileMapping);
|
|
m_hFileMapping = NULL;
|
|
}
|
|
if (m_hMutex)
|
|
{
|
|
CloseHandle(m_hMutex);
|
|
m_hMutex = NULL;
|
|
}
|
|
}
|
|
};
|
|
|
|
#endif
|