分享
 
 
 

一个完整的共享內存类

王朝vc·作者佚名  2006-01-09
窄屏简体版  字體: |||超大  

/******************************************************************

++ File Name : FFMClass.h

++ Description: 共享內存類

---------------------------------------------------------------

++ Author: Fei ZhaoDong

++ Create time: 2004/3/25 上午 10:00:00

++ Version: 1.1

++ Modifier:

++ Activities:

++ Update List: 2004/3/30 下午 02:59:45

*******************************************************************/

// FFMClass.h: interface for the CFFMClass.

//

//////////////////////////////////////////////////////////////////////

#ifndef FZD_FFMCLASS_H

#define FZD_FFMCLASS_H

#include <aclapi.h>

//////////////////////////////////////////////////////////////////////

// Macro definition

// 以下為共享內存定義

#define DEFAULT_FILENAME NULL // 默認的文件名

#define DEFAULT_MAPNAME "_FZD_MAP_" // 默認的共享內存名

#define DEFAULT_MAPSIZE (0xFFFF + 1) // 默認的共享內存大小

const DWORD NETRGUSER_CFM_CODE = 0x1211DBFF; // 校驗碼, 用於命令數據

const DWORD NETRGUSER_CMD_NONE = 0; // 初始化指令碼, 無指令

// 以下為錯誤碼定義

#define ERROR_LEN 256 // 錯誤描述長度

#define ERROR_INVALID_CMDCODE 0xE00001FF // 已經存在完全一樣的共享內存

#define ERROR_NO_MAPFILE 0xE00002FF // 未分配共享內存文件

#define ERROR_INVALID_CFMCODE 0xE00003FF // 校驗碼不匹配

//////////////////////////////////////////////////////////////////////

// 內存文件格式定義

#pragma pack(1)

// 用於存儲命令數據的內存文件格式

typedef struct _tagDATA_HEADER

{

DWORD dwConfirmCode; // 校驗碼

DWORD nCommandCode; // 指令識別碼

DWORD dwDataSize; // 數據的大小

BYTE dwReserved[19]; // 保留

BYTE bInfo[1]; // 數據起始地址

_tagDATA_HEADER()

{

dwConfirmCode = NETRGUSER_CFM_CODE;

nCommandCode = NETRGUSER_CMD_NONE;

dwDataSize = 0;

ZeroMemory(dwReserved, 19);

ZeroMemory(bInfo, 1);

}

}DATA_HEADER, *LPDATA_HEADER;

typedef DWORD (WINAPI *PSetEntriesInAcl)(ULONG, PEXPLICIT_ACCESS, PACL, PACL*);

// 用於存儲應答數據的共享內存文件格式 (暫不用)

typedef struct _tagANS_HEADER

{

}ANS_HEADER, *LPANS_HEADER;

#pragma pack()

//////////////////////////////////////////////////////////////////////

// 類定義,共享內存服務端

class CFFMServer

{

public:

CFFMServer();

virtual ~CFFMServer();

CFFMServer(char *szFileName, char *szMapName, DWORD dwSize);

protected:

PSetEntriesInAcl m_fnpSetEntriesInAcl;

HANDLE m_hFile; // 映射文件句柄

HANDLE m_hFileMap; // 內存文件句柄

LPVOID m_lpFileMapBuffer; // 緩衝區指針

char *m_pFileName; // 映射文件名

char *m_pMapName; // 內存文件名

DWORD m_dwSize; // 緩衝區大小

BOOL m_bCreateFlag; // 是否已創建共享內存

DWORD m_dwLastError; // 錯誤代碼

private:

void _Init(); // 初始化參數

BOOL _IsWinNTLater(); // 判斷當前操作系統

public:

BOOL Create(char *szFileName = DEFAULT_FILENAME,

char *szMapName = DEFAULT_MAPNAME,

DWORD dwSize = DEFAULT_MAPSIZE); // 新建共享內存

LPVOID GetBuffer(); // 獲取內存文件指針

DWORD GetSize(); // 獲取內存文件大小

void Destory(); // 銷毀已有的共享內存

BOOL WriteCmdData( // 寫入命令數據

DWORD nCommandCode,

DWORD dwDataSize,

const LPVOID pBuf);

};

//////////////////////////////////////////////////////////////////////

// 類定義,共享內存客戶端

class CFFMClient

{

public:

CFFMClient();

virtual ~CFFMClient();

CFFMClient(DWORD dwAccess, char *szMapName, DWORD dwSize);

protected:

HANDLE m_hFileMap; // 內存文件句柄

LPVOID m_lpFileMapBuffer; // 內存文件指針

char *m_pMapName; // 內存文件名

BOOL m_bOpenFlag; // 是否已經打開了一個內存文件

DWORD m_dwLastError; // 錯誤代碼

private:

void _Init(); // 初始化參數

public:

BOOL Open(DWORD dwAccess = FILE_MAP_READ,

char *szMapName = DEFAULT_MAPNAME,

DWORD dwSize = 0); // 打開一個內存文件

LPVOID GetBuffer(); // 獲取當前內存文件的指針

void Destory(); // 關閉當前對內存文件的訪問

BOOL GetCmdDataSize(DWORD *pDataSize); // 讀取命令數據大小

BOOL ReadCmdData( // 讀取命令數據

DWORD dwCommandCode,

DWORD dwBufSize,

LPVOID pOutBuf);

};

#endif // FZD_FFMCLASS_H

/******************************************************************

++ File Name : FFMClass.cpp

++ Description: 共享內存類

---------------------------------------------------------------

++ Author: Fei ZhaoDong

++ Create time: 2004/3/25 上午 10:00:00

++ Version: 1.0

++ Modifier:

++ Activities:

++ Update List: 2004/3/29 下午 02:59:45

*******************************************************************/

// FFMClass.cpp: implementation of the CFFMClass.

//

//////////////////////////////////////////////////////////////////////

#include "stdafx.h"

#include "FFMClass.h"

#include <aclapi.h>

//////////////////////////////////////////////////////////////////////

// CFFMServer

//////////////////////////////////////////////////////////////////////

CFFMServer::CFFMServer()

{

m_dwLastError = 0;

m_fnpSetEntriesInAcl = NULL;

_Init();

}

CFFMServer::~CFFMServer()

{

Destory();

}

CFFMServer::CFFMServer(char *szFileName, char *szMapName, DWORD dwSize)

{

// 以自定義設置創建共享內存塊

_Init();

Create(szFileName, szMapName, dwSize);

}

// 初始化各個參數

void CFFMServer::_Init()

{

m_hFile = NULL;

m_hFileMap = NULL;

m_lpFileMapBuffer = NULL;

m_pFileName = NULL;

m_pMapName = NULL;

m_dwSize = 0;

m_bCreateFlag = FALSE;

}

// 判斷是否NT4.0以上操作系統

BOOL CFFMServer::_IsWinNTLater()

{

OSVERSIONINFO Ver;

BOOL bAbleVersion = FALSE;

Ver.dwOSVersionInfoSize = sizeof(OSVERSIONINFO);

if (GetVersionEx(&Ver))

{

if (Ver.dwPlatformId == VER_PLATFORM_WIN32_NT

&& Ver.dwMajorVersion >= 4)

{

bAbleVersion = TRUE;

}

}

else

{

m_dwLastError = GetLastError();

}

return bAbleVersion;

}

// 釋放當前共享內存,並重新初始化參數

void CFFMServer::Destory()

{

if (m_lpFileMapBuffer != NULL)

{

UnmapViewOfFile(m_lpFileMapBuffer);

m_lpFileMapBuffer = NULL;

}

if (m_hFileMap != NULL)

{

CloseHandle(m_hFileMap);

m_hFileMap = NULL;

}

if (m_hFile && m_hFile != INVALID_HANDLE_VALUE)

{

CloseHandle(m_hFile);

m_hFile = NULL;

}

if (m_pFileName != NULL)

{

free(m_pFileName);

m_pFileName = NULL;

}

if (m_pMapName != NULL)

{

free(m_pMapName);

m_pMapName = NULL;

}

_Init();

}

// 創建共享內存塊

BOOL CFFMServer::Create(char *szFileName, char *szMapName, DWORD dwSize)

{

// 釋放已有的共享內存塊

if (m_bCreateFlag)

{

Destory();

}

// 拷貝各個參數

if (szFileName)

{

m_pFileName = _strdup(szFileName);

}

if (szMapName)

{

m_pMapName = _strdup(szMapName);

}

else

{

m_pMapName = _strdup(DEFAULT_MAPNAME);

}

if (dwSize > 0)

{

m_dwSize = dwSize;

}

else

{

m_dwSize = DEFAULT_MAPSIZE;

}

// 以下創建共享內存

if (m_pFileName)

{

m_hFile = CreateFile(

m_pFileName,

GENERIC_READ|GENERIC_WRITE,

FILE_SHARE_READ|FILE_SHARE_WRITE,

NULL,

OPEN_ALWAYS,

FILE_ATTRIBUTE_NORMAL,

NULL

);

}

else

{

// 默認情況下,在頁面文件中創建共享內存

m_hFile = INVALID_HANDLE_VALUE;

}

if (_IsWinNTLater())

{

// Set DACL

const int NUM_ACES = 2; // number if ACEs int DACL

// evryone -- read

// creator -- full access

// 初始化參數

PSID pEveryoneSID = NULL; // everyone群組SID

PSID pCreatorSID = NULL; // creator群組SID

PACL pFileMapACL = NULL; // 準備新內存文件的DACL

PSECURITY_DESCRIPTOR pSD = NULL; // 內存文件的SD

SECURITY_ATTRIBUTES saFileMap; // 內存文件的SA

EXPLICIT_ACCESS ea[NUM_ACES]; // 外部訪問結構

BOOL bHasErr = FALSE; // 返回值

// 以下創建SID

SID_IDENTIFIER_AUTHORITY SIDAuthWorld = SECURITY_WORLD_SID_AUTHORITY;

SID_IDENTIFIER_AUTHORITY SIDAuthCreator = SECURITY_CREATOR_SID_AUTHORITY;

// Evryone

if (!AllocateAndInitializeSid(&SIDAuthWorld, 1, SECURITY_WORLD_RID,

0, 0, 0, 0, 0, 0, 0, &pEveryoneSID))

{

bHasErr = TRUE;

goto Finish;

}

// Creator

if (!AllocateAndInitializeSid(&SIDAuthCreator, 1, SECURITY_CREATOR_OWNER_RID,

0, 0, 0, 0, 0, 0, 0, &pCreatorSID))

{

bHasErr = TRUE;

goto Finish;

}

// 填充ACE

ZeroMemory(&ea, NUM_ACES * sizeof(EXPLICIT_ACCESS));

// S-1-1-0 evryone, 唯讀權限

ea[0].grfAccessPermissions = GENERIC_READ | GENERIC_WRITE;

ea[0].grfAccessMode = SET_ACCESS;

ea[0].grfInheritance= NO_INHERITANCE;

ea[0].Trustee.TrusteeForm = TRUSTEE_IS_SID;

ea[0].Trustee.TrusteeType = TRUSTEE_IS_WELL_KNOWN_GROUP;

ea[0].Trustee.ptstrName = (LPTSTR) pEveryoneSID;

// S-1-3-0 creator owner, 完全權限

ea[1].grfAccessPermissions = STANDARD_RIGHTS_ALL;

ea[1].grfAccessMode = SET_ACCESS;

ea[1].grfInheritance= NO_INHERITANCE;

ea[1].Trustee.TrusteeForm = TRUSTEE_IS_SID;

ea[1].Trustee.TrusteeType = TRUSTEE_IS_WELL_KNOWN_GROUP;

ea[1].Trustee.ptstrName = (LPTSTR) pCreatorSID;

// 創建並填充ACL

if(NULL == m_fnpSetEntriesInAcl)

{

HINSTANCE hLib = ::LoadLibrary("Advapi32.dll");

if(NULL != hLib)

{

m_fnpSetEntriesInAcl = (PSetEntriesInAcl)GetProcAddress(hLib,"SetEntriesInAclA");

::FreeLibrary(hLib);

hLib = NULL;

}

}

if (ERROR_SUCCESS != m_fnpSetEntriesInAcl(NUM_ACES, ea, NULL, &pFileMapACL))

{

bHasErr = TRUE;

goto Finish;

}

// 創建並初始化SD

pSD = (PSECURITY_DESCRIPTOR)LocalAlloc(LPTR, SECURITY_DESCRIPTOR_MIN_LENGTH);

if (NULL == pSD)

{

bHasErr = TRUE;

goto Finish;

}

if (!InitializeSecurityDescriptor(pSD, SECURITY_DESCRIPTOR_REVISION))

{

bHasErr = TRUE;

goto Finish;

}

// 添加ACL到SD中去

if (!SetSecurityDescriptorDacl(pSD,

TRUE, // fDaclPresent flag

pFileMapACL,

FALSE)) // not a default DACL

{

bHasErr = TRUE;

goto Finish;

}

// 設置SA

saFileMap.nLength = sizeof(SECURITY_ATTRIBUTES);

saFileMap.bInheritHandle = FALSE;

saFileMap.lpSecurityDescriptor = pSD;

// 創建共享內存文件

if (m_hFile != NULL)

{

m_hFileMap = CreateFileMapping(

m_hFile,

&saFileMap,

PAGE_READWRITE,

0,

m_dwSize,

m_pMapName);

if (NULL == m_hFileMap)

{

m_hFileMap = OpenFileMapping(FILE_MAP_READ | FILE_MAP_WRITE,

TRUE, m_pMapName);

if (NULL == m_hFileMap)

{

m_dwLastError = GetLastError();

Destory();

goto Finish;

}

}

}

Finish:

if (pSD != NULL)

{

LocalFree(pSD);

}

if (pFileMapACL != NULL)

{

LocalFree(pFileMapACL);

}

if (pEveryoneSID != NULL)

{

FreeSid(pEveryoneSID);

}

if (pCreatorSID != NULL)

{

FreeSid(pCreatorSID);

}

if (bHasErr)

{

m_dwLastError = GetLastError();

return FALSE;

}

}

else

{

// 創建共享內存文件

if (m_hFile)

{

m_hFileMap = CreateFileMapping(

m_hFile,

NULL,

PAGE_READWRITE,

0,

m_dwSize,

m_pMapName);

if (NULL == m_hFileMap)

{

m_dwLastError = GetLastError();

Destory();

return FALSE;

}

}

}

// 映射文件指針到用戶

if (m_hFileMap)

{

m_lpFileMapBuffer = MapViewOfFile(

m_hFileMap,

FILE_MAP_ALL_ACCESS,

0,

0,

m_dwSize);

if (NULL == m_lpFileMapBuffer)

{

m_dwLastError = GetLastError();

Destory();

return FALSE;

}

}

m_bCreateFlag = TRUE;

return TRUE;

}

// 獲取內存文件指針

LPVOID CFFMServer::GetBuffer()

{

return (m_lpFileMapBuffer)?(m_lpFileMapBuffer):(NULL);

}

// 獲取內存文件大小

DWORD CFFMServer::GetSize()

{

return m_dwSize;

}

BOOL CFFMServer::WriteCmdData(DWORD nCommandCode, DWORD dwDataSize, const LPVOID pBuf)

{

// 檢驗數據的合理性

if (NULL == GetBuffer())

{

m_dwLastError = ERROR_NO_MAPFILE;

SetLastError(ERROR_NO_MAPFILE);

return FALSE;

}

if (NETRGUSER_CMD_NONE == nCommandCode)

{

m_dwLastError = ERROR_INVALID_CMDCODE;

SetLastError(ERROR_INVALID_CMDCODE);

return FALSE;

}

if (dwDataSize > 0 && pBuf == NULL)

{

m_dwLastError = ERROR_INVALID_USER_BUFFER;

SetLastError(ERROR_INVALID_USER_BUFFER);

return FALSE;

}

if (dwDataSize + sizeof(DATA_HEADER) > GetSize())

{

m_dwLastError = ERROR_BUFFER_OVERFLOW;

SetLastError(ERROR_BUFFER_OVERFLOW);

return FALSE;

}

// 填寫數據結構

// 文件頭

DATA_HEADER dataHeader;

dataHeader.nCommandCode = nCommandCode;

dataHeader.dwDataSize = dwDataSize;

ZeroMemory(GetBuffer(), GetSize());

memcpy(GetBuffer(), &dataHeader, sizeof(DATA_HEADER));

// 數據塊

LPDATA_HEADER pData = (LPDATA_HEADER)GetBuffer();

memcpy(pData->bInfo, pBuf, dwDataSize);

return TRUE;

}

//////////////////////////////////////////////////////////////////////

// CFFMClient

//////////////////////////////////////////////////////////////////////

CFFMClient::CFFMClient()

{

m_dwLastError = 0;

_Init();

}

CFFMClient::~CFFMClient()

{

Destory();

}

CFFMClient::CFFMClient(DWORD dwAccess, char *szMapName, DWORD dwSize)

{

_Init();

if (!Open(dwAccess, szMapName, dwSize))

{

Destory();

}

}

// 初始化參數

void CFFMClient::_Init()

{

m_hFileMap = NULL;

m_lpFileMapBuffer = NULL;

m_pMapName = NULL;

m_bOpenFlag = FALSE;

}

// 關閉當前對內存文件的訪問

void CFFMClient::Destory()

{

if (m_lpFileMapBuffer)

{

UnmapViewOfFile(m_lpFileMapBuffer);

m_lpFileMapBuffer = NULL;

}

if (m_hFileMap)

{

CloseHandle(m_hFileMap);

m_hFileMap = NULL;

}

if (m_pMapName)

{

free(m_pMapName);

m_pMapName = NULL;

}

_Init();

}

// 打開一個內存文件

BOOL CFFMClient::Open(DWORD dwAccess, char *szMapName, DWORD dwSize)

{

if (m_bOpenFlag)

{

Destory();

}

if (szMapName != NULL)

{

m_pMapName = _strdup(szMapName);

}

else

{

m_pMapName = _strdup(DEFAULT_MAPNAME);

}

m_hFileMap = OpenFileMapping(dwAccess, TRUE, m_pMapName);

if (NULL == m_hFileMap)

{

m_dwLastError = GetLastError();

Destory();

return FALSE;

}

m_lpFileMapBuffer = MapViewOfFile(m_hFileMap, dwAccess, 0, 0, dwSize);

if (NULL == m_lpFileMapBuffer)

{

m_dwLastError = GetLastError();

Destory();

return FALSE;

}

m_bOpenFlag = TRUE;

return TRUE;

}

// 獲取當前內存文件的指針

LPVOID CFFMClient::GetBuffer()

{

return (m_lpFileMapBuffer)?(m_lpFileMapBuffer):(NULL);

}

// 讀取命令數據大小

BOOL CFFMClient::GetCmdDataSize(DWORD *pDataSize)

{

ASSERT(pDataSize != NULL);

*pDataSize = 0;

LPDATA_HEADER pHeader = (LPDATA_HEADER)GetBuffer();

if (NULL == pHeader)

{

m_dwLastError = ERROR_NO_MAPFILE;

SetLastError(ERROR_NO_MAPFILE);

return FALSE;

}

if (NETRGUSER_CFM_CODE != pHeader->dwConfirmCode)

{

m_dwLastError = ERROR_INVALID_CFMCODE;

SetLastError(ERROR_INVALID_CFMCODE);

return FALSE;

}

if (NETRGUSER_CMD_NONE == pHeader->nCommandCode)

{

m_dwLastError = ERROR_INVALID_CMDCODE;

SetLastError(ERROR_INVALID_CMDCODE);

return FALSE;

}

*pDataSize = pHeader->dwDataSize;

return TRUE;

}

// 讀取命令數據

BOOL CFFMClient::ReadCmdData(DWORD dwCommandCode, DWORD dwBufSize, LPVOID pOutBuf)

{

ASSERT (pOutBuf != NULL);

LPDATA_HEADER pHeader = (LPDATA_HEADER)GetBuffer();

if (NULL == pHeader)

{

m_dwLastError = ERROR_NO_MAPFILE;

SetLastError(ERROR_NO_MAPFILE);

return FALSE;

}

if (NETRGUSER_CFM_CODE != pHeader->dwConfirmCode)

{

m_dwLastError = ERROR_INVALID_CFMCODE;

SetLastError(ERROR_INVALID_CFMCODE);

return FALSE;

}

if (NETRGUSER_CMD_NONE == pHeader->nCommandCode)

{

m_dwLastError = ERROR_INVALID_CMDCODE;

SetLastError(ERROR_INVALID_CMDCODE);

return FALSE;

}

if (pHeader->dwDataSize > dwBufSize)

{

m_dwLastError = ERROR_BUFFER_OVERFLOW;

SetLastError(ERROR_BUFFER_OVERFLOW);

return FALSE;

}

if (pHeader->nCommandCode != dwCommandCode)

{

m_dwLastError = ERROR_INVALID_CMDCODE;

SetLastError(ERROR_INVALID_CMDCODE);

return FALSE;

}

ZeroMemory(pOutBuf, dwBufSize);

// 拷貝數據到緩衝區

memcpy(pOutBuf, pHeader->bInfo, pHeader->dwDataSize);

return TRUE;

}

 
 
 
免责声明:本文为网络用户发布,其观点仅代表作者个人观点,与本站无关,本站仅提供信息存储服务。文中陈述内容未经本站证实,其真实性、完整性、及时性本站不作任何保证或承诺,请读者仅作参考,并请自行核实相关内容。
2023年上半年GDP全球前十五强
 百态   2023-10-24
美众议院议长启动对拜登的弹劾调查
 百态   2023-09-13
上海、济南、武汉等多地出现不明坠落物
 探索   2023-09-06
印度或要将国名改为“巴拉特”
 百态   2023-09-06
男子为女友送行,买票不登机被捕
 百态   2023-08-20
手机地震预警功能怎么开?
 干货   2023-08-06
女子4年卖2套房花700多万做美容:不但没变美脸,面部还出现变形
 百态   2023-08-04
住户一楼被水淹 还冲来8头猪
 百态   2023-07-31
女子体内爬出大量瓜子状活虫
 百态   2023-07-25
地球连续35年收到神秘规律性信号,网友:不要回答!
 探索   2023-07-21
全球镓价格本周大涨27%
 探索   2023-07-09
钱都流向了那些不缺钱的人,苦都留给了能吃苦的人
 探索   2023-07-02
倩女手游刀客魅者强控制(强混乱强眩晕强睡眠)和对应控制抗性的关系
 百态   2020-08-20
美国5月9日最新疫情:美国确诊人数突破131万
 百态   2020-05-09
荷兰政府宣布将集体辞职
 干货   2020-04-30
倩女幽魂手游师徒任务情义春秋猜成语答案逍遥观:鹏程万里
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案神机营:射石饮羽
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案昆仑山:拔刀相助
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案天工阁:鬼斧神工
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案丝路古道:单枪匹马
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案镇郊荒野:与虎谋皮
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案镇郊荒野:李代桃僵
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案镇郊荒野:指鹿为马
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案金陵:小鸟依人
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案金陵:千金买邻
 干货   2019-11-12
 
推荐阅读
 
 
 
>>返回首頁<<
 
靜靜地坐在廢墟上,四周的荒凉一望無際,忽然覺得,淒涼也很美
© 2005- 王朝網路 版權所有