如何正确使用文件映射并将数据传递给子进程?

Posted

技术标签:

【中文标题】如何正确使用文件映射并将数据传递给子进程?【英文标题】:How to correctly use File Mapping and pass Data to a child process? 【发布时间】:2012-02-21 16:47:00 【问题描述】:

我的应用程序正在执行另一个进程(“update.exe”),我想将大数据(可能是一条记录)从我的应用程序传递到 update程序。

使用命令行传递数据参数不是一种选择,因为数据太大(而且数据大小可能会有所不同)。

如何正确创建CreateFileMapping/MapViewOfFile/UnmapViewOfFile, 然后执行我的 update.exe, 最后在 update.exe 程序中接收数据 (OpenFileMapping), 并释放所有句柄(从主应用程序和 update.exe),这样我就没有内存/句柄泄漏?

代码会很好(请不要JCL)。 C++ 也不错。 谢谢。


编辑:我认为我的主要问题是如何在update.exe 完成读取数据后向UnmapViewOfFileCloseHandle “发送信号”。 (或者我可能需要在我的子进程中使用 OpenFileMapping 并将 bInheritHandle 设置为 True?) 这是Example。如果主进程调用UnmapViewOfFileCloseHandle,第二进程如何读取数据?

【问题讨论】:

但是 JCL 的定义很棒...... 一个简单的解决方案是将数据存储在一个文件中,并在命令行中传递文件名。 @LURD,我想做什么,但传递 FileMapping 名称作为参数并使用 OpenFileMapping... ;) 好吧,我的意思是一个普通的文件,但是看这里有一个使用windows文件映射的例子,Limiting multiple instances. Restoring last instance. The file mapping approach。 【参考方案1】:

您可以在Inter-process communication 找到一些很好的示例。正确的方法取决于您的数据大小和速度要求。

【讨论】:

【参考方案2】:

这是我们用于在应用程序之间传递实时视频(未压缩)的内存映射文件中的代码 sn-p,不需要 SecurityDescriptor,但我已将其留在其中,CreateWorldAccessDescriptor 是我们的功能之一。

如果您需要使用这种类型的系统来控制从服务到应用程序的消息传递,或者从使用不同用户凭据运行的应用程序,请确保您的文件名以“全局\”开头

procedure TRawFeedImageQueue.CreateFileMap;
var
  SysInfo: TSystemInfo;
  sd: TSecurityDescriptor;
begin
  GetSystemInfo( SysInfo );
  MapGranularity := SysInfo.dwAllocationGranularity;
  MapSize := sizeof( TRawFeedImageQueueData );

  FSecObjOk := CreateWorldAccessDescriptor( sd, GENERIC_ALL );

  FileMappingHandle := CreateFileMapping( $FFFFFFFF, @sd, PAGE_READWRITE OR SEC_COMMIT, 0, MapSize and $FFFFFFFF, PChar(FFileName) );
  if FileMappingHandle <> 0 then
  begin
    MapView := MapViewOfFile( FileMappingHandle, FILE_MAP_ALL_ACCESS, 0, 0, MapSize );
  end
  else
  begin
    MapView := nil;
  end;
end;

procedure TRawFeedImageQueue.ReleaseFileMap;
begin
  if FileMappingHandle <> 0 then
  begin
    unMapViewOfFile( MapView );
    CloseHandle( FileMappingHandle );
  end;
end;

希望能有所帮助。

更新

这段代码只是在整个文件的文件上创建了一个MapView,而且只是一个视图,如果需要你当然可以在同一个文件上创建多个更小的视图。

【讨论】:

以上是关于如何正确使用文件映射并将数据传递给子进程?的主要内容,如果未能解决你的问题,请参考以下文章

使用 MSW 测试 React-query,并将数据传递给子组件

如何在 iOS 中检索数据并将数据传递给标签栏控制器的子视图?

Android:如何将数据传递给子活动?

如何使用ts将数据传递给vue3中的多深度子组件

我如何使用 CodeIgniter 执行 sql 脚本并将数据传递给它?

Angular2 - 将 ASYNC 数据传递给子组件