This is a function operators can manually invoke for a payload to ask the payload's C2 profiles to generate a set of redirection rules for that payload. Nothing in Mythic knows more about a specific C2 profile than the C2 profile itself, so it makes sense that a C2 profile should be able to generate its own redirection rules for a given payload.
These redirection rules are up to the C2 Profile creators, but can include things like Apache mod_rewrite rules, Nginx configurations, and more.
Operationally, users can invoke this function from the created payloads page with a dropdown menu for the payload they're interested in. Functionally, this code lives in the class definition of your C2 Profile.
This function gets passed the same sort of information that the opsec check and configuration check functions get; namely, information about all of the payload's supplied c2 profile parameter values. This function can also access the C2 Profile's current configuration.
The format of the function is as follows:
Check Agent's Configuration Before Generation
Configuration checks are optional checks implemented by a C2 profile to alert the operator if they're generating an agent with a C2 configuration that doesn't match the current C2 docker services.
This check occurs every time an agent is generated, and this output is added to the payload's build_message
. Thus, an operator sees it when generating a payload, but it's always viewable again from the created payloads page.
The function is part of your C2 Profile's class definition, so it has access to your local config.json
file as well as the instance configuration from the agent.
This section talks about the different components for creating the server side docker container for a new C2 profile. This piece accepts messages from the agent, decodes them, forwards them off to the Mythic server, and replies back with the response. Specifically, this goes into the following components:
Docker containers
Configuration Files
Server
When creating payloads, Mythic will send a C2 Profile's parameters to the associated C2 Profile container for an "opsec check". This is a function that you can choose to write (or not) to look over the C2-specific parameter values that an operator selected to see if they pass your risk tolerance. This function is part of your C2 Profile's class definition:
In the end, the function is returning success or error for if the OPSEC check passed or not.
OPSEC checks for C2 profiles are executed every time a Payload is created. This means when an operator does it through the UI, when somebody scripts it out, and when a payload is automatically generated as part of tasking (such as for lateral movement or spawning new callbacks).
All C2 profiles are backed by a Docker container or intermediary layer of some sort.
What do the C2 docker containers do? Why are things broken out this way? In order to make things more modular within Mythic, most services are broken out into their own containers. When it comes to C2 profiles, they simply serve as an intermediary layer that translates between your special sauce C2 mechanism and the normal RESTful interface that Mythic uses. This allows you to create any number of completely disjoint C2 types without having to modify anything in the main Mythic codebase.
C2 Profile Contianers, like Payload Type and Translation Containers, all use the same mythic_base_container
Docker image. From there you can leverage the github.com/MythicMeta/MythicContainer
GoLang package or the mythic_container
PyPi package depending on if you want to write the meta information about your C2 profile in GoLang or Python. The actual code that binds to ports and accepts messages can be written in any language.
There are a few things needed to make a C2 container. For reference on general code structure options, check out Payload Type Development. The general structure is the same for Payload Types, C2 Profiles, and Translation containers.
Instead of declaring a new class of Payload Type though, you declare a new class of type C2Profile. For example, in Python you can do:
The key here for a C2 Profile though is the server_binary_path
- this indicates what actually gets executed to start listening for agent messages. This can be whatever you want, in any language you want, but you just need to make sure it's executable and identified here. If you want this to pick up something from the environment (and it's a script), be sure to put it as a #!
at the top. For example, the default containers leverage python3, so they have #! /usr/bin/env python3
at the top. This file is always executed via bash, so as a sub-process like ./server
Your server
code *MUST* send an HTTP header of Mythic: ProfileNameHere
when connecting to Mythic. This allows Mythic to know which profile is connecting
Within the server_folder_path
should be a file called config.json
, this is what the operator is able to edit through the UI and should contain all of the configuration components. The one piece that doesn't need to be here are if the operator needs to add additional files (like SSL certs).
This is a small class that just defines the metadata aspects of the C2 profile. A big piece here is the definition of the parameters
array. Each element here is a C2ProfileParameter
class instance with a few possible arguments:
There are a few main values you can supply for parameter_type
when defining the parameters of your c2 profile:
String
- This is simply a text box where you can input a string value
ChooseOne
- this is a dropdown choice where the operator makes a choice from a pre-defined list of options
Array
- This allows an operator to input an array of values rather than a single string value. When this is processed on the back-end, it becomes a proper array value like ["val1", "val2"]
.
Date
- This is a date in the YYYY-MM-DD format. However, when specifying a default value for this, you simply supply an offset of the number of days from the current day. For example, to have a default value for the user be one year from the current date, the default_value would be 365
. Similarly, you can supply negative values and it'll be days in the past. This manifests as a date-picker option for the user when generating a payload.
Dictionary
- This one is a bit more complicated, but allows you to specify an arbitrary dictionary for the user to generate and allows you to set some restrictions on the data. Let's take a look at this one more closely:
This is saying that we have a Dictionary called "headers" with a few pre-set options.
Every C2 Profile should have a config.json
file located in their defined server_folder_path
which contains all the fields an operator would need to configure.
This is the main way for an operator to do configurations of the C2 profile without having to connect to the server where Mythic is running. This can be any format in reality, the name just has to stay the same.