BCB Client

- C++ Builderを用いたWindowsプログラミングメモ -

共有メモリ(メモリマップドファイル)を試してみる

プロセス間でデータの受け渡しをする際には、イロイロと方法があるようですが
今回は共有メモリ(メモリマップドファイル or メモリマップトファイル)を試してみます。

なにが出来るかというと、xxx.exeとyyy.exeがあったとして
xxx.exeのデータを共有メモリに書き込んで、yyy.exeから読み込めるという事です。


では、試す為には2つの.exeを作成しなければなりません。
今回は、書込側:Shared01.exe  読込側:Shared02.exe で実施します。



sharedmemory_01.png

 ←Shared01.exe(書込側)のフォームはこんな感じです。
  書込みボタンを押すと
  エディットボックスに表示されている文字列を
  共有メモリに書き込みます。





sharedmemory_02.png

 ←Shared02.exe(読込側)のフォームはこんな感じです。

  読込ボタンを押すと
  共有メモリのデータをエディットボックスに表示します。






<Shared01.exe(書込側) | Unit1.h>
//---------------------------------------------------------------------------
#ifndef Unit1H
#define Unit1H
//---------------------------------------------------------------------------
#include <Classes.hpp>
#include <Controls.hpp>
#include <StdCtrls.hpp>
#include <Forms.hpp>
//---------------------------------------------------------------------------
class TForm1 : public TForm
{
__published:	// IDE 管理のコンポーネント
	TEdit *Edit1;
	TButton *Button1;
	void __fastcall FormClose(TObject *Sender, TCloseAction &Action);
	void __fastcall Button1Click(TObject *Sender);
private:	// ユーザー宣言

	HANDLE m_hMapping;
	// 共有メモリ作成
	void __fastcall SharedMem_Create(AnsiString shd_name);
	// 共有メモリ追加
	void __fastcall SharedMem_Append(AnsiString shd_name, AnsiString shd_data);
	// 共有メモリ削除
	void __fastcall SharedMem_Delete(void);

public:		// ユーザー宣言
	__fastcall TForm1(TComponent* Owner);
};
//---------------------------------------------------------------------------
extern PACKAGE TForm1 *Form1;
//---------------------------------------------------------------------------
#endif



<Shared01.exe(書込側) | Unit1.cpp>
//---------------------------------------------------------------------------
#include <vcl.h>
#pragma hdrstop
#include "Unit1.h"
//---------------------------------------------------------------------------
#pragma package(smart_init)
#pragma resource "*.dfm"
TForm1 *Form1;
//---------------------------------------------------------------------------
__fastcall TForm1::TForm1(TComponent* Owner)
	: TForm(Owner)
{
}
//---------------------------------------------------------------------------
// フォームが閉じた時呼ばれるイベント
void __fastcall TForm1::FormClose(TObject *Sender, TCloseAction &Action)
{
	// 共有メモリ削除
	SharedMem_Delete();
}
//---------------------------------------------------------------------------
// 共有メモリへ書込ボタン
void __fastcall TForm1::Button1Click(TObject *Sender)
{
	AnsiString shd_name = "shared_test";

	// 共有メモリ作成
	SharedMem_Create(shd_name);
	// 共有メモリ追加
	SharedMem_Append(shd_name, Edit1->Text);
}
//---------------------------------------------------------------------------
//---------------------------------------------------------------------------
// 共有メモリ作成
void __fastcall TForm1::SharedMem_Create(AnsiString shd_name)
{
	// 共有メモリ(メモリマップトファイル)作成
	m_hMapping = CreateFileMapping(INVALID_HANDLE_VALUE,
					NULL,
					PAGE_READWRITE,	// 読書き両方にする
					0,
					512,	// 上限サイズを512byte設定
					shd_name.c_str()// 共有メモリ名を設定
					);
	if ( m_hMapping == NULL ) {
		ShowMessage("共有メモリ作成失敗");
		return;
	}

	// マッピング開始
	char *dat = (char *)MapViewOfFile(m_hMapping,
					FILE_MAP_ALL_ACCESS, // 読書き両方
					0,
					0,
					512); // 上限サイズは512byte
	// 0クリアで初期化
	ZeroMemory(dat, 512);
	// マッピング解除
	UnmapViewOfFile(dat);
}
//---------------------------------------------------------------------------
// 共有メモリ追加
void __fastcall TForm1::SharedMem_Append(AnsiString shd_name, AnsiString shd_data)
{
	HANDLE hMapping = OpenFileMapping(FILE_MAP_WRITE,  // 書込みモード
					FALSE,
					shd_name.c_str()); // 共有メモリ名指定
	if ( hMapping == NULL ) {
		ShowMessage("共有メモリが見つかりません");
		return;
	}

	// マッピング開始
	char *dat = (char *)MapViewOfFile(hMapping,
					FILE_MAP_WRITE,  // 書込で開始
					0,
					0,
					512);  // 上限サイズは512byte

	// データ書き込み
	strcpy(dat, shd_data.c_str());
	// マッピング解除
	UnmapViewOfFile(dat);
}
//---------------------------------------------------------------------------
// 共有メモリ削除
void __fastcall TForm1::SharedMem_Delete(void)
{
	CloseHandle(m_hMapping);
	m_hMapping = NULL;
}
//---------------------------------------------------------------------------





<Shared02.exe(読込側) | Unit1.h>
//---------------------------------------------------------------------------
#ifndef Unit1H
#define Unit1H
//---------------------------------------------------------------------------
#include <Classes.hpp>
#include <Controls.hpp>
#include <StdCtrls.hpp>
#include <Forms.hpp>
//---------------------------------------------------------------------------
class TForm1 : public TForm
{
__published:	// IDE 管理のコンポーネント
	TEdit *Edit1;
	TButton *Button1;
	void __fastcall Button1Click(TObject *Sender);
private:	// ユーザー宣言
public:		// ユーザー宣言
	__fastcall TForm1(TComponent* Owner);
};
//---------------------------------------------------------------------------
extern PACKAGE TForm1 *Form1;
//---------------------------------------------------------------------------
#endif



<Shared02.exe(読込側) | Unit1.cpp>
//---------------------------------------------------------------------------
#include <vcl.h>
#pragma hdrstop
#include "Unit1.h"
//---------------------------------------------------------------------------
#pragma package(smart_init)
#pragma resource "*.dfm"
TForm1 *Form1;
//---------------------------------------------------------------------------
__fastcall TForm1::TForm1(TComponent* Owner)
	: TForm(Owner)
{
}
//---------------------------------------------------------------------------
// 共有メモリから読込ボタン
void __fastcall TForm1::Button1Click(TObject *Sender)
{
	// 共有メモリ(メモリマップトファイル)を開く
	HANDLE hMapping = OpenFileMapping(FILE_MAP_READ, FALSE, "shared_test");
	if ( hMapping == NULL ) {
		ShowMessage("共有メモリが見つかりません");
		return;
	}

	// マッピング開始
	char *dat = (char *)MapViewOfFile(hMapping,
					FILE_MAP_READ,	// 読込モード
					0,
					0,
					0);		// 上限まで読込
	if ( dat == NULL ) {
		ShowMessage("共有メモリのデータがありません");
		return;
	}

	// データ読込
	Edit1->Text = AnsiString(dat);

	// マッピング解除
	UnmapViewOfFile(dat);
}
//---------------------------------------------------------------------------



Shared01.exeの書込みボタンから「レッツ共有!」という文字列を
共有メモリに書き込んでから、Shared02.exeの読込ボタンで読み込むと、
「レッツ共有!」が表示されます。

ちなみに、
上の例ではchar *ですが、構造体なんかでも問題なしです。

[ トップ | 一覧 | 前へ | 次へ ]

  • トップ
  • 一覧
  • リンク
  • 掲示板

Copyright © BCB Client. All Rights Reserved. Template by ネットマニア