Skip to main content
  1. Documentation/
  2. Developer Guide/

Extension Points

Table of Contents
TantoC2 is designed to be extended. Every major subsystem is pluggable — from agents to modules to listeners.

What Can You Build?
#

Extension PointWhat It IsEffortStart Here
Agent PackageA complete deployable agent with its own crypto, wire protocol, build pipeline, and capabilitiesLargeYou want to create a new agent in Go, Rust, C, etc.
Agent ModuleA compiled payload (BOF, shellcode, DLL, etc.) loaded into agents at runtimeMediumYou have compiled tradecraft to deploy through agents
Tools ModuleA Python plugin for direct network interaction (SSH, SMB, LDAP, etc.)SmallYou want to interact with a new protocol without an agent
Transport PluginA listener implementation (HTTP, DNS, named pipes, etc.)MediumYou need a new C2 channel

How Plugins Work
#

All plugin types share the same underlying mechanism:

  1. Every plugin extends PluginBase with a unique plugin_name() and a plugin_type()
  2. Discovery is automatic — drop a .py file in the right directory, or install a wheel with entry points
  3. Hot-reload without restart — the plugin watcher detects changes and reloads
  4. No core changes needed — the framework discovers and wires everything at runtime
 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
from tantoc2.server.plugins import PluginBase

class PluginBase(ABC):
    @classmethod
    @abstractmethod
    def plugin_name(cls) -> str:
        """Unique name for this plugin."""

    @classmethod
    @abstractmethod
    def plugin_type(cls) -> str:
        """Type: 'transport', 'module', 'agentless_module', 'agent_package', 'crypto_provider', 'protocol_codec'."""

Plugin Discovery
#

Plugins are discovered through three mechanisms:

1. Directory Scanning
#

Drop a .py file in the appropriate directory. The framework scans for PluginBase subclasses:

1
2
3
4
5
modules/my_module.py                    → Server module
plugins/transports/my_transport.py      → Transport
plugins/agentless/my_tool.py            → Tools module
plugins/agent_packages/my_agent.py      → Agent package
agent_modules/my_module/manifest.yaml   → Agent module (YAML + payload)

2. Python Entry Points
#

Package your plugin as a wheel and declare entry points in pyproject.toml:

1
2
3
4
5
6
7
8
[project.entry-points."tantoc2.agent_packages"]
my_agent = "my_package.agent:MyAgentPackage"

[project.entry-points."tantoc2.crypto_providers"]
my_crypto = "my_package.crypto:MyCryptoProvider"

[project.entry-points."tantoc2.protocol_codecs"]
my_codec = "my_package.codec:MyProtocolCodec"

Entry point names must match plugin_name() return values.

3. Plugin Inbox
#

Drop .py or .whl files into the inbox directory (plugin_inbox_dir config). The watcher auto-detects the plugin type, moves .py files to the correct directory, and pip-installs .whl files.

Dependencies
#

Modules can declare pip dependencies in their metadata:

1
2
3
4
5
ModuleMetadata(
    name="my_module",
    ...,
    dependencies=["paramiko", "impacket"],
)

Missing packages are auto-installed at discovery time. If installation fails, the module is tracked as unavailable (queryable via unavailable_modules).

Development Setup
#

1
2
3
4
5
6
7
# Clone and install in dev mode
git clone <repo-url> tantoc2
cd tantoc2
make dev

# Your plugin file goes in the appropriate directory
# The framework auto-discovers it on next refresh

Next Steps
#

Pick the extension point that matches your goal and follow the dedicated guide.