Saturday, February 15, 2020

Sifting Through ETW for Persistence in C#


Continuing my deep dive into how .NET can be used maliciously, this blog post will cover hunting for and detecting persistence created by a toolkit written in C#.

While persistence is considered what some refer to as "right of boom/breach", its importance cannot be understated for an attacker. If the attacker cannot maintain a hold on the system to move laterally and exfiltrate data, all is lost.


Today I will be looking at the SharPersist toolkit by Brett Hawkins ( There are a number of ways to establish persistence in Windows environments,  via the registry, services and startup folder. With multiple detection opportunities in place for PowerShell, it only seems right to start looking for alternate means of holding onto access.

SharPersist offers a number of options to create persistence, for this post we will focus on creating a service. On one side, detecting a new service should be relatively easy with logging in place, but without event tracing, visibility into .NET execution is severely limited.

What do All These Event Logs Mean?

While not ideal, all logging was conducted on the target Windows 10 system due to the amount of logs generated by event tracing. Our fictitious story begins after some log analysis identifies a new service installed on the system via Event ID 4697.

Figure 1

Okay, so the file name for service information is definitely interesting and will require some further digging. Since we are auditing the registry, we are able to identify when a value is set/modified. When there is a change to the registry, specifically the Services hive, this notifies the analyst that someone or something has attempted to modify the configuration of a service.

Figure 2

I think if I had to choose just one event ID from Sysmon, it would be EID 1. In the log for process creation, an analyst can note the image, the full command executed as well as the parent image for the process. As seen below in Figure 3, we can now identify the application responsible for this new service, as well as find out what application ran the executable.

Figure 3

Unfortunately, this is where information on SharPersist ends. To gain more visibility into what exactly this is tool doing and to start creating detections based on anomalous behavior, we turn to event tracing for the Microsoft Windows DotNet Runtime channel.

Tracing All The Things

After installing and setting up SilkETW to run as a service, I adjusted the configuration file to log all events to an event log which could be opened in Event Viewer. Event tracing provides a view into .NET that most may not be ready for. While there is a wealth of information to be pulled out of ETW, it takes almost as much time to filter out what really is important to the analyst and what strays away from "normal".

To wade through all the logs that event tracing provides, I want to focus on monitoring events  that should stand out from what we know as normal:

  - Image/Module & Assembly loading
  - Use of P/Invoke and follow on calls to Win32 API's
  - Loading of .NET DLL's that may be unusual (mscoree, mscorelib, clr, ...)
  - Processes loading .NET assemblies that do not usually load them

This list is by no means all inclusive, but is a good starting point to detect out of the ordinary behavior from .NET.

Figure 4
Above we can see the Assembly Loading for the SharPersist tool. As I stated earlier, we have to filter out the noise to get to the parts of the log that are important.

Figure 5
Again, we can view the command line for the created service, but if you look real hard you can see *clr.dll (.NET Common Language Runtime or CLR) has been loaded by the SharPersist process. Some processes may invoke CLR, whether the event is malicious or not requires further digging and knowing your environment.

Figure 6
The use of P/Invoke allows developers to call Windows API's (unmanaged) to interact with managed code. When discussing P/Invoke for offensive purposes, think of any Win32 API you may need and what you can do with it.

In Figure 6 we can also see a number of SharPersist libraries that are called, but more importantly references to the Service Control Manager. Putting all the pieces together, we can start to understand the purpose of the SharPersist tool that created the "FINDME" service.

Figure 7

To declare P/Invoke, we need to include the "using System.Runtime.InteropServices;" namespace. In addition to the numerous libraries for Service Control  called in Figure seven, the "CreateService" method should remove any more doubt we have as to what created the service.


Piecing the above events together and zeroing in on the suspicious calls to the Service Control Manager class and abused DLL's, we have enough information to initiate an incident response. While it is highly unlikely an attacker would drop the SharPersist tool on the system, I believe this was a successful exercise in using ETW to identify malicious indicators.

The SharPersist toolkit offers many paths to create persistence along with some interesting tradecraft options. Combined with the numerous tools being created for .NET exploitation, I plan to keep digging into ways to identify malicious use of the framework.

As I continue learning about C# tradecraft, I plan to focus more on creating solid detections and how the use of Dynamic Invoke over P/Invoke effects visibility. Below are some links to interesting articles if your interested.



Thursday, February 6, 2020

Putting a Spotlight on CSI… the Binary, Not the Show

6 Feb 2020

While PowerShell is likely to be the go to for threat actors looking to gain an initial foothold, the power of .NET development tools cannot go overlooked. A few of these tools come native with a fresh download of Visual Studio and allow for unsigned C# code to be executed.

The focus of this post will be on csi.exe, which provides an interactive console to run C# scripts (.csx). Even for someone like me still learning, C# script files are unbelievably easy to whip up and run. The usual path for csi.exe is:

- C:\Program Files(x86)\Microsoft Visual Studio\2019\Community\MSBuild\Current\Bin\Roslyn\

You may be saying, 'This comes with VS? Who cares, that means it's trusted".  A few lines of C# can be executed with the same ease as in the VS IDE. If this doesn't get your attention, what if I told you there isn't a great deal of visibility into this tool?

Thursday, November 21, 2019

Easy Wins for All…Slowing Attacks With the Basics


The below was conducted in my home lab, configurations may/may not scale to an enterprise network. A good bit of work still needs to be done to the policies and configuration files.

It seems like nearly everyday a new "NextGen" product is debuted with the latest bells and whistles to stop the next APT attack.  Not many of us have the resources to update infrastructure to the latest and greatest, nor have time for a defense team to learn the product. With a majority of attacker gaining access to networks by way of LOLBINS/LOLBAS, natively on Windows, why not protect/prevent those same attacks with native tools?

Tuesday, October 8, 2019

Tracing The Route of A Malicious Document

08 Oct 2019

This post will follow on from where my last one left off. I did a quick analysis of a malicious Word document that turned out to be a RTF document with a whole lot of flare. While digging more into the C# code buried in the Excel file that was part of the document, I came across a couple awesome posts/talks:

The above resources were a great help in understanding how to detect .NET malware. Not knowing a thing about C# or the .NET framework, I installed SilkETW ( and went to work in my lab.

This post will not go into the specifics of event tracing for Windows (ETW) or the software needed to get your hunt on. The authors above dropped enough knowledge bombs and step-by-step instructions to keep you busy for a while. As I said, I utilized SilkETW, set up the program to use SilkService, identified providers, and sent the output from the collectors to a separate server running Splunk.

In addition to introducing myself to the providers, I must say that the output of the collectors is quite overwhelming and may take a while to determine what is malicious and what is benign.

Going back in time, below is the C# code that is executed as part of the malicious document.

Figure 1

Detection, on Detection, on Detection

As identified in the last post, the above code is executed via Powershell which in turn calls on csc.exe to compile the code. There are two function calls that are especially interesting; RtlMoveMemory,  and Marshal.Copy. The first function as the name implies, has the ability to move unmanaged memory into a destination memory block. In this case kernel32.dll is called.

The second function is similar to the first, however its purpose is to move unmanaged memory to an unmanaged memory array or managed array. While I am sure that little lesson was not the most exciting, what we do know is that this malicious code is making use of unmanaged memory blocks to weasel it's way into networks.

Before we start looking at ETW output, I wanted to touch on some interesting finds using everyday tools.

Figure 2

The above figure depicts the process tree starting with Powershell, but also briefly catching the execution of csc.exe.

If we hover over the currently running PS process, we can view the obfuscated code that was caught by script block logging. Note* I ran (detonated) the sample a few times, hence the multiple instances of PS running.

Figure 3

Looking deeper into the PowerShell process properties reveals additional information that may stand out to us.

Figure 4
I am not 100% positive, but I don't think wmic spawning PowerShell is normal activity and would constitute anomalous actions. Before sounding the alarm, this particular find may have to be analyzed across the network and what is normal for computers with specific roles (admins).

If you remember the last post, the above PowerShell command kicked off a GET request to a malicious domain with no User-Agent. Again not earth shattering, but worth taking a deeper look.

The PowerShell and wmic pairing will come into play again later when we get into analyzing output from our traces of the system.

The last item in our look at the PowerShell properties deals with .NET Assemblies. The loading of .NET runtime DLL's may not be anomalous in all cases, but this seems like it may be one of those events.

Figure 5

The Assemblies tab allows for the viewing of event assembly loads. Normally, each assembly loaded would include a path. The lack of a path for an assembly load could possibly indicate in-memory evasion.

Please note at the bottom of the above figure that "swvggacb" has no path and is a dynamically loaded assembly. Although this sample does not utilize Cobalt Strike, a great series on in-memory evasion can be found at: .

Event Tracing For Windows FTW?

While setup  and ensuring logs were flowing was relatively straight-forward and very user friendly, a few things about collecting ETW have to be stated.

Before you start ingesting the logs into your SIEM of choice, it may be smart to first filter exactly what you are hunting for.  I collected the following providers Microsoft-Windows-WMI, Microsoft-Windows-PowerShell, and Microsft-DotNetRuntime. In the short time I started the SilkService and ran the malicious sample, my splunk instance received 50k+ events!

After reading some of the above posts, I decided to have my WMI events output to a json file. Again, this was a very noisy file and quickly grew in size. Thanks to @IISReseMe 's blog, parsing the JSON file via PowerShell was pretty easy.

Figure 6

As seen in @mattifestation 's slides, when it comes to WMI detection, EventID 23 is a good place to start.  I ran a couple of tests prior to running the malware to ensure everything was working. Nevertheless, we can see there are at least a few events that may be worth looking at.

It should be noted that the other events are just as important as EventID23.  For example, EvenID 5858 logs all WMI query errors.

Figure 7

While the above query may seem harmless, there were a number of other query errors that when combined can provide an adversary with valuable information.

The above query could provide an attacker with particular software and hardware installed on a system. This could identify sandboxes or virtual machines, which could result in the malicious program stopping/deleting itself.

Moving back to our EvenID23 cases, some quick PowerShell can provide us with the client ID and commandline parameter used.

Figure 8

WMI and PowerShell may be utilized heavily on your network, but is there really a reason to be hiding a window if this wasn't anomalous? The hunt continues...

Messing around some more with PowerShell and the JSON file, we can get additional WMI classes that were called in relation to the malware being run.

Figure 9

While we clearly have enough information to elevate these events to an incident, this post was supposed to be about ETW, so I should probably cover what was found in Splunk.

Figure 10

Above figure depicts domain module loads of .NET assemblies with the process name of PowerShell.

Figure 11

While the output isn't the best (I will change that for the next go round), we can see a number of .NET DLL's loaded by PowerShell. This may not be overtly malicious, but is worth looking into when you start to filter on ProcessID:5000.

Figure 12
Utilizing the PowerShell provider, we can again view the malicious obfuscated code that was run on the system.

Looking at the logs can definitely lead down a rabbit hole. Other interesting events that can be identified are Interop Method calls, as well as DomainModule events with PDB information.

This was just a short introduction into ETW and it's capabilities. This would be a great detection method alongside Sysmon and other endpoint solutions.

Hopefully someone found the above useful. Playing around with additional detection methods for this malware sample, I came up with the below extremely beginner Snort rule. Please hate on it all you want, just let me know how to better it.

alert tcp $HOME_NET any -> $EXTERNAL_NET any (msg:" Possible Malicious Document - Retrieving Payload"; flow:established,to_server; content:"GET"; http_method; content:".exe"; http_uri; pcre:"/\/[0-9]{1,7}\.exe$/U"; content:!"User-Agent"; content:!"Referer|3A|"; http_header; sid:2; rev:1;)

Happy Hunting!

Wednesday, September 18, 2019

Analyzing an RTF document from Cyber Comm Drop

18 Sep 2019

About a week ago, U.S. Cyber Command made public a number of malware samples purported to be from North Korea via Twitter.  It's not often these samples are made public outside of VirusTotal (I am not cool enough for a full account). The folks at Hybrid-Analysis were kind enough to release them for us regular folk.

I have a particular liking for malicious Microsoft Office documents and how adversaries package them to bypass EDR solutions. While browsing the samples, a .doc file caught my eye.

Wednesday, August 28, 2019

Quick Network Analysis of Excel Document Utilizing WS-Discovery Protocol

 I thoroughly enjoy analyzing how malware slithers through endpoints using new/novel techniques to evade detection.  Searching through network traffic packets and putting together the "story" of the infection is just as if not more exciting.

I came across this sample some time ago, and did not immediately look at the network traffic in depth. Out of nowhere, I got the itch to analyze the traffic and found some techniques I was not familiar with.  The below will include a quick analysis of what I was able to pull from the network traffic captures.

Saturday, August 10, 2019

Malware Traffic Analysis Exercise (July 2019)

It had been a while since the last time I completed one of Brad's exercises. I felt I might be a little rusty with Wireshark and Scapy, so I decided to lookup the latest blog entry.

The exercise for this post can be found at:

Friday, July 5, 2019

PowerShell Reverse Meterpreter Script Analysis

While perusing Pastebin (& not researching in my lab like I had planned) for malicious PowerShell scripts, I came upon an interesting script.

Saturday, June 1, 2019

Japan Themed Emotet Utilizes WMI to Execute Obfuscated PowerShell

01 June 2019

 I recently came across an interesting sample of the Emotet trojan that departs from the tried and true tactics of Word doc > VBA code > PowerShell script.  Well, those elements are still there, but how the PowerShell script is executed is different from what I have seen other Emotet samples accomplish. 

Sunday, May 19, 2019

Defeating The Empire With The Basics: Detecting Powershell Empire

19 May 2019


 Powershell Empire is a household name for penetration testers, red team members, and even your favorite APT group. Combining the everyday use of Powershell for most admins and the C2 framework of Empire, makes for a deadly combination that may go unnoticed by defenders.

Sifting Through ETW for Persistence in C#

 Introduction Continuing my deep dive into how .NET can be used maliciously, this blog post will cover hunting for and detecting persist...