Thnks4RWX
Compile an implant with RWX sections of memory to simulate a dropper with dynamic functionality in its own .text section
Last updated
Compile an implant with RWX sections of memory to simulate a dropper with dynamic functionality in its own .text section
Last updated
Like we've talked about in my discussions about assembly (especially inline assembly), it's increasingly harder to successfully execute malicious code from unbacked RX or RWX sections of memory. In my writeup called TTPs:BadAsm we used inline assembly labels to clobber some sacrificial bytes so we could execute shellcode from the .text section of memory. This technique is pretty interesting, and implies the existence of a host of new capabilities centered around the use of inline assembly that we'll continue to use in this blog. But it was one major shortfall: we have to use the MinGW compiler.
MinGW is a useful capability, but it detracts from the utility of our technique because the defacto standard for malware development are the Visual Studio and Visual Studio Code platforms. Visual Studio in particular does not provide support for MinGW and inline assembly is not supported in the MSVC compiler for visual studio.
However, that doesn't mean we're entirely out of options. In this article, we're going to talk about function hollowing and the options it provides us for malware development and payload execution from inside the .text section of our program.
We begin our development by creating a new Visual Studio project that looks something like this:
We can use the below template code to get started. It's important to note here that this technique revolves around using the /OPT:REF option
Next you can implement code that functions like this:
And if we open up our program in x64dbg, we'll see that our function pointer gives us access to our HollowFunction!
Now that we have seen that we can get an address in our .text section, we can actually do something pretty interesting. We can compile our program with a RWX .text section and use our function pointer to overwrite our hollow function and execute malicious payloads!
It's best to turn off optimizations and compile in Release mode to get more consistent performance.
Now, we can use the following code template to execute our shellcode at the HollowFunction address we found earlier.
In this writeup we used a function pointer and a RWX .text section to inject and execute our payload into the .text section of our program. I am continuing to explore making other areas of memory RWX at compile time, and continue to get surprising results.
It appear that a lot of AV/EDR behavior definitions rely on standard compilation options and do not account for non-standard permissions in different areas of memory. This technique should continue to be explored and refined to allow for the execution of more stable payloads.
https://github.com/0xTriboulet/Red_Team_Code_Snippets/tree/main/Cpp/bad_fn_ptr