Announcing YetiHunter: An open-source tool to detect and hunt for suspicious activity in Snowflake

Illustration Cloud

Extending Cloud Console Cartographer With New Mappings

Last month Permiso’s P0 Labs released the Cloud Console Cartographer open-source framework and corresponding research presentation at Black Hat Asia in Singapore. Recently we released our full suite of unit tests. Now let’s talk about how to extend the framework by adding new mapping definitions.

By way of background, Cloud Console Cartographer is a framework for condensing groupings of cloud events (e.g. CloudTrail logs) and mapping them to the original user input actions in the management console UI for simplified analysis and explainability. This is extremely beneficial for defenders since numerous input actions in management console sessions can generate 10's and even many 100's of events originating from a single interactive click by the end user.


Source Code:

We recently added our full unit tests to the project to make it easier for the community to contribute new mappings while quickly ensuring any updates do not break existing mappings. There are many complex scenarios to account for since mappings are based on event combinations that can often be overlapping from a timeline perspective. Therefore, unit tests calculated for entire sessions of events is the most effective format that we use for all internal and external unit tests for this framework.

In this blog post we will outline the steps required to create a new mapping in Cloud Console Cartographer. We will focus on the components required for an existing mapping to highlight the order and interworking between Signal definitions, Label applications and then the remaining Signal generation and optional Signal modifications.

Generation of CloudTrail Events for Mapping

First we will create an AWS Management Console session and perform the manual click-mapping of the service, in this case the CloudTrail service. After clicking on CloudTrail→Insights we will record the exact time of the click so we can retrieve the CloudTrail events corresponding to the activity.

CouldTrail Events Mapping

Screenshot of AWS Management Console: CloudTrail->Insights


Focusing on the first click, CloudTrail->Insights, we can see the following events and corresponding requestParameters and userAgent values were generated:

ClouldTrail Events Generated

CloudTrail events generated when clicking CloudTrail->Insights

Creating New Mapping (via Signal and Label Definitions)

Translating a simple mapping like this in Cloud Console Cartographer is as simple as 1-2-3 in the following files in the Code directory of the project:

                  1. In the SignalDefinitions.ps1 file add a new Signal enum corresponding to the breadcrumb of where the click can be found in the AWS Managment Console: CloudTrail_Insights. This enum will be used throughout the rest of the code as both Label and Signal references.



                    Signal Enumeration in SignalDefinitions


                    Example Signal enum in SignalDefinitions.ps1 file


                1. In the SignalDefinitions.ps1 file add a new Signal class constructor definition for the events and metadata associated with the CloudTrail_Insights enum created in Step #1. At a minimum this involves the event listings (AnchorEvents, RequiredEvents and OptionalEvents) along with the base metadata to be included in the generated Signal objects (including placeholder values like in the Url and Summary properties that can be substituted at the time of the Signal generation).


                  Signal Class Structure in SignalDefinitions


                  Example Signal class constructor in SignalDefinitions.ps1 file




      1. In the AddLabels.ps1 file’s Add-Label function add the CloudTrail_Insights enum created in Step #1 to all events defined in the Signal definition in Step #2. If the eventSource + eventName pairing is not yet listed in this file’s switch statement then add the appropriate switch statement structure to successfully match the event. This is where particular focus should be directed to the event’s requestParameters and userAgent properties. Whichever switch statement block is matched (if any) then all the listed Labels will be returned in the order they are listed. This ordering is extremely important in the Signal generation process as it (paired with strategic specification in each Signal definition’s AnchorEvents property) determine the order of priority of potentially competing and overlapping Signals during the generation process.
        GetTrailStatus Example Label



        Example Label application for specific eventSource + eventName pairing in AddLabels.ps1 file’s Add-Label function


That’s it! Nothing else is required to add a new mapping for this simple scenario. Re-running the framework will now group these labeled events and cause the corresponding Signal to be generated.

Simple substitutions like placeholder value in each Signal definition’s Url and Summary properties are automatically performed for all generated Signals. Any additional optional substitutions and multi-event information extraction steps occur in NewSignal.ps1 file’s New-Signal function (shown below). More nuanced Signal overrides, merges and look-ahead/look-behind Signal-borrowing scenarios are defined in AddSignal.ps1 file’s Add-Signal function (not shown).

Example Signal Summary and URL Mods

Example Signal Summary and Url modifications in NewSignal.ps1 file’s New-Signal function.

Debugging Mappings

A helpful function for debugging at the event level is Show-EventSummary -Detail signal,event_mapped,event_unmapped which displays every event (green if mapped to a Signal, yellow if not) with additional Signal details above and event metadata below that is useful for updating Label assignment logic in AddLabels.ps1 file’s Add-Label function. Of note is the list of Labels evaluated for each event (same list of Labels added in Add-Label function for each event in specific matching switch statement) with color-coding to show which Labels did not contribute to a Signal (red), did contribute to a Signal (green) or were skipped due to previous successful Signal contribution (grey).

Debugging Command

Debugging command: dir ./demoEvents.json | Add-Signal | Show-EventSummary -Detail signal,event_mapped,event_unmapped


Unit Tests

The last step after confirming the new Signal is working as expected on our generated session data is to ensure we did not break or clobber any other Signal logic. This is where the latest update of the unit tests tooling in the Tests folder comes into play.

We tried to make unit testing as simple as 1-2:

      1. Input current events into the New-UnitTest function to automatically create minimized input event file and expected output result file in Tests/Sessions folder: dir ./demoEvents.json | New-UnitTest -Verbose
        Creation of unit test files

        Creation of unit test files for current events and Signals: dir ./demoEvents.json | New-UnitTest -Verbose

        1. Run unit tests for specific test sessions (organized by dynamically generated session ID) or all sessions in Tests/Sessions folder using the Pester unit testing framework: Invoke-Pester -TagFilter FullEvent

          Execution of all unit tests


          xecution of all unit tests: Invoke-Pester -TagFilter FullEvent



While this blog post does not seek to exposit all the intricate capabilities of the Cloud Console Cartographer framework meant to handle numerous complicated clobbering scenarios, Signal merge scenarios or look-ahead/look-behind Signal-borrowing scenarios, we hope it is enough to get interested community members started in codifying their own knowledge of AWS Management Console click-mappings into a repeatable and shareable framework.

Stay tuned for more project updates plus new research and open-source tools from the Permiso P0 Labs team!

Illustration Cloud

Related Articles

Introducing YetiHunter: An open-source tool to detect and hunt for suspicious activity in Snowflake

Summary On May 30, 2024 Snowflake confirmed many clients were affected by an attacker leveraging compromised NHI credentials to perform data theft. In their notice, Snowflake included some indicators and suggested hunts. Our good friends at Mandiant

Unmasking Adversary Cloud Defense Evasion Strategies: Modify Cloud Compute Infrastructure Part 2

Detection and Mitigation The 'Create Snapshot', ‘Create Cloud Instance’, ‘Delete Cloud Instance’, ‘Revert Cloud Instance’ and ‘Modify Cloud Compute Configurations’ features are widely available across major cloud platforms such as AWS, Azure, and

Unmasking Adversary Cloud Defense Evasion Strategies: Modify Cloud Compute Infrastructure Part 1

The MITRE ATT&CK (Adversarial Tactics, Techniques and Common Knowledge) Framework is a globally-accessible knowledge base of adversary tactics and techniques and procedures (TTPs) which are constantly updated to reflect real-world observations of

View more posts