进程间通信——共享内存

Posted xiongyang123

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了进程间通信——共享内存相关的知识,希望对你有一定的参考价值。

public class ShareMem 
{
    [DllImport("user32.dll", CharSet = CharSet.Auto)]
            public static extern IntPtr SendMessage(IntPtr hWnd, int Msg, int wParam, IntPtr lParam);
    [DllImport("Kernel32.dll", CharSet = CharSet.Auto)]
            public static extern IntPtr CreateFileMapping(int hFile, IntPtr lpAttributes, uint flProtect, uint dwMaxSizeHi, uint dwMaxSizeLow, string lpName);
    [DllImport("Kernel32.dll", CharSet = CharSet.Auto)]
            public static extern IntPtr OpenFileMapping(int dwDesiredAccess,[MarshalAs(UnmanagedType.bool)] bool bInheritHandle,string lpName);
    [DllImport("Kernel32.dll", CharSet = CharSet.Auto)]
            public static extern IntPtr MapViewOfFile(IntPtr hFileMapping,uint dwDesiredAccess, uint dwFileOffsetHigh, uint dwFileOffsetLow,uint dwNumberOfBytesToMap);
    [DllImport("Kernel32.dll", CharSet = CharSet.Auto)]
            public static extern bool UnmapViewOfFile(IntPtr pvBaseAddress);
    [DllImport("Kernel32.dll", CharSet = CharSet.Auto)]
            public static extern bool CloseHandle(IntPtr handle);
    [DllImport("kernel32", EntryPoint="GetLastError")]
            public static extern int GetLastError ();
    const int ERROR_ALREADY_EXISTS = 183;
    const int FILE_MAP_COPY = 0x0001;
    const int FILE_MAP_WRITE = 0x0002;
    const int FILE_MAP_READ = 0x0004;
    const int FILE_MAP_ALL_ACCESS = 0x0002 | 0x0004;
    const int PAGE_READONLY = 0x02;
    const int PAGE_READWRITE = 0x04;
    const int PAGE_WRITECOPY = 0x08;
    const int PAGE_EXECUTE = 0x10;
    const int PAGE_EXECUTE_READ = 0x20;
    const int PAGE_EXECUTE_READWRITE = 0x40;
    const int SEC_COMMIT = 0x8000000;
    const int SEC_IMAGE = 0x1000000;
    const int SEC_NOCACHE = 0x10000000;
    const int SEC_RESERVE = 0x4000000;
    const int INVALID_HANDLE_VALUE = -1;
    IntPtr m_hSharedMemoryFile = IntPtr.Zero;
    IntPtr m_pwData = IntPtr.Zero;
    bool m_bAlreadyExist = false;
    bool m_bInit = false;
    long m_MemSize=0;
    public ShareMem() 
    {
    }
    ~ShareMem() 
    {
        Close();
    }
    /// <summary>
    /// 初始化共享内存
    /// </summary>
    /// <param name="strName">共享内存名称</param>
    /// <param name="lngSize">共享内存大小</param>
    /// <returns></returns>
    public int Init(string strName, long lngSize) 
    {
        if (lngSize <= 0 || lngSize > 104857600) lngSize = 104857600;
        //0x00800000
        m_MemSize = lngSize;
        if (strName.Length > 0) 
        {
            //创建内存共享体(INVALID_HANDLE_VALUE)
            m_hSharedMemoryFile = CreateFileMapping(INVALID_HANDLE_VALUE, IntPtr.Zero, (uint)PAGE_READWRITE, 0, (uint)lngSize, strName);
            if (m_hSharedMemoryFile == IntPtr.Zero) 
            {
                m_bAlreadyExist = false;
                m_bInit = false;
                return 2;
                //创建共享体失败
            } else 
            {
                if (GetLastError() == ERROR_ALREADY_EXISTS)  //已经创建 
                {
                    m_bAlreadyExist = true;
                } else                                         //新创建 
                {
                    m_bAlreadyExist = false;
                }
            }
            //---------------------------------------
            //创建内存映射
            m_pwData = MapViewOfFile(m_hSharedMemoryFile, FILE_MAP_WRITE, 0, 0, (uint)lngSize);
            if (m_pwData == IntPtr.Zero) 
            {
                m_bInit = false;
                CloseHandle(m_hSharedMemoryFile);
                return 3;
                //创建内存映射失败
            } else 
            {
                m_bInit = true;
                if (m_bAlreadyExist == false) 
                {
                    //初始化
                }
            }
            //----------------------------------------
        } else 
        {
            return 1;
            //参数错误
        }
        return 0;
        //创建成功
    }
    /// <summary>
    /// 关闭共享内存
    /// </summary>
    public void Close() 
    {
        if (m_bInit) 
        {
            UnmapViewOfFile(m_pwData);
            CloseHandle(m_hSharedMemoryFile);
        }
    }
    /// <summary>
    /// 读数据
    /// </summary>
    /// <param name="bytData">数据</param>
    /// <param name="lngAddr">起始地址</param>
    /// <param name="lngSize">个数</param>
    /// <returns></returns>
    public int Read(ref byte[] bytData, int lngAddr, int lngSize) 
    {
        if (lngAddr + lngSize > m_MemSize) return 2;
        //超出数据区
        if (m_bInit) 
        {
            Marshal.Copy(m_pwData, bytData, lngAddr, lngSize);
        } else 
        {
            return 1;
            //共享内存未初始化
        }
        return 0;
        //读成功
    }
    /// <summary>
    /// 写数据
    /// </summary>
    /// <param name="bytData">数据</param>
    /// <param name="lngAddr">起始地址</param>
    /// <param name="lngSize">个数</param>
    /// <returns></returns>
    public int Write(byte[] bytData, int lngAddr, int lngSize) 
    {
        if (lngAddr + lngSize > m_MemSize) return 2;
        //超出数据区
        if (m_bInit) 
        {
            Marshal.Copy(bytData, lngAddr, m_pwData, lngSize);
        } else 
        {
            return 1;
            //共享内存未初始化
        }
        return 0;
        //写成功
    }
}
 

ShareMem MemDB = new ShareMem();//声明共享内存操作类
MemDB.Init("shared", 64* 1024 * 1024);//初始化共享内存   返回0表示初始化成功
byte[] bytes = new byte[2];
MemDB.Read(ref bytes, 0, 2);//读取数据,返回0表示读取成功
MemDB.Write(bytes, 0, 2);//写入数据

  

以上是关于进程间通信——共享内存的主要内容,如果未能解决你的问题,请参考以下文章

进程间通信

操作系统实验3共享内存进程间通信实验

linux进程间通信之Posix共享内存用法详解及代码举例

进程间通信之共享内存

进程间通信

进程间通信