Executing Shellcode In C#
This was a topic that was brought up on Tuts4You here:
https://forum.tuts4you.com/topic/39503-getting-peb-in-c/
I Google’d around and could not find a single instance of doing this in C# within the parameters given by the poster so I took to some ideas in mind of how I could allocate memory without any imports.
Some ideas that came to mind were:
- Marshal.AllocHGlobal
- Marshal.AllocCoTaskMem
- MemoryStream
Sadly, all three of these options only allocate the memory that have protection flags of PAGE_READ and PAGE_WRITE with no ability to execute.
Next, I thought of memory mapped files, these are a way to share memory between processes. This API allows you to specify the access type of the file, including execution permissions. C# has this built-in via the ‘System.IO.MemoryMappedFiles’ namespace within the System.Core.dll module.
Using this namespace, we can create a mapped file in memory, write our shellcode to it, create a function delegate to the function and invoke it. Here’s an example of doing this, getting the PEB of the process (32bit):
/**
* C# Shellcode Example
* (c) 2017 atom0s [atom0s@live.com]
*
* Demonstrates how to invoke shellcode within C# using a memory mapped file.
*/
namespace ShellcodeExample
{
using System;
using System.IO.MemoryMappedFiles;
using System.Runtime.InteropServices;
class Program
{
/// <summary>
/// Function delegate to invoke the shellcode.
/// </summary>
/// <returns></returns>
private delegate IntPtr GetPebDelegate();
/// <summary>
/// Shellcode function used to obtain the PEB of the process.
/// </summary>
/// <returns></returns>
private unsafe static IntPtr GetPeb()
{
var shellcode = new byte[]
{
0x64, 0xA1, 0x30, 0x00, 0x00, 0x00, // mov eax, dword ptr fs:[30]
0xC3 // ret
};
MemoryMappedFile mmf = null;
MemoryMappedViewAccessor mmva = null;
try
{
// Create a read/write/executable memory mapped file to hold our shellcode..
mmf = MemoryMappedFile.CreateNew("__shellcode", shellcode.Length, MemoryMappedFileAccess.ReadWriteExecute);
// Create a memory mapped view accessor with read/write/execute permissions..
mmva = mmf.CreateViewAccessor(0, shellcode.Length, MemoryMappedFileAccess.ReadWriteExecute);
// Write the shellcode to the MMF..
mmva.WriteArray(0, shellcode, 0, shellcode.Length);
// Obtain a pointer to our MMF..
var pointer = (byte*)0;
mmva.SafeMemoryMappedViewHandle.AcquirePointer(ref pointer);
// Create a function delegate to the shellcode in our MMF..
var func = (GetPebDelegate)Marshal.GetDelegateForFunctionPointer(new IntPtr(pointer), typeof(GetPebDelegate));
// Invoke the shellcode..
return func();
}
catch
{
return IntPtr.Zero;
}
finally
{
mmva?.Dispose();
mmf?.Dispose();
}
}
/// <summary>
/// Entry point.
/// </summary>
/// <param name="args"></param>
static void Main(string[] args)
{
var peb = GetPeb();
Console.WriteLine("PEB is located at: {0:X8}", peb.ToInt32());
}
}
}
Comments