【Windows核心编程】一个使用内存映射文件进行进程间通信的例子
进程间通信的方式有很多种,其底层原理使用的都是内存映射文件。
本文实现了Windows核心编程第五版475页上的demo,即使用内存映射文件来在进程间通信。

进程1
按钮【Create mapping of Data】用来创建命名内存映射文件,后备存储器为页交换文件,而非磁盘上的文件,大小为4K,将全部大小映射到进程地址空间,将Data中的数据写入该内存映射文件,然后撤销对文件视图的映射。注意在进程1里不能CloseHandle(m_hFileMapping)
进程2
按钮【Open maping and get Data】用来打开进程1创建的命名内存映射文件,将全部大小映射到进程地址空间,从中读出数据,将数据内容放到Data里。
按钮【Close mapping of Data】用来关闭CloseHandle进程1返回的内存映射文件m_hFileMapping。
void CMemoryMappingDlg::OnBnClickedBtnCreate2()
{
// TODO: 在此添加控件通知处理程序代码;
LPCTSTR lpFileMappingName = _T("MMFSharedData");
m_hFileMapping = CreateFileMapping(
INVALID_HANDLE_VALUE, NULL, PAGE_READWRITE, , * , lpFileMappingName);
DWORD dwErr = GetLastError(); if (NULL == m_hFileMapping )
{
AfxMessageBox(_T("无法创建该内存映射文件"));
return;
}
if (dwErr == ERROR_ALREADY_EXISTS)
{
AfxMessageBox(_T("存在同名内存映射文件"));
CloseHandle(m_hFileMapping);
return;
} PVOID pMapOfView = MapViewOfFile(m_hFileMapping, FILE_MAP_READ | FILE_MAP_WRITE, , , /*4 * 1024*/);
if (NULL == pMapOfView)
{
AfxMessageBox(_T("映射该文件错误"));
CloseHandle(m_hFileMapping);
return;
} ZeroMemory(pMapOfView, * ); CString strText;
GetDlgItemText(IDC_EDIT_DATA, strText);
memcpy_s(pMapOfView, (strText.GetLength() + ) * sizeof(TCHAR), strText.GetBuffer(),
(strText.GetLength() + ) * sizeof(TCHAR)); UnmapViewOfFile(pMapOfView);
//CloseHandle(m_hFileMapping); 不能执行此句,否则进程2不能打开该命名内存映射文件。
} void CMemoryMappingDlg::OnBnClickedBtnClose()
{
// TODO: 在此添加控件通知处理程序代码;
CloseHandle(m_hFileMapping);
} void CMemoryMappingDlg::OnBnClickedBtnOpen()
{
// TODO: 在此添加控件通知处理程序代码
LPCTSTR lpFileMappingName = _T("MMFSharedData"); //OpenFileMapping的第一个参数一定不能是PAGE_**, 区别于CreateFileMapping函数
//HANDLE hFileMapping = OpenFileMapping(PAGE_READWRITE, FALSE, lpFileMappingName);
HANDLE hFileMapping = OpenFileMapping(FILE_MAP_READ | FILE_MAP_WRITE, FALSE, lpFileMappingName); if (NULL == hFileMapping)
{
AfxMessageBox(_T("打不开该内存映射文件"));
return;
} PVOID pMapOfFile = MapViewOfFile(hFileMapping, FILE_MAP_READ | FILE_MAP_WRITE, , , /*4 * 1024 */);
if (NULL == pMapOfFile)
{
AfxMessageBox(_T("映射该文件错误"));
CloseHandle(hFileMapping);
return;
} TCHAR tchArr[];
ZeroMemory(tchArr, sizeof(tchArr));
memcpy_s(tchArr, sizeof(tchArr), pMapOfFile, sizeof(tchArr));
SetDlgItemText(IDC_EDIT_DATA, tchArr); UnmapViewOfFile(pMapOfFile);
CloseHandle(hFileMapping);
}
需要注意的地方是:
0、后备存储器为页交换文件的内存映射文件,CreateFileMapping的文件句柄参数为INVALID_HANDLE_VALUE
1、进程1创建了命名内存映射文件后,一定不能CloseHandle(内存映射文件句柄),否则进程2不能OpenFileMapping打开该命名内存映射文件
2、OpenFileMapping的第一个参数一定不能是PAGE_**, 区别于CreateFileMapping函数
【Windows核心编程】一个使用内存映射文件进行进程间通信的例子的更多相关文章
- Java编程思想:内存映射文件
import java.io.*; import java.nio.IntBuffer; import java.nio.MappedByteBuffer; import java.nio.chann ...
- 《windows核心编程系列》十八谈谈windows钩子
windows应用程序是基于消息驱动的.各种应用程序对各种消息作出响应从而实现各种功能. windows钩子是windows消息处理机制的一个监视点,通过安装钩子能够达到监视指定窗体某种类型的消息的功 ...
- 《windows核心编程系列》十六谈谈内存映射文件
内存映射文件允许开发人员预订一块地址空间并为该区域调拨物理存储器,与虚拟内存不同的是,内存映射文件的物理存储器来自磁盘中的文件,而非系统的页交换文件.将文件映射到内存中后,我们就可以在内存中操作他们了 ...
- Windows核心编程 第十七章 -内存映射文件(下)
17.3 使用内存映射文件 若要使用内存映射文件,必须执行下列操作步骤: 1) 创建或打开一个文件内核对象,该对象用于标识磁盘上你想用作内存映射文件的文件. 2) 创建一个文件映射内核对象,告诉系统该 ...
- Windows核心编程 第十七章 -内存映射文件(上)
第1 7章 内存映射文件 对文件进行操作几乎是所有应用程序都必须进行的,并且这常常是人们争论的一个问题.应用程序究竟是应该打开文件,读取文件并关闭文件,还是打开文件,然后使用一种缓冲算法,从文件的各个 ...
- 《windows核心编程》 17章 内存映射文件
内存映射文件主要用于以下三种情况: 系统使用内存映射文件载入并运行exe和dll,这大量节省了页交换文件的空间以及应用程序的启动时间 开发人员可以使用内存映射文件来访问磁盘上的数据文件.这使得我们可以 ...
- Java编程的逻辑 (61) - 内存映射文件及其应用 - 实现一个简单的消息队列
本系列文章经补充和完善,已修订整理成书<Java编程的逻辑>,由机械工业出版社华章分社出版,于2018年1月上市热销,读者好评如潮!各大网店和书店有售,欢迎购买,京东自营链接:http:/ ...
- 文件映射(Windows核心编程)
映射内存的可执行文件和dll 当一个线程调用CreateProcess的时候,系统会执行以下步骤: 系统会先确定CreateProcess所指定的可执行文件的所在位置.如果找不到文件,那么Create ...
- 全面介绍Windows内存管理机制及C++内存分配实例(四):内存映射文件
本文背景: 在编程中,很多Windows或C++的内存函数不知道有什么区别,更别谈有效使用:根本的原因是,没有清楚的理解操作系统的内存管理机制,本文企图通过简单的总结描述,结合实例来阐明这个机制. 本 ...
随机推荐
- spring boot--日志、开发和生产环境切换、自定义配置(环境变量)
Spring Boot日志常用配置: # 日志输出的地址:Spring Boot默认并没有进行文件输出,只在控制台中进行了打印 logging.file=/home/zhou # 日志级别 debug ...
- AC日记——2条不相交的路径 51nod 1076
1076 2条不相交的路径 基准时间限制:1 秒 空间限制:131072 KB 分值: 40 难度:4级算法题 收藏 关注 给出一个无向图G的顶点V和边E.进行Q次查询,查询从G的某个顶点V[s] ...
- Linux下使用mv重命名文件或者移动文件(增强版的工具为rename)
mv命令既可以重命名,又可以移动文件或文件夹. 例子:将目录A重命名为B mv A B 例子:将/a目录移动到/b下,并重命名为c mv /a /b/c 例子:将文件A.txt重命名为B.txt mv ...
- n个平面把空间最多分成几个部分?
题目: n个平面把空间最多分成几个部分? 解答: 1条直线可以把平面分成2部分,2条直线最多可以把平面分成4部分, 3条直线最多可以把平面分成几部分,4条直线呢?你能不能想出n条直线最多可以把平面分成 ...
- weblogic92 启动慢解决办法
使用SUN JDK 启动时要很长时间,但启动启来weblogic正常. 特征见下面标红部分,时间很长. test01@linux-suse:~/bea/weblogic92/samples/dom ...
- sqlalchemy如何实现时间列自动更新?
目标:数据表的时间列在其他列内容更新的时候,自动更新时间列到更新的时间 方法:数据库表模型如下:server_default表示初始时间,onupdate表示更新的时间 class MonitorDa ...
- 理解Neural Style
paperA Neural Algorithm of Artistic Style 在艺术领域,尤其是绘画,艺术家们通过创造不同的内容与风格,并相互交融影响来创立独立的视觉体验.如果给定两张图像,现在 ...
- SSH 原理和公匙私匙
先主要介绍了Telnet.SSH 的通信原理,分析了其通信时的工作流程. Telnet 无论Telnet协议连接的是什么类型终端,都会转换为NVT(Net Virtual Terminal)格式进行通 ...
- scheme语言编写执行
scheme是lisp的一种 编辑器能够用emacs.网上有非常多教导怎样编写的 (begin (display "hello") (newline)) 编写完以.scm保存,这里 ...
- vue-router钩子beforeRouteEnter函数获取到this实例
官方文档: const Foo = { template: `...`, beforeRouteEnter (to, from, next) { // 在渲染该组件的对应路由被 confirm 前调用 ...