[远程Call]32位远程多参数带返回调用

引子

在Windows上可以使用CreateRemoteThread实现远程Call,但是有不带返回值且只能传递一个参数的限制。

解决思路

将多个参数利用VirtualAllocEx和WriteProcessMemory写入目标程序,再通过此方法注入一段shellcode,通过shellcode完成多参数的调用。

核心shellcode
push var_1
...
push var_n
mov eax,function_addr
/*
如果为 cdcel则需要平栈
add esp,count_param
*/
call eax
实现c++代码
#include <iostream>
#include <Windows.h>
#include <vector>
#include <thread> using namespace std; LPVOID RemoteNew(HANDLE hProcess, PUCHAR data,size_t size)
{
auto hMem=VirtualAllocEx(hProcess, NULL, size, MEM_COMMIT, PAGE_EXECUTE_READWRITE);
if (hMem == NULL)
{
return FALSE;
}
if (WriteProcessMemory(hProcess, hMem, data, size,NULL) == FALSE)
{
VirtualFreeEx(hProcess, hMem, 0, MEM_RELEASE);
return FALSE;
}
return hMem;
} BOOL RemoteCall(
HANDLE hProcess,
LPVOID remoteFuncAddr,
vector<LPVOID> param,
bool cdcelCall,
bool waitRemoteThread
)
{
if (remoteFuncAddr == NULL)
return FALSE; vector<UCHAR> shellcode;
//push 结构 for (int i = param.size() - 1; i >= 0; i--)//调用栈是个栈
{
if (((UINT)param[i]) <= 255) //小参数可以只传低位
shellcode.push_back(106), shellcode.push_back((UCHAR)param[i]); //push byte
else
shellcode.push_back(104), shellcode.insert(shellcode.end(), (PUCHAR)&param[i], (PUCHAR)(&param[i] + 1)); //push dword
}
//把addr塞入寄存器
shellcode.push_back(184); //mov
shellcode.insert(shellcode.end(), (PUCHAR)&remoteFuncAddr, (PUCHAR)(&remoteFuncAddr + 1)); //eax,addr
shellcode.push_back(255),shellcode.push_back(208);//call eax if (cdcelCall)
{
size_t paramSize = param.size() * sizeof(LPVOID);
//cdcel是函数调用后平栈,stdcall是函数自己平
shellcode.push_back(129), shellcode.push_back(196);//add esp
shellcode.insert(shellcode.end(), (PUCHAR)&paramSize, (PUCHAR)(&paramSize + 1));
}
shellcode.push_back(195);//ret
auto shellcodeAddr=RemoteNew(hProcess, shellcode.data(), shellcode.size() * sizeof(UCHAR));
if (shellcodeAddr == NULL)
return FALSE; auto hThread=CreateRemoteThread(hProcess, NULL, 0, (LPTHREAD_START_ROUTINE)shellcodeAddr, NULL, NULL, NULL);
if (hThread == NULL)
{
VirtualFreeEx(hProcess, shellcodeAddr, 0, MEM_RELEASE);
return FALSE;
} thread waiter([hThread, hProcess, shellcodeAddr] {
WaitForSingleObject(hThread, INFINITE);
VirtualFreeEx(hProcess, shellcodeAddr, 0, MEM_RELEASE);
DWORD retCode;
GetExitCodeThread(hThread, &retCode);
cout <<"Ret: " << retCode << endl;
});
if (waitRemoteThread)
waiter.join();
else
waiter.detach(); return TRUE;
} int add(int a, int b)
{
return a + b;
} int main()
{
char a[] = "hello world";
char b[] = "C++ YES"; //-1是自己
RemoteCall((HANDLE)-1, add, { (LPVOID)1,(LPVOID)3 }, true, true); auto p1 = RemoteNew((HANDLE)-1, (PUCHAR)a, sizeof(a));
auto p2 = RemoteNew((HANDLE)-1, (PUCHAR)b, sizeof(b));
RemoteCall((HANDLE)-1, MessageBoxA, { 0, p1,p2,(LPVOID)64 }, true, true); std::cout << "Hello World!\n";
Sleep(-1);
}
实现缺陷
  1. 目前只能实现32位的远程调用,64位新增了内存的可执行权限,这样注入的shellcode没法执行。

  2. 返回值只能接受32位整数,其实实现64位整数和浮点的方法也不复杂,都可以用汇编把对应寄存器的值写到内存里,但是情况比较多,懒得写了。

[远程Call]32位远程多参数带返回调用的更多相关文章

  1. VBA: 带参数带返回值的函数

    Function pda(x) a = x If Len(a) = 1 Then ab = "00" & a ElseIf Len(a) = 2 Then ab = &qu ...

  2. 32位的Win7系统下安装64位的Sql Sever?

    来自:http://zhidao.baidu.com/link?url=nQBoaLgoOyYCUdI7V4WZCMlTW3tKscdkOnLTIvlYtPpwoVhQkSahq44HeofBfzFT ...

  3. Linux:使用rpcgen实现64位程序调用32位库函数

    摘要:本文介绍使用rpcgent实现64位程序调用32位库函数的方法,并给出样例代码. 我的问题 我的程序运行在64位Linux系统上,需要使用一个从外部获得的共享库中的函数,这个共享库是32位的,无 ...

  4. IOS是否存在32位和64位版本的区分

    苹果于2013年9月推出了iPhone 5S新手机,采用的全新A7处理器其最大特色就是支持64位运算.其64位A7处理器的使用意味着iPhone性能会大有提高,性能和速度更加出色:而要到达到这样的性能 ...

  5. CLR调试报错“Visual Studio远程调试监视器 (MSVSMON.EXE) 的 64 位版本无法调试 32 位进程或 32 位转储。请改用 32 位版本”的解决

    Win7 64位电脑上进行visual studio的数据库项目的CLR存储过程进行调试时,报错: ---------------------------Microsoft Visual Studio ...

  6. Visual Studio远程调试监视器(MSVSMON.EXE)的32位版本不能用于调试64位进程或64位转储

    在VS2013中调试Silverlight项目时,提示:无法附加.Visual Studio远程调试监视器(MSVSMON.EXE)的32位版本不能用于调试64位进程或64位转储.请改用64位版本. ...

  7. 使用visual c++ 2005远程调试64位系统上32位与64位程序

    一直都挺喜欢使用visual c++远程调试代码,它能展现给我们当时代码执行最真实的情景,今天有时间记录一下,以免以后忘了. 远程调试需要在被调试端安装服务器,对于visual c++ 2005来说调 ...

  8. mysql 远程连接不上,bind-address参数配置要求,以及怎么去使得mysql能够允许远程的客户端访问

    刚安装了MySQL服务器,使用远程管理工具总是连接不上,因为知道mysql的默认端口是3306,于是使用telnet连接这个端口,(从这里可以学到telnet是可以这样用的) telnet 192.1 ...

  9. Photoshop做32位带Alpha通道的bmp图片

    原文链接: http://blog.sina.com.cn/s/blog_65c0cae801016e5u.html   批量制作32位带Alpha通道的bmp图片,可以制作一个动作,内容可以如下: ...

  10. 论DATASNAP远程方法支持自定义对象作参数

    论DATASNAP远程方法支持自定义对象作参数 DATASNAP远程方法已经可以支持自定义对象作参数,这是非常方便的功能. 1)自定义对象 type TMyInfo = class(TObject) ...

随机推荐

  1. C# 中的“智能枚举”:如何在枚举中增加行为

    目录 枚举的基本用法回顾 枚举常见的设计模式运用 介绍 智能枚举 代码示例 业务应用 小结 枚举的基本用法回顾 以下是一个常见的 C# 枚举(enum)的示例: enum Weekday { Mond ...

  2. 在使用abaqus时可能会遇到的一些问题

    ​我收集了一些网友及客户在使用abaqus软件时遇到的一些问题,下面来看看是如何解决的~ (1)Linux平台使用Abaqus子程序的免费方案 gcc+gfortran 本方法在centos7和cen ...

  3. 【python基础】基本数据类型-字符串类型

    1.初识字符串 字符串就是一系列字符.在python中,用引号括起来文本内容的都是字符串. 其语法格式为:'文本内容'或者"文本内容" 我们发现其中的引号可以是单引号,也可以是双引 ...

  4. VuePress v2.0 项目创建

    VuePress v2.0 项目创建 参考:VuePress v2.0 文档 1.创建文件夹 我创建了一个文件夹,然后在文件夹中打开了powershell E:\2023个人项目\terramours ...

  5. Nucleic Acids Research上关于生物医学分析Galaxy平台在几个独立面上的最新发展。 该平台的官方主服务器拥有超过124000注册用户,每月新注册用户~2000。平均而言,......

    本文分享自微信公众号 - 生信科技爱好者(bioitee).如有侵权,请联系 support@oschina.cn 删除.本文参与"OSC源创计划",欢迎正在阅读的你也加入,一起分 ...

  6. 逍遥自在学C语言 | 指针函数与函数指针

    前言 在C语言中,指针函数和函数指针是强大且常用的工具.它们允许我们以更灵活的方式处理函数和数据,进而扩展程序的功能. 本文将介绍指针函数和函数指针的概念,并讲解一些常见的应用示例. 一.人物简介 第 ...

  7. 迟来的秋招面经,17家公司,Java岗位

    一位朋友秋招面试了17家公司(都是中小公司或者银行),Java 后端岗.下面是他的个人情况.求职经验已经这17家公司的面经. 个人情况和求职经验 其实现在是挺后悔大学没有好好的学习的,因为基本上都会提 ...

  8. Java正三角、倒三角

    正三角 public static void main(String[] args) { // 正三角 int num = 8; for(int i = 1;i<=num;i++) { for( ...

  9. Python随机数据生成——Faker的使用

    安装Faker pip install faker 导入模块及基本配置 # 导入Faker from faker import Faker # 初始化,设置locale为中文:默认是英文 fake = ...

  10. 11k+ Star 一款更适合中国用户的开源 BI 工具

    在当今数字化时代,数据分析和可视化成为企业决策和发展的重要支撑,很多 BI 工具昂贵的许可费用,让许多中小型企业用户和个人用户望而却步,开源 BI 工具的出现,让其成为很多用户进行数据分析展示的首选. ...