However, as the new set of utilities and supporting infrastructure increased in size and variety, so did the complexities around their formal integration and orchestration. For example, take the overabundance of penetration testing distributions like Jok3r, or reconnaissance tools like Recon-ng currently available; now think of the amount of effort that it will take just to provide a coherent backend on which to run these, or the disparate takedown steps that are almost inevitable. What if you could rely on a single scaffold on which to base your next team engagement, without additional concerns as to the type of Virtual Private Server (VPS), automation strategies, or even the addition of your favorite scripts, all under one roof?
Meet Axiom—a single, dynamic cloud infrastructure framework designed for red teamers and bug hunters alike, with the purpose of providing a repeatable approach to the challenge of creating distributed pentesting instances.
Sponsored by none other than SecurityTrails, and with a growing set of fantastic additions by its many skilled contributors, Axiom will certainly expand to become the go-to implementation for parallelizing pentesting workloads in a predictable, affordable, and intuitive manner. Let’s dive in and take a closer look at this unique application.
What is the Axiom framework?
Orchestrating with Axiom begins with understanding the role of droplets. These are DigitalOcean’s compute services in the form of Linux-based virtual machines popular with developers and hobbyists due to their relative low-cost, reliability, and scalability features. Extant references to multiparty computation abound in the literature; to this effect, Axiom’s toolkit makes use of distributed computing to tacitly achieve its performance objectives.
In a nutshell, Axiom relies on a combination of three core principles or components—instances, images, and boxes. In Axiom’s terms, an image is a snapshot of a DigitalOcean droplet (or instance) that has been pre-configured by running a set of scripts to arrive at a packaged configuration that is easily consumed and restored on demand. Boxes are the equivalent of backup files, expressed in text format, which contain a list of common configuration files (e.g., .zsh_history) that are to be included, or excluded, when restoring a particular image from backup.
Axiom’s capability to generate multiple instances of this base image allows the framework to spread a large number of targeted scans interspersed with a handful of additional tools such as nuclei or subfinder. Not surprisingly, the benefits are akin to those heralded by multi-threaded applications: once a set amount of instances, collectively known as a “fleet”, have been spun up, Axiom can perform substantial scan-like operations in a matter of minutes. Last but not least, Axiom provides a list of helper utilities that make moving files between instances a seamless task.
Anyone who’s ever attempted to put together such a dissimilar array of infrastructure and applications, for whatever the purpose, can easily attest to the time-saving benefits provided by a platform such as Axiom. Fans of this sort of turnkey scenario, like ourselves at SecurityTrails, will not only avoid the inevitable configuration and automation woes so prevalent in the setup stages, but will gain the distinct advantage of not “burning” source IPs if one happens to engage in frequent scanning.
Installation and configuration
Axiom provides two distinct modes of installation: the manual mode and the automated “easy” install mode. The manual mode relies on a pre-existing set of dependencies and requirements that include:
- A DigitalOcean API key
- An SSH private/public key pair
- jq - 1.6
- packer (tested with v.1.5.6)
- lsb_release (tested with v.1.4)
As per the documentation, “the key dependencies are jq, fzf, doctl and packer. The exact versions are on the GitHub, and they are important. If you use an old version of jq, packer or doctl, it could break the entire setup.” fzf is not strictly needed, but it is required to display menus.
Using your Linux distribution of choice, and using an account having sudo privileges, ensure that a previous installation does not conflict with the new one by issuing the following command:
rm -rf ~/.axiom/
Ever want to delete Axiom? Just remove this directory and it’ll be gone!
Once all dependencies are met, installation can proceed by cloning the Axiom repository from Github like so:
git clone https://github.com/pry0cc/axiom ~/.axiom/
Finally, run the configuration script as follows:
If you are running Ubuntu 20.04, Kali 2020.4, or relying on the Windows Subsystem, however, the automated installation mode can make your life a whole lot easier by running a one-liner like so:
bash <(curl -s https://raw.githubusercontent.com/pry0cc/axiom/master/interact/axiom-configure)
As part of the setup process, Axiom will install the Go programming language and ask you to select a cloud provider as well—the original and best-supported provider for Axiom is DigitalOcean.
Sit back and relax… it will take the script quite some time to select provider regions, spin instances and containers, collect suggested packages, create SSH keys, and download all the necessary tools. If you run into trouble while pursuing either installation mode, try the following quick tips and recommendations:
- Does ~/.axiom/axiom.json exist? Is it empty?—this is the config file and it is auto-generated by the axiom-configure script above.
- Is doctl configured? Test by running doctl compute instances list, you may also need to run doctl auth.
- Is Axiom in your path? Run echo $PATH, your $PATH should contain ~/.axiom/interact/—this is the directory that contains all the toolkit scripts.
- Is git complaining about non-mergeable files on update? Delete the conflicting ones, then run the update again.
- Do you get an error about functions.sh? Run axiom-account-setup
And don’t forget to check the installation guide to learn about other potential fixes and to find answers to some frequently asked questions!
Finally, a successful installation will look something like this:
Testing and results
Now that we’ve covered the basics and gone through the installation steps, let’s take Axiom for a spin. Start a new instance by typing:
Launching a new instance entails generating a random hostname from a predefined pool of known scientists and infosec professionals, and a number. Once started, the instance name will be written to a selection profile under ~/.axiom/profile.json—finally, we can ssh to it like so:
Additionally, you are presented with your instance’s public IP if you ever need to link to it.
Fleets and modules
As previously mentioned, spinning up a fleet is Axiom’s most powerful mechanized feature—remember, a fleet is a set number of instances or hosts, usually greater than 3, that can be used for various purposes including distributed scanning, parallel file transfers, and command execution.
For example, the below command will start up a fleet of 5 instances (droplets) called “sectrails”. These will be named sectrails01, 02… and so on.
axiom-fleet sectrails -i=5
axiom-fleet can also leverage features such as DigitalOcean’s regional compatibility matrix to allow you to deploy droplet-specific resources across a multitude of geographic locations.
For instance, the command:
axiom-fleet -i=15 --regions=NYC3,AMS3,SGP1,AMS3,TOR1
will deploy a total of 15 droplets in a round-robin fashion throughout data centers in New York, Amsterdam, Singapore, London, and Toronto, achieving optimal levels of resiliency and scalability in the process.
Now, to use instances in parallel fashion, they need to be selected by appending the wildcard character (∗) to the base image name. Let’s start building our proof of concept (PoC) by testing Axiom via axiom-scan on a handful of Netflix US-based endpoints using the masscan module on the top 2,000 ports, adding the filename netflixips.txt as our input and saving the results to a file called outputnetflix.txt for further manipulation. Let’s select our fleet…
…and spin Masscan; the job will be split across all droplets and the results concatenated into a single file.
In all, the process took two and half minutes to analyze 2,000 ports on all 29 targets. As seen below, the Masscan results were readily presented:
Axiom’s default interact modules are plain json files or templates that dictate how to execute your favorite commands—these can be expanded upon or customized depending on use case. As of the date of this blog post, the following modules are available:
amass.json dnsgen.json ffuf.json gau.json gowitness.json masscan.json meg.json nmapx.json shuffledns.json subfinder.json dalfox.json dnsx.json gospider.json httpx.json massdns.json nmap.json nuclei.json soxy.json
Let’s take Axiom for another spin by using the nmapx module this time—by running one process per target, the nmapx module takes advantage of nmap’s superior handle of both host and network resources to create a more efficient scanning routine. When supplied with “-oX’’ flag, this will also distribute nmapx across your fleet and send the results to a bootstrap-themed HTML file, which is a very intuitive way to read your output.
axiom-scan netflixips.txt -m nmapx -T5 -sV -p443 -oX scan.xml
The distributed operation took less than a minute to Nmap all 29 targets and resulted in the following output (rendered via a separate XML viewer):
Overall, Axiom’s performance was nothing short of impressive, but we’ve barely scratched the surface. With only a few cents in running-time expenses ($0.007 per hour per instance), the time-saving benefits and team-wide acquisition opportunities become obvious as well, especially if more complex and lengthy engagements are to be considered.
For example, Axiom does an excellent job at quantifying costs when you provide the time-to-expire parameter (e.g., t=2) in hours as part of the axiom-fleet droplets creation routine—although axiom is retiring the time-to-expire flag to prevent users from killing their instances by mistake, it will be replaced with “–remove-after-complete”, which will automatically delete your instance(s) once the scan has completed, if you choose this route. Be sure to use this option as frequently as possible if you’re tasked with providing expense reports and that sort of thing. Also, don’t forget to spin down and remove your instances when everything’s said and done; there is still a quick and intuitive way of doing so:
axiom-rm "sectrails*" -f
Finally, Axiom’s own wiki and cheatsheet are excellent resources to learn about all of the above commands and many more. Now, go and have some fun!
With the arrival of dynamic cloud services, conducting red team activities and similar efforts at high concurrency rates has become easier than ever. Moreover, it is important to emphasize that this fine-grained approach doesn’t necessarily translate into excessive costs—in fact, computation at scale has seen a steady reduction in operating expenses over the past few years; a trend that is likely to persist given the economic and technological improvements constantly underway.
In working with the Axiom framework, we were able to build a small yet powerful assortment of cloud computing instances to perform distributed activities that would have normally taken a lot longer to put together, not to mention at a fraction of the cost. With a single command to set things in motion, seemingly disparate utilities comprising some of the best well-known penetration testing, red-teaming, and bug bounty toolkits were easily configured and deployed using a handful of well-written scripts. Overall, kudos to the Axiom team!
As always, the open-source nature of tools like Axiom can never be a carte blanche for illegitimate purposes—as with any other security tool at our disposal, please understand the regulatory and legal considerations surrounding our profession before you consider any unlawful practices.