Windows进程通信-共享内存空间

三个模块

1,game.exe,三个方法,控制台输入指令(‘A‘,‘B‘,‘R‘)分别控制三个方法的调用;

2,WGDll.dll,要注入到game进程中的dll文件;

3,myconsole.exe,用来注入dll文件的程序;

先开启game进程,然后用myconsole把dll注入到game,dll模块和myconsole模块利用共享内存实现进程通信,在myconsole的控制台输入指令,dllmokuai接受指令,调用game模块的方法,达到控制game的目的

game模块

#include<stdio.h>

void attack()
{
    printf("**********attack**********");
    return;
}
void rest()
{
    printf("**********rest**********\n");
    return;
}
void blood()
{
    printf("**********blood**********\n");
    return;
}

int main()
{
    char orderChar;
    printf("**********GAME BEGIN**********\n");
    while (1)
    {
        orderChar = getchar();
        switch (orderChar)
        {
        case ‘A‘:
            attack();
            break;
        case ‘R‘:
            rest();
            break;
        case ‘B‘:
            blood();
            break;
        case ‘Q‘:
            printf("**********GAME OVER**********\n");
            return 0;
        }
    }

    return 0;
}

dll模块

// dllmain.cpp : 定义 DLL 应用程序的入口点。
#include<Windows.h>
#include<iostream>
#include<stdio.h>
using namespace std;

#define _MAP_ TEXT("gameDll")

#define ATTACK 0x0641740
#define REST 0x0641800
#define BLOOD 0x06417a0

HANDLE hMapFile;
LPTSTR lpBuffer;
TCHAR dwType;

DWORD WINAPI ThreadProc(LPVOID lpParameter)
{
    HANDLE hMapFile = OpenFileMapping(FILE_MAP_ALL_ACCESS, FALSE, _MAP_);
    if (!hMapFile)
    {
        printf("OpenMappingFile Error : %d", GetLastError());
        return 0;
    }
    lpBuffer = (LPTSTR)MapViewOfFile(hMapFile, FILE_MAP_ALL_ACCESS, 0, 0, BUFSIZ);
    for (;;)
    {
        Sleep(2000);
        if (lpBuffer != NULL)
        {
           // CopyMemory(&dwType, lpBuffer, 4);
            wmemcpy_s(&dwType, 4, lpBuffer, 1);
            wcout << lpBuffer << endl;
        }
        if (dwType == L‘A‘)
        {
            //MessageBox(NULL, TEXT("AAAAA"), TEXT("AAAAA"), MB_OK);
            __asm
            {
                mov eax, ATTACK
                call eax
            }
            //dwType = 0;
            //CopyMemory(lpBuffer, &dwType, 4);
        }
        if (dwType == L‘B‘)
        {
            //MessageBox(NULL, TEXT("BBBBBB"), TEXT("BBBBBBB"), MB_OK);
            __asm
            {
                mov eax, BLOOD
                call eax
            }
            //dwType = 0;
            //CopyMemory(lpBuffer, &dwType, 4);
        }
        if (dwType == L‘R‘)
        {
            //MessageBox(NULL, TEXT("RRRRRRR"), TEXT("RRRRRRR"), MB_OK);
            __asm
            {
                mov eax, REST
                call eax
            }
            //dwType = 0;
            //CopyMemory(lpBuffer, &dwType, 4);
        }
        if (dwType == L‘Q‘)
        {
            //MessageBox(NULL, TEXT("QQQQQQQ"), TEXT("QQQQQQ"), MB_OK);
            UnmapViewOfFile(lpBuffer);
        }
    }
    return 0;
}

BOOL APIENTRY DllMain(HMODULE hModule,
    DWORD  ul_reason_for_call,
    LPVOID lpReserved
)
{
    switch (ul_reason_for_call)
    {
    case DLL_PROCESS_ATTACH:
        MessageBox(NULL, TEXT("hehe"), TEXT("HAHA"), MB_OKCANCEL);
        CreateThread(NULL, 0, (LPTHREAD_START_ROUTINE)ThreadProc, NULL, 0, NULL);
    case DLL_THREAD_ATTACH:
    case DLL_THREAD_DETACH:
    case DLL_PROCESS_DETACH:
        break;
    }
    return TRUE;
}

myconsole模块

#include<Windows.h>
#include<stdio.h>
#include<Tlhelp32.h>
#include <iostream>
#include<stdlib.h>
using namespace std;

#define _MAP_ TEXT("gameDll")

HANDLE hFileMapping;
LPTSTR lpBuffer;
BOOL init()
{

    hFileMapping = CreateFileMapping(INVALID_HANDLE_VALUE, NULL, PAGE_READWRITE, 0, 0x1000, _MAP_);
    if (hFileMapping==NULL)
    {
        printf("create filemapping failed error : %d", GetLastError());
        return FALSE;
    }
    lpBuffer = (LPTSTR)MapViewOfFile(hFileMapping, FILE_MAP_ALL_ACCESS, 0, 0, BUFSIZ);
    if (lpBuffer==NULL)
    {
        printf("create filemappingview failed error : %d", GetLastError());
        return FALSE;
    }
    return TRUE;
}

DWORD GetPid(const TCHAR* pDest)
{
    HANDLE hProcessHandle;
    PROCESSENTRY32 pe32 = {0};

    hProcessHandle = CreateToolhelp32Snapshot(TH32CS_SNAPPROCESS,0);
    if (hProcessHandle == INVALID_HANDLE_VALUE)
    {
        return FALSE;
    }
    pe32.dwSize = sizeof(PROCESSENTRY32);
    //const TCHAR* pDest = TEXT("game.exe");
    while (Process32Next(hProcessHandle,&pe32))
    {
        //printf("%s\n", pe32.szExeFile);
        if (wcscmp(pe32.szExeFile,pDest)==0)
        {
            CloseHandle(hProcessHandle);
            return pe32.th32ProcessID;
            wcout << pe32.szExeFile << ":" << pe32.th32ProcessID << endl;
        }

    }
    return 0;

}

BOOL LoadDll(DWORD pID,const TCHAR* pName)
{
    HANDLE hDestProcess = OpenProcess(PROCESS_ALL_ACCESS, FALSE, pID);

    DWORD pLEN = sizeof(WCHAR)*wcslen(pName)+1;
    LPVOID lpStart =  VirtualAllocEx(hDestProcess, NULL, pLEN, MEM_COMMIT, PAGE_READWRITE);
    BOOL bRET = WriteProcessMemory(hDestProcess, lpStart, pName, pLEN, NULL);
    if (!bRET)
    {
        cout << "writeprocessmemory failed error : %d" << GetLastError() << endl;
        CloseHandle(hDestProcess);
        return FALSE;
    }
    HMODULE hModule = GetModuleHandle(TEXT("Kernel32.dll"));
    if (!hModule)
    {
        cout << "get kernel32 failed error :" << GetLastError() << endl;
        CloseHandle(hDestProcess);
        return FALSE;
    }
    DWORD f = (DWORD)GetProcAddress(hModule, "LoadLibraryW");
    if (!f)
    {
        cout << "get loadLibraryA failed error :" << GetLastError() << endl;
        CloseHandle(hDestProcess);
        CloseHandle(hModule);
        return FALSE;
    }
    CreateRemoteThread(hDestProcess,NULL,0, (LPTHREAD_START_ROUTINE)f,lpStart,NULL,NULL);
    CloseHandle(hDestProcess);
    CloseHandle(hModule);
    return TRUE;
}

int main()
{
    init();

    const TCHAR* pName = TEXT("game.exe");
    DWORD pid = GetPid(pName);
    wcout << pid << endl;
    TCHAR DLLNAME[] = TEXT("D:\\vs-workspace\\WGDll\\Debug\\WGDll.dll");
    TCHAR* DNAME = DLLNAME;
    BOOL fl = LoadDll(pid, DNAME);
    if (fl)
    {
        cout << "haha" << endl;
    }

    TCHAR gameCmd[] = { L‘A‘,L‘B‘,L‘R‘ };
    TCHAR tempp;
    int randnum = 0;
    for (;;)
    {
        randnum = rand()%3;
        tempp = gameCmd[randnum];
        wcout << tempp << endl;
        CopyMemory(lpBuffer, &tempp,4);
        wmemcpy_s(lpBuffer, 4, &tempp, 1);
        Sleep(2000);
    }
    getchar();
    return 0;
}

原文地址:https://www.cnblogs.com/a-s-m/p/12297825.html

时间: 2024-10-09 02:12:51

Windows进程通信-共享内存空间的相关文章

Windows进程通信 -- 共享内存

享内存的方式原理就是将一份物理内存映射到不同进程各自的虚拟地址空间上,这样每个进程都可以读取同一份数据,从而实现进程通信.因为是通过内存操作实现通信,因此是一种最高效的数据交换方法. 共享内存在 Windows 中是用 FileMapping 实现的,从具体的实现方法上看主要通过以下几步来实现: 1.调用 CreateFileMapping 创建一个内存文件映射对象: HANDLE CreateFileMapping( HANDLE hFile, // handle to file to map

Windows进程通信 -- 共享内存(1)

共享内存的方式原理就是将一份物理内存映射到不同进程各自的虚拟地址空间上,这样每个进程都可以读取同一份数据,从而实现进程通信.因为是通过内存操作实现通信,因此是一种最高效的数据交换方法. 共享内存在 Windows 中是用 FileMapping 实现的,从具体的实现方法上看主要通过以下几步来实现: 1.调用 CreateFileMapping 创建一个内存文件映射对象: HANDLE CreateFileMapping( HANDLE hFile, // handle to file to ma

Linux程序设计学习笔记----System V进程通信(共享内存)

转载请注明出处:http://blog.csdn.net/suool/article/details/38515863 共享内存可以被描述成内存一个区域(段)的映射,这个区域可以被更多的进程所共享.这是IPC机制中最快的一种形式,因为它不需要中间环节,而是把信息直接从一个内存段映射到调用进程的地址空间. 一个段可以直接由一个进程创建,随后,可以有任意多的进程对其读和写.但是,一旦内存被共享之后,对共享内存的访问同步需要由其他 IPC 机制,例如信号量来实现.象所有的System V IPC 对象

Windows进程间共享内存通信实例

抄抄补补整出来 采用内存映射文件实现WIN32进程间的通讯:Windows中的内存映射文件的机制为我们高效地操作文件提供了一种途径,它允许我们在WIN32进程中保留一段内存区域,把硬盘或页文件上的目标文件映射到这段虚拟内存中.注意:在程序实现中必须考虑各进程之间的同步问题. 在Windows操作系统下,任何一个进程不允许读取.写入或是修改另一个进程的数据(包括变量.对象和内存分配等),但是在某个进程内创建的文件映射对象的视图却能够为多个其他进程所映射,这些进程共享的是物理存储器的同一个页面. 因

Linux学习笔记(14)-进程通信|共享内存

共享内存是允许两个不相关的进程访问同一个逻辑内存的进程间通信方法,是在两个正在运行的进程之间共享和传递数据的一种非常有效的方式. 不同进程之间共享的内存通常安排为同一段物理内存.进程可以将同一段共享内存连接到它们自己的地址空间中,所有进程都可以访问共享内存中的地址. 就好像它们是由用C语言malloc()分配的内存一样.

进程通信之内存共享篇

进程通信之_ 内存共享 概念:共享内存是被多个进程共享的一部分物理内存.共享内存是进程间的共享数最快的方法,一个进程向共享内存区域写入数据,共享这个内存区域的所有进程就可以写入数据,所有进程就可以立刻看到其中的内容. 实现步骤;1.创建共享内存,使用shmget函数2.映射共享内存,将这段创建的共享内存映射到具体的进程空间去,使用shmat函数 创建:int shmget (key_t key,int size,int shmflg)key 标识内存功效的键值0/ipc_private.成功返回

Windows环境下共享内存通信

一.引言 在Windows程序中,各个进程之间常常需要交换数据,进行数据通讯.WIN32 API提供了许多函数使我们能够方便高效的进行进程间的通讯,通过这些函数我们可以控制不同进程间的数据交换. 进程间通讯(即:同机通讯)和数据交换有多种方式:消息.共享内存.匿名(命名)管道.邮槽.Windows套接字等多种技术."共享内存"(shared memory)可以定义为对一个以上的进程是可见的内存或存在于多个进程的虚拟地址空间.例如:如果两个进程使用相同的DLL,只把DLL的代码页装入内存

C# .Net 多进程同步 通信 共享内存 内存映射文件 Memory Mapped 转

原文:C# .Net 多进程同步 通信 共享内存 内存映射文件 Memory Mapped 转 节点通信存在两种模型:共享内存(Shared memory)和消息传递(Messages passing). 内存映射文件对于托管世界的开发人员来说似乎很陌生,但它确实已经是很远古的技术了,而且在操作系统中地位相当.实际上,任何想要共享数据的通信模型都会在幕后使用它. 内存映射文件究竟是个什么?内存映射文件允许你保留一块地址空间,然后将该物理存储映射到这块内存空间中进行操作.物理存储是文件管理,而内存

进程-IPC 共享内存和消息队列 (三)

详见:https://github.com/ZhangzheBJUT/linux/blob/master/IPC(%E4%B8%89).md 五 共享内存 5.1. 共享内存简介 共享内存指多个进程共享同一块物理内存,它只能用于同一台机器上的两个进程之间的通信.在进程的逻辑地址空间中有一段地址范围是用来进行内存映射使用的,该段逻辑地址空间可以映射到共享的物理内存地址上(进程空间介绍:http://blog.csdn.net/zhangzhebjut/article/details/3906025