mirror of
https://github.com/rapid7/metasploit-payloads
synced 2024-12-21 05:35:54 +01:00
Beginning of work on the building blocks for PSH->Meterp bindings
This commit is contained in:
parent
6e5afca1b3
commit
ee807408ec
@ -6,7 +6,7 @@
|
||||
#define _METERPRETER_SOURCE_COMMON_COMMON_H
|
||||
|
||||
/*! @brief Set to 0 for "normal", and 1 to "verbose", comment out to disable completely. */
|
||||
//#define DEBUGTRACE 0
|
||||
#define DEBUGTRACE 0
|
||||
|
||||
#include <stdlib.h>
|
||||
#include <stdio.h>
|
||||
|
@ -11,6 +11,7 @@
|
||||
#include "../../ReflectiveDLLInjection/dll/src/ReflectiveLoader.c"
|
||||
|
||||
#include "powershell_bridge.h"
|
||||
#include "powershell_bindings.h"
|
||||
|
||||
// this sets the delay load hook function, see DelayLoadMetSrv.h
|
||||
EnableDelayLoadMetSrv();
|
||||
@ -34,6 +35,7 @@ Command customCommands[] =
|
||||
DWORD __declspec(dllexport) InitServerExtension(Remote *remote)
|
||||
{
|
||||
hMetSrv = remote->met_srv;
|
||||
gRemote = remote;
|
||||
|
||||
DWORD result = initialize_dotnet_host();
|
||||
|
||||
|
47
c/meterpreter/source/extensions/powershell/powershell_bindings.cpp
Executable file
47
c/meterpreter/source/extensions/powershell/powershell_bindings.cpp
Executable file
@ -0,0 +1,47 @@
|
||||
/*!
|
||||
* @file powershell_bindings.cpp
|
||||
* @brief Wrapper functions for bridging native meterp calls to powershell
|
||||
*/
|
||||
extern "C" {
|
||||
#include "../../common/common.h"
|
||||
#include "powershell_bindings.h"
|
||||
}
|
||||
|
||||
Remote* gRemote = NULL;
|
||||
|
||||
VOID MeterpreterInvoke(unsigned int isLocal, unsigned char* input, unsigned int inputLength, unsigned char** output, unsigned int* outputLength)
|
||||
{
|
||||
dprintf("[PSH BINDING] Input %p of %d bytes received", input, inputLength);
|
||||
/*
|
||||
dprintf("[PYTHON] a function was invoked on: %s", self->ob_type->tp_name);
|
||||
const char* packetBytes = NULL;
|
||||
BOOL isLocal = FALSE;
|
||||
Py_ssize_t packetLength = 0;
|
||||
|
||||
PyArg_ParseTuple(args, "is#", &isLocal, &packetBytes, &packetLength);
|
||||
dprintf("[PYTHON] packet %p is %u bytes and is %s", packetBytes, packetLength, isLocal ? "local" : "not local");
|
||||
|
||||
Packet packet = { 0 };
|
||||
packet.header = *(PacketHeader*)packetBytes;
|
||||
packet.payload = (PUCHAR)(packetBytes + sizeof(PacketHeader));
|
||||
packet.payloadLength = (ULONG)packetLength - sizeof(TlvHeader);
|
||||
|
||||
// If the functionality doesn't require interaction with MSF, then
|
||||
// make the packet as local so that the packet receives the request
|
||||
// and so that the packet doesn't get sent to Meterpreter
|
||||
packet.local = isLocal;
|
||||
|
||||
command_handle(gRemote, &packet);
|
||||
|
||||
// really not sure how to deal with the non-local responses at this point.
|
||||
if (packet.partner == NULL)
|
||||
{
|
||||
// "None"
|
||||
return Py_BuildValue("");
|
||||
}
|
||||
|
||||
PyObject* result = PyString_FromStringAndSize(packet.partner->payload, packet.partner->payloadLength);
|
||||
packet_destroy(packet.partner);
|
||||
return result;
|
||||
*/
|
||||
}
|
13
c/meterpreter/source/extensions/powershell/powershell_bindings.h
Executable file
13
c/meterpreter/source/extensions/powershell/powershell_bindings.h
Executable file
@ -0,0 +1,13 @@
|
||||
/*!
|
||||
* @file powershell_bindings.h
|
||||
* @brief Declarations for bindings to meterpreter functions that can be called from Powershell.
|
||||
*/
|
||||
#ifndef _METERPRETER_SOURCE_EXTENSION_POWERSHELL_BINDINGS_H
|
||||
#define _METERPRETER_SOURCE_EXTENSION_POWERSHELL_BINDINGS_H
|
||||
|
||||
extern Remote* gRemote;
|
||||
|
||||
VOID MeterpreterInvoke(unsigned char* input, unsigned int inputLength, unsigned char** output, unsigned int* outputLength);
|
||||
|
||||
#endif
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*!
|
||||
* @file powershell_bridge.c
|
||||
* @file powershell_bridge.cpp
|
||||
* @brief Wrapper functions for bridging native meterp calls to powershell
|
||||
*/
|
||||
extern "C" {
|
||||
|
@ -273,11 +273,13 @@ copy /y "$(TargetDir)$(TargetFileName)" "$(ProjectDir)..\..\output\$(PlatformSho
|
||||
</ItemDefinitionGroup>
|
||||
<ItemGroup>
|
||||
<ClCompile Include="..\..\source\extensions\powershell\powershell.c" />
|
||||
<ClCompile Include="..\..\source\extensions\powershell\powershell_bindings.cpp" />
|
||||
<ClCompile Include="..\..\source\extensions\powershell\powershell_bridge.cpp" />
|
||||
<ClCompile Include="..\..\source\extensions\powershell\powershell_runner.cpp" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<ClInclude Include="..\..\source\extensions\powershell\powershell.h" />
|
||||
<ClInclude Include="..\..\source\extensions\powershell\powershell_bindings.h" />
|
||||
<ClInclude Include="..\..\source\extensions\powershell\powershell_bridge.h" />
|
||||
<ClInclude Include="..\..\source\extensions\powershell\powershell_runner.h" />
|
||||
</ItemGroup>
|
||||
|
148
powershell/MSF.Powershell/Enumerations.cs
Executable file
148
powershell/MSF.Powershell/Enumerations.cs
Executable file
@ -0,0 +1,148 @@
|
||||
using System;
|
||||
|
||||
namespace MSF.Powershell
|
||||
{
|
||||
public enum PacketType
|
||||
{
|
||||
Request = 0,
|
||||
Response = 1,
|
||||
PlainRequest = 10,
|
||||
PlainResponse = 11
|
||||
};
|
||||
|
||||
[Flags]
|
||||
public enum MetaType
|
||||
{
|
||||
None = 0,
|
||||
String = 1 << 16,
|
||||
Uint = 1 << 17,
|
||||
Raw = 1 << 18,
|
||||
Bool = 1 << 19,
|
||||
Qword = 1 << 20,
|
||||
Compressed = 1 << 21,
|
||||
|
||||
Group = 1 << 30,
|
||||
Complex = 1 << 31
|
||||
};
|
||||
|
||||
public enum ExtensionBase
|
||||
{
|
||||
Stdapi = 0,
|
||||
Incognito = 20000,
|
||||
Priv = 20000,
|
||||
Kiwi = 20000
|
||||
};
|
||||
|
||||
public enum TlvType
|
||||
{
|
||||
// Actual types
|
||||
Any = MetaType.None,
|
||||
Method = MetaType.String | 1,
|
||||
RequestId = MetaType.String | 2,
|
||||
Exception = MetaType.Group | 3,
|
||||
Result = MetaType.Uint | 4,
|
||||
|
||||
String = MetaType.String | 10,
|
||||
Uint = MetaType.Uint | 11,
|
||||
Bool = MetaType.Bool | 12,
|
||||
|
||||
Length = MetaType.Uint | 25,
|
||||
Data = MetaType.Raw | 26,
|
||||
Flags = MetaType.Uint | 27,
|
||||
|
||||
ChannelId = MetaType.Uint | 50,
|
||||
ChannelType = MetaType.String | 51,
|
||||
ChannelData = MetaType.Raw | 52,
|
||||
ChannelDataGroup = MetaType.Group | 53,
|
||||
ChannelClass = MetaType.Uint | 54,
|
||||
ChannelParentId = MetaType.Uint | 55,
|
||||
|
||||
SeekWhence = MetaType.Uint | 70,
|
||||
SeekOffset = MetaType.Uint | 71,
|
||||
SeekPos = MetaType.Uint | 72,
|
||||
|
||||
ExceptionCode = MetaType.Uint | 300,
|
||||
ExceptionString = MetaType.String | 301,
|
||||
|
||||
LibraryPath = MetaType.String | 400,
|
||||
TargetPath = MetaType.String | 401,
|
||||
MigratePid = MetaType.Uint | 402,
|
||||
MigrateLen = MetaType.Uint | 403,
|
||||
|
||||
TransType = MetaType.Uint | 430,
|
||||
TransUrl = MetaType.String | 431,
|
||||
TransUa = MetaType.String | 432,
|
||||
TransCommTimeout = MetaType.Uint | 433,
|
||||
TransSessExp = MetaType.Uint | 434,
|
||||
TransCertHash = MetaType.Raw | 435,
|
||||
TransProxyHost = MetaType.String | 436,
|
||||
TransProxyUser = MetaType.String | 437,
|
||||
TransProxyPass = MetaType.String | 438,
|
||||
TransRetryTotal = MetaType.Uint | 439,
|
||||
TransRetryWait = MetaType.Uint | 440,
|
||||
TransGroup = MetaType.Group | 441,
|
||||
|
||||
MachineId = MetaType.String | 460,
|
||||
Uuid = MetaType.Raw | 461,
|
||||
|
||||
CipherName = MetaType.String | 500,
|
||||
CipherParameters = MetaType.Group | 501,
|
||||
|
||||
PeerHost = MetaType.String | 1500,
|
||||
PeerPort = MetaType.Uint | 1501,
|
||||
LocalHost = MetaType.String | 1502,
|
||||
LocalPort = MetaType.Uint | 1503,
|
||||
|
||||
// STDAPI stuff
|
||||
ComputerName = MetaType.String | (ExtensionBase.Stdapi + 1040),
|
||||
OsName = MetaType.String | (ExtensionBase.Stdapi + 1041),
|
||||
UserName = MetaType.String | (ExtensionBase.Stdapi + 1042),
|
||||
Architecture = MetaType.String | (ExtensionBase.Stdapi + 1043),
|
||||
LangSystem = MetaType.String | (ExtensionBase.Stdapi + 1044),
|
||||
Sid = MetaType.String | (ExtensionBase.Stdapi + 1045),
|
||||
Domain = MetaType.String | (ExtensionBase.Stdapi + 1046),
|
||||
LoggedOnUserCount = MetaType.Uint | (ExtensionBase.Stdapi + 1047),
|
||||
|
||||
Mount = MetaType.Group | (ExtensionBase.Stdapi + 1207),
|
||||
MountName = MetaType.String | (ExtensionBase.Stdapi + 1208),
|
||||
MountType = MetaType.Uint | (ExtensionBase.Stdapi + 1209),
|
||||
MountSpaceUser = MetaType.Qword | (ExtensionBase.Stdapi + 1210),
|
||||
MountSpaceTotal = MetaType.Qword | (ExtensionBase.Stdapi + 1211),
|
||||
MountSpaceFree = MetaType.Qword | (ExtensionBase.Stdapi + 1212),
|
||||
MountUncPath = MetaType.String | (ExtensionBase.Stdapi + 1213),
|
||||
|
||||
Pid = MetaType.Uint | (ExtensionBase.Stdapi + 2300),
|
||||
ProcessName = MetaType.String | (ExtensionBase.Stdapi + 2301),
|
||||
ProcessPath = MetaType.String | (ExtensionBase.Stdapi + 2302),
|
||||
ProcessGroup = MetaType.Group | (ExtensionBase.Stdapi + 2303),
|
||||
ProcessArch = MetaType.Uint | (ExtensionBase.Stdapi + 2306),
|
||||
ParentPid = MetaType.Uint | (ExtensionBase.Stdapi + 2307),
|
||||
ProcessSession = MetaType.Uint | (ExtensionBase.Stdapi + 2308),
|
||||
|
||||
// PRIV stuff
|
||||
ElevateTechnique = MetaType.Uint | (ExtensionBase.Priv + 200),
|
||||
ElevateServiceName = MetaType.String | (ExtensionBase.Priv + 201),
|
||||
|
||||
// KIWI stuff
|
||||
KiwiPwdId = MetaType.Uint | (ExtensionBase.Kiwi + 1),
|
||||
KiwiPwdResult = MetaType.Group | (ExtensionBase.Kiwi + 2),
|
||||
KiwiPwdUserName = MetaType.String | (ExtensionBase.Kiwi + 3),
|
||||
KiwiPwdDomain = MetaType.String | (ExtensionBase.Kiwi + 4),
|
||||
KiwiPwdPassword = MetaType.String | (ExtensionBase.Kiwi + 5),
|
||||
KiwiPwdAuthHi = MetaType.Uint | (ExtensionBase.Kiwi + 6),
|
||||
KiwiPwdAuthLo = MetaType.Uint | (ExtensionBase.Kiwi + 7),
|
||||
KiwiPwdLmHash = MetaType.String | (ExtensionBase.Kiwi + 8),
|
||||
KiwiPwdNtlmHash = MetaType.String | (ExtensionBase.Kiwi + 9),
|
||||
|
||||
// INCOGNITO stuff
|
||||
IncognitoListTokensDelegation = MetaType.String | (ExtensionBase.Incognito + 2),
|
||||
IncognitoListTokensImpersonation = MetaType.String | (ExtensionBase.Incognito + 3),
|
||||
IncognitoListTokensTokenOrder = MetaType.Uint | (ExtensionBase.Incognito + 4),
|
||||
IncognitoImpersonateToken = MetaType.String | (ExtensionBase.Incognito + 5),
|
||||
IncognitoGenericResponse = MetaType.String | (ExtensionBase.Incognito + 6),
|
||||
IncognitoUserName = MetaType.String | (ExtensionBase.Incognito + 7),
|
||||
IncognitoPassword = MetaType.String | (ExtensionBase.Incognito + 8),
|
||||
IncognitoServerName = MetaType.String | (ExtensionBase.Incognito + 9),
|
||||
IncognitoGroupName = MetaType.String | (ExtensionBase.Incognito + 10)
|
||||
};
|
||||
}
|
@ -38,8 +38,11 @@
|
||||
</Reference>
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<Compile Include="Enumerations.cs" />
|
||||
<Compile Include="Meterpreter.cs" />
|
||||
<Compile Include="Properties\AssemblyInfo.cs" />
|
||||
<Compile Include="Runner.cs" />
|
||||
<Compile Include="Tlv.cs" />
|
||||
</ItemGroup>
|
||||
<Import Project="$(MSBuildToolsPath)\Microsoft.CSharp.targets" />
|
||||
<!-- To modify your build process, add your task inside one of the targets below and uncomment it.
|
||||
|
@ -1,4 +1,5 @@
|
||||
using System;
|
||||
using MSF.Powershell;
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Text;
|
||||
|
||||
@ -8,10 +9,17 @@ namespace MSF.PowershellTester
|
||||
{
|
||||
static void Main(string[] args)
|
||||
{
|
||||
var x = MSF.Powershell.Runner.Get("Default");
|
||||
System.Console.Write(x.Execute("$x = $(whoami)"));
|
||||
System.Console.Write(x.Execute("$x"));
|
||||
MSF.Powershell.Runner.Remove("Default");
|
||||
//var x = MSF.Powershell.Runner.Get("Default");
|
||||
//System.Console.Write(x.Execute("$x = $(whoami)"));
|
||||
//System.Console.Write(x.Execute("$x"));
|
||||
//MSF.Powershell.Runner.Remove("Default");
|
||||
|
||||
Tlv t = new Tlv();
|
||||
t.Pack(TlvType.ElevateTechnique, 1);
|
||||
t.Pack(TlvType.ElevateServiceName, "abcd1234");
|
||||
|
||||
var x = t.Bytes;
|
||||
var y = 0;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
59
powershell/MSF.Powershell/Meterpreter.cs
Executable file
59
powershell/MSF.Powershell/Meterpreter.cs
Executable file
@ -0,0 +1,59 @@
|
||||
using System;
|
||||
using System.Runtime.InteropServices;
|
||||
using System.Text;
|
||||
|
||||
namespace MSF.Powershell
|
||||
{
|
||||
public static class Meterpreter
|
||||
{
|
||||
private delegate void MeterpreterInvoke(uint isLocal, byte[] input, uint inputSize, ref IntPtr output, ref uint outputSize);
|
||||
|
||||
private static MeterpreterInvoke _callback = null;
|
||||
|
||||
public static void SetInvocationPointer(Int64 callbackPointer)
|
||||
{
|
||||
_callback = (MeterpreterInvoke)Marshal.GetDelegateForFunctionPointer(new IntPtr(callbackPointer), typeof(MeterpreterInvoke));
|
||||
}
|
||||
|
||||
public static string RandomString(int length)
|
||||
{
|
||||
var r = new Random();
|
||||
var chars = "abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789";
|
||||
var bytes = new byte[length];
|
||||
for (int i = 0; i < length; ++i)
|
||||
{
|
||||
bytes[i] = (byte)chars[r.Next(chars.Length)];
|
||||
}
|
||||
|
||||
return Encoding.ASCII.GetString(bytes);
|
||||
}
|
||||
|
||||
internal static byte[] InvokeMeterpreterBinding(bool isLocal, byte[] input)
|
||||
{
|
||||
if (_callback != null)
|
||||
{
|
||||
|
||||
IntPtr output = IntPtr.Zero;
|
||||
try
|
||||
{
|
||||
uint outputLength = 0;
|
||||
_callback(isLocal ? 1U : 0U, input, (uint)input.Length, ref output, ref outputLength);
|
||||
|
||||
var result = new byte[outputLength];
|
||||
Marshal.Copy(output, result, 0, result.Length);
|
||||
|
||||
return result;
|
||||
}
|
||||
finally
|
||||
{
|
||||
if (output != IntPtr.Zero)
|
||||
{
|
||||
Marshal.FreeCoTaskMem(output);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return null;
|
||||
}
|
||||
}
|
||||
}
|
108
powershell/MSF.Powershell/Tlv.cs
Executable file
108
powershell/MSF.Powershell/Tlv.cs
Executable file
@ -0,0 +1,108 @@
|
||||
using System;
|
||||
using System.IO;
|
||||
using System.Net;
|
||||
using System.Text;
|
||||
|
||||
namespace MSF.Powershell
|
||||
{
|
||||
public class Tlv
|
||||
{
|
||||
private MemoryStream _stream = null;
|
||||
|
||||
public byte[] Bytes
|
||||
{
|
||||
get
|
||||
{
|
||||
if (_stream != null)
|
||||
{
|
||||
return _stream.ToArray();
|
||||
}
|
||||
return null;
|
||||
}
|
||||
}
|
||||
|
||||
public Tlv()
|
||||
{
|
||||
_stream = new MemoryStream();
|
||||
}
|
||||
|
||||
public void Pack(TlvType t, bool b)
|
||||
{
|
||||
ValidateMetaType(MetaType.Bool, t);
|
||||
Append(t, b ? new byte[] { 1 } : new byte[] { 0 });
|
||||
}
|
||||
|
||||
public void Pack(TlvType t, uint i)
|
||||
{
|
||||
ValidateMetaType(MetaType.Uint, t);
|
||||
Append(t, ToBytes(i));
|
||||
}
|
||||
|
||||
public void Pack(TlvType t, int i)
|
||||
{
|
||||
ValidateMetaType(MetaType.Uint, t);
|
||||
Append(t, ToBytes(i));
|
||||
}
|
||||
|
||||
public void Pack(TlvType t, Int64 i)
|
||||
{
|
||||
ValidateMetaType(MetaType.Qword, t);
|
||||
Append(t, ToBytes(i));
|
||||
}
|
||||
|
||||
public void Pack(TlvType t, string s)
|
||||
{
|
||||
ValidateMetaType(MetaType.String, t);
|
||||
var value = Encoding.UTF8.GetBytes(s + "\x00");
|
||||
Append(t, value);
|
||||
}
|
||||
|
||||
public void Pack(TlvType t, Tlv tlv)
|
||||
{
|
||||
ValidateMetaType(MetaType.Group, t);
|
||||
var tlvBytes = tlv.Bytes;
|
||||
if (tlvBytes != null)
|
||||
{
|
||||
Append(t, tlv.Bytes);
|
||||
}
|
||||
}
|
||||
|
||||
public void Pack(TlvType t, byte[] value)
|
||||
{
|
||||
ValidateMetaType(MetaType.Raw, t);
|
||||
Append(t, value);
|
||||
}
|
||||
|
||||
private void Append(TlvType t, byte[] value)
|
||||
{
|
||||
var type = ToBytes((int)t);
|
||||
var length = ToBytes(value.Length);
|
||||
_stream.Write(length, 0, length.Length);
|
||||
_stream.Write(type, 0, type.Length);
|
||||
_stream.Write(value, 0, value.Length);
|
||||
}
|
||||
|
||||
private void ValidateMetaType(MetaType expected, TlvType actual)
|
||||
{
|
||||
if ((MetaType)((TlvType)expected & actual) != expected)
|
||||
{
|
||||
throw new ArgumentException("Invalid Meta type given");
|
||||
}
|
||||
}
|
||||
|
||||
private byte[] ToBytes(Int64 i)
|
||||
{
|
||||
return BitConverter.GetBytes(IPAddress.HostToNetworkOrder(i));
|
||||
}
|
||||
|
||||
private byte[] ToBytes(int i)
|
||||
{
|
||||
return BitConverter.GetBytes(IPAddress.HostToNetworkOrder(i));
|
||||
}
|
||||
|
||||
private byte[] ToBytes(uint i)
|
||||
{
|
||||
return BitConverter.GetBytes(IPAddress.HostToNetworkOrder(i));
|
||||
}
|
||||
}
|
||||
}
|
Loading…
Reference in New Issue
Block a user