windows 下共享内存使用方法示例

windows下共享内存使用方法较 linux 而言微微复杂

  • 示例实现的功能

    有一个视频文件,一块内存区域 ;

    程序 A,将该视频写入该内存区域 ;

    程序 B,从该内存区域读取该视频 ;

    

  • 代码模块实现

  程序 A:main.h

 1 #ifndef MAIN_H
 2 #define MAIN_H
 3 #include <tchar.h>
 4 #include <fstream>
 5 #include <math.h>
 6 #include <Windows.h>
 7 
 8 #include<opencv2/opencv.hpp>
 9 #include<opencv2/highgui/highgui.hpp>
10 #include<opencv2/imgproc/imgproc.hpp>
11 #include<iostream>
12 
13 using namespace std;
14 using namespace cv;
15 
16 #define IMGWIDTH 1920
17 #define IMGHEIGHT 1080
18 
19 #define FRAME_SIZE IMGWIDTH*IMGHEIGHT    //每帧图像(单通道)的大小
20 #define BUF_SIZE FRAME_SIZE*5              //设定共享内存总大小(图像头信息 + RGB图像数据信息);
21 TCHAR shareZoneName[] = TEXT("share_Image");    //共享内存的名字
22 
23 #define ORIGINAL_IMAGE_HEAD (char*)pBuf+FRAME_SIZE*0 //图像头信息首地址
24 #define ORIGINAL_IMAGE_DATA (char*)pBuf+FRAME_SIZE*2 //图像数据信息首地址
25 
26 HANDLE hMapFile;    //这块共享内存的句柄
27 LPCTSTR pBuf;        //这块共享内存的首地址
28 
29 typedef struct
30 {
31     int width;         //图像宽度
32     int height;        //图像的高度
33     int frame_no;     //该帧图像的帧序号
34 }imgInfHead;          //自定义的一个图像头结构体
35 
36 #endif

  程序 A: main.cpp

 1 #include"main.hpp"
 2 
 3 using namespace std;
 4 using namespace cv;
 5 
 6 // 创建共享内存, 通过句柄 hMapFile,获取共享内存首地址 pBuf
 7 int createFileMapping()
 8 {
 9     hMapFile = CreateFileMapping(
10         INVALID_HANDLE_VALUE,    // use paging file
11         NULL,                    // default security
12         PAGE_READWRITE,          // read/write access
13         0,                       // maximum object size (high-order DWORD)
14         BUF_SIZE,                // maximum object size (low-order DWORD)
15         shareZoneName);          // name of mapping object
16 
17     if (hMapFile == NULL)
18     {
19         printf("Could not create file mapping object (%d).\n",
20             GetLastError());
21         return 1;
22     }
23     
24 
25     pBuf = (LPTSTR)MapViewOfFile(hMapFile,   // handle to map object
26         FILE_MAP_ALL_ACCESS,                  // read/write permission
27         0,
28         0,
29         BUF_SIZE);
30 
31     if (pBuf == NULL)
32     {
33         printf("Could not map view of file (%d).\n",
34             GetLastError());
35 
36         CloseHandle(hMapFile);
37 
38         return 1;
39     }
40     return 0;
41 }
42 
43 //将 图像头 和 图像数据信息 写入到共享内存中
44 void copyToMemory(IplImage* IplImageOriginal, int frame_no)
45 {
46     if (IplImageOriginal->imageData == NULL)
47     {
48         cout << "fail copy to memory!" << endl;
49         return;
50     }
51 
52     imgInfHead img_inf_head_original;
53 
54     img_inf_head_original.width = IplImageOriginal->width;
55     img_inf_head_original.height = IplImageOriginal->height;
56     img_inf_head_original.frame_no = frame_no;
57     
58     memcpy(ORIGINAL_IMAGE_HEAD, &img_inf_head_original, sizeof(imgInfHead));    //在 共享内存 中保存图像头信息
59     memcpy(ORIGINAL_IMAGE_DATA, IplImageOriginal->imageData, 
          IplImageOriginal->width*IplImageOriginal->height*IplImageOriginal->nChannels); //在 共享内存 中保存图像信息 60 } 61 62 int main() 63 { 64 VideoCapture capture("VIDEO.mp4"); 65 66 if (!capture.isOpened()) 67 { 68 std::cout << "open video failed...!" << endl; 69 return 0; 70 } 71 72 createFileMapping(); //创建共享内存 73 74 Mat Image; 75 int frame_no = 1; 76 IplImage* IplImageOrigal = cvCreateImage(Size(IMGWIDTH, IMGHEIGHT), 8, 3); 77 78 while ( true ) 79 { 80 capture.read( Image ); 81 82 if ( Image.empty() ) 83 { 84 std::cout << "OVER!" << endl; 85 break; 86 } 87 88 IplImageOrigal = &IplImage(Image); 89 copyToMemory(IplImageOrigal, frame_no); 90 91 frame_no++; 92 } 93 94 CloseHandle(hMapFile); 95 return 0; 96 }

 

 

  程序 B:main.h

 1 #ifndef MAIN_H
 2 #define MAIN_H
 3 
 4 #include <tchar.h>
 5 #include <fstream>
 6 #include <math.h>
 7 #include <Windows.h>
 8 
 9 #include <opencv2/opencv.hpp>
10 #include <opencv2/highgui/highgui.hpp>
11 #include <opencv2/imgproc/imgproc.hpp>
12 
13 #include <string.h>
14 #include <iostream>
15 
16 using namespace std;
17 using namespace cv;
18 
19 //单帧图像长宽
20 #define IMGWIDTH 1920
21 #define IMGHEIGHT 1080
22 
23 #define FRAME_SIZE IMGWIDTH*IMGHEIGHT         //单帧大小
24 #define BUF_SIZE FRAME_SIZE*5                 //设定共享内存总大小
25 #define ORIGINAL_IMAGE_HEAD (char*)pBuf+FRAME_SIZE*0     //图像头首地址  
26 #define ORIGINAL_IMAGE_DATA (char*)pBuf+FRAME_SIZE*2      //图像数据首地址
27 
28 TCHAR shareZoneName_getSrcImg[] = TEXT("share_Image");   
29 HANDLE hMapFile;  //共享内存 句柄
30 LPCTSTR pBuf;     //共享内存 所映射到的 首地址
31 
32 typedef struct
33 {
34     int width;
35     int height;
36     int frame_no;
37 }imgInfHead;    //自定义的一个图像头结构体
38 
39 #endif

  程序 B:main.cpp

 1 #include "main.h"
 2 
 3 //打开共享内存(通过 共享内存 名称获取对应共享内存句柄,并获取共享内存首地址)
 4 int openFileMapping()
 5 {
 6     hMapFile = OpenFileMapping(
 7         FILE_MAP_ALL_ACCESS,       // read/write access
 8         FALSE,                        // do not inherit the name
 9         shareZoneName_getSrcImg); // name of mapping object
10 
11     if (hMapFile == NULL)
12     {
13         printf("Could not open file mapping object (%d).\n", GetLastError());
14         return 1;
15     }
16 
17     pBuf = (LPTSTR)MapViewOfFile(hMapFile,   // handle to map object
18         FILE_MAP_ALL_ACCESS,                  // read/write permission
19         0,
20         0,
21         BUF_SIZE);
22 
23     if (pBuf == NULL)
24     {
25         printf("Could not map view of file (%d).\n", GetLastError());
26         CloseHandle(hMapFile);
27         return 1;
28     }
29     return 0;
30 }
31 
32 //将共享内存中的图像读取
33 int copyImageFromMemory(IplImage* &IplImageoOrignal, int* frame_no_adrr)
34 {
35     imgInfHead img_inf_head_orginal;
36 
37     memcpy(&img_inf_head_orginal, ORIGINAL_IMAGE_HEAD, sizeof(imgInfHead));
38     *frame_no_adrr = img_inf_head_orginal.frame_no;                             //获取该帧图像的 帧序号
39 
40     IplImageoOrignal = cvCreateImage(cvSize(img_inf_head_orginal.width, img_inf_head_orginal.height), 8, 3);
41     int channels = IplImageoOrignal->nChannels;
42 
43     memcpy(IplImageoOrignal->imageData, ORIGINAL_IMAGE_DATA, img_inf_head_orginal.width*img_inf_head_orginal.height*channels);
44     return 0;
45 }
46 
47 int main()
48 {
49     IplImage* IplImageOriginal;
50     int frame_no;
51     
52     
53 
54     Mat image_result;
55     while (true)
56     {
57         int flag_accept = openFileMapping();
58         if (flag_accept)
59         {
60             continue;
61         }
62 
63         int flag_bad = copyImageFromMemory(IplImageOriginal, &frame_no);
64         if (flag_bad)
65         {
66             cout << "复制失败" << endl;
67             continue;
68         }
69 
70         Mat(IplImageOriginal).copyTo(image_result); // 转成Mat类型
71         if (image_result.empty())
72         {
73             cvReleaseImage(&IplImageOriginal);
74             continue;
75         }
76 
77         //将帧序号显示在图片上
78         std::stringstream ss;
79         std::string frame_no_s;
80         ss << frame_no;
81         ss >> frame_no_s;
82         putText(image_result, frame_no_s, cv::Point(0, 50), cv::FONT_HERSHEY_SIMPLEX, 2.0, cv::Scalar(0, 255, 255), 8, 10);
83 
84         imshow("readShareMemImg", image_result);
85         waitKey(1);
86     }
87     
88     CloseHandle(hMapFile);
89     return 0;
90 }

 

 

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

posted @ 2017-12-31 23:25  koalamaster  阅读(4031)  评论(0编辑  收藏  举报