当前位置:网站首页>shellcode编写(未完)
shellcode编写(未完)
2022-07-28 14:16:00 【[email protected]】
一:基本
对于shellcode来说,它是独立的,可以附加在各种各样的进程中,所以他的每句代码都是独立,只与shellcode中的代码有联系,与外部代码都是隔绝的。
在生成exe的时候,编译器将函数转为真正实现这个函数功能的入口地址(绝对地址),由于shellcode是附加在其他进程上的,每个进程是不一样的,这个地址可能是其他功能,所以运用绝对地址不符合。所以需要动态调用,先获得函数的地址,在进行执行。
类似于这种:
GetProcAddress(LoadLibraryA(“kernel32.dll”), “CreateFileA”);
但是,LoadLibraryA与GetProcAddress的地址也需获取,在windows操作系统下,每一个进程都会对ntdll、kernel32、kernelbase做一个系统内部的加载,所以只需寻找内部加载的地址,就可以得到LoadLibraryA(“kernel32.dll”)的地址。
1,得到LoadLibraryA(“kernel32.dll”)
FS寄存器指向当前活动线程的TEB结构(线程结构)
偏移 说明
000 指向SEH链指针
004 线程堆栈顶部
008 线程堆栈底部
00C SubSystemTib
010 FiberData
014 ArbitraryUserPointer
018 FS段寄存器在内存中的镜像地址
020 进程PID
024 线程ID
02C 指向线程局部存储指针
030 PEB结构地址(进程结构)
034 上个错误号
偷了张图片:
模块在内存顺序:
__declspec(naked) DWORD getKernel32()
{
__asm
{
mov eax,fs:[30h] //得到PEB
mov eax,[eax+0ch] //PEB_LDR_DATA
mov eax,[eax+14h] //得到inmemoryodermodulelist,第一个模块
mov eax,[eax]
mov eax,[eax] //第三个模块kernel32.dll
mov eax,[eax+10h] //得到Baseaddress,kernel的基址
ret
}
}
2,得到GetProcAddress地址
GetProcAddress这个函数也在kernel32中,
FARPROC _GetProcAddress(HMODULE hModuleBase)
{
PIMAGE_DOS_HEADER lpDosHeader = (PIMAGE_DOS_HEADER)hModuleBase;
PIMAGE_NT_HEADERS32 lpNtHeader = (PIMAGE_NT_HEADERS)((DWORD)hModuleBase + lpDosHeader->e_lfanew);
if (!lpNtHeader->OptionalHeader.DataDirectory[IMAGE_DIRECTORY_ENTRY_EXPORT].Size){
return NULL;
}
if (!lpNtHeader->OptionalHeader.DataDirectory[IMAGE_DIRECTORY_ENTRY_EXPORT].VirtualAddress) {
return NULL;
}
PIMAGE_EXPORT_DIRECTORY lpExports = (PIMAGE_EXPORT_DIRECTORY)((DWORD)hModuleBase + (DWORD)lpNtHeader->OptionalHeader.DataDirectory[IMAGE_DIRECTORY_ENTRY_EXPORT].VirtualAddress);
PDWORD lpdwFunName = (PDWORD)((DWORD)hModuleBase + (DWORD)lpExports->AddressOfNames);
PWORD lpword = (PWORD)((DWORD)hModuleBase + (DWORD)lpExports->AddressOfNameOrdinals);
PDWORD lpdwFunAddr = (PDWORD)((DWORD)hModuleBase + (DWORD)lpExports->AddressOfFunctions);
DWORD dwLoop = 0;
FARPROC pRet = NULL;
for (; dwLoop <= lpExports->NumberOfNames - 1; dwLoop++) {
char* pFunName = (char*)(lpdwFunName[dwLoop] + (DWORD)hModuleBase);
if (pFunName[0] == 'G'&&
pFunName[1] == 'e'&&
pFunName[2] == 't'&&
pFunName[3] == 'P'&&
pFunName[4] == 'r'&&
pFunName[5] == 'o'&&
pFunName[6] == 'c'&&
pFunName[7] == 'A'&&
pFunName[8] == 'd'&&
pFunName[9] == 'd'&&
pFunName[10] == 'r'&&
pFunName[11] == 'e'&&
pFunName[12] == 's'&&
pFunName[13] == 's')
{
pRet = (FARPROC)(lpdwFunAddr[lpword[dwLoop]] + (DWORD)hModuleBase);
break;
}
}
return pRet;
}
3,字符串打散
字符串常量是一个固定地址,之前提到,为了避免使用绝对地址,改为使用字符数组,并且最后记得加上截断字符,避免越界。
4,函数生成位置
在单文件中,函数地址顺序与在代码编辑时的函数定义顺序有关。
在多文件中,在这个vcxproj下面。
二,编写shellcode
基本框架:
#include "pch.h"
#include <windows.h>
#include <stdio.h>
FARPROC getProcAddress(HMODULE hModuleBase);
DWORD getKernel32();
int EntryMain()
{
//声明定义GetProcAddress
typedef FARPROC(WINAPI *FN_GetProcAddress)(
_In_ HMODULE hModule,
_In_ LPCSTR lpProcName
);
//获取GetProcAddress真实地址
FN_GetProcAddress fn_GetProcAddress = (FN_GetProcAddress)getProcAddress((HMODULE)getKernel32());
//声明定义CreateFileA
typedef HANDLE(WINAPI *FN_CreateFileA)(
__in LPCSTR lpFileName,
__in DWORD dwDesiredAccess,
__in DWORD dwShareMode,
__in_opt LPSECURITY_ATTRIBUTES lpSecurityAttributes,
__in DWORD dwCreationDisposition,
__in DWORD dwFlagsAndAttributes,
__in_opt HANDLE hTemplateFile
);
//将来的替换,地址全部动态获取
//FN_CreateFileA fn_CreateFileA = (FN_CreateFileA)GetProcAddress(LoadLibrary("kernel32.dll"), "CreateFileA");
//带引号的字符串打散处理
char xyCreateFile[] = {
'C','r','e','a','t','e','F','i','l','e','A',0 };
//动态获取CreateFile的地址
FN_CreateFileA fn_CreateFileA = (FN_CreateFileA)fn_GetProcAddress((HMODULE)getKernel32(), xyCreateFile);
char xyNewFile[] = {
'1','.','t','x','t','\0' };
fn_CreateFileA(xyNewFile, GENERIC_WRITE, 0, NULL, CREATE_ALWAYS, 0, NULL);
}
版权声明
本文为[[email protected]]所创,转载请带上原文链接,感谢
https://blog.csdn.net/qq_38641816/article/details/106932578
边栏推荐
- Modify the default path of Jupiter notebook
- PHP magic method
- Instructions for common symbols in kotlin
- Shader顶点着色器修改顶点高度的一个思路
- Is the expansion operator a deep copy or a shallow copy
- UTF-8、UTF-16 和 UTF-32 字符编码之间的区别?[图文详解]
- What are the main threats to cloud security
- Word creates a title list with automatic numbering
- idea调试burpsuit插件
- Find papers and their open source code
猜你喜欢

Compose learning notes 1-compose, state, flow, remember

SSRF vulnerability

Establishment and traversal of binary tree (implemented in C language)

Mlx90640 infrared thermal imager sensor module development notes (VIII)

The automatic prompt of vs code code is missing - a tick to solve it

21、 TF coordinate transformation (I): coordinate MSG message

Xiaobai can understand the 35 necessary questions in MySQL interview

Chapter II linear table

使用cpolar发布树莓派网页(apache2网页的发布)
Gradle -- package multiple variants with gradle
随机推荐
JS -- realize the rotation chart (complete function)
22、 TF coordinate transformation (II): static coordinate transformation
Mlx90640 infrared thermal imager sensor module development notes (VIII)
How to conduct risk assessment related to intellectual property rights
Examples of Pareto optimality and Nash equilibrium
Google lab usage notes
9、 C array explanation
VTK vtkcontourwidget extracts regions of interest
PS modify the length and width pixels and file size of photos
拓展运算符是深拷贝还是浅拷贝
3559. 围圈报数
安装mosek,license安装位置查找
Enumeration type
MySQL authorization method
4、 C language operators
MITK creates plug-ins and generates plug-ins
云计算需要考虑的安全技术列举
NCBI experience accumulation
Instant experience | further improve application device compatibility with cts-d
10、 C enum enumeration