migrated away from free rdp lots of improvements there and created native libs feel free to use native libs but contribute if you improve please add more wider api support and cli and shell payload mutator for api endpoint going to do that for payloads gens and other stuff later and im also planning some more bug changes and improvement check the api template
5.5 KiB
Module Development
Reference for maintainers and contributors writing new Rustsploit modules.
How Modules Are Discovered
Rustsploit uses a build-time code-generation approach — no manual registry:
-
build.rsscan — Before compilation,build.rsrecursively walkssrc/modules/looking for.rsfiles that are notmod.rs. -
Signature detection — A file that exposes
pub async fn run(is treated as a callable module. -
Name generation — Both a short name (
ssh_bruteforce) and a qualified path (creds/generic/ssh_bruteforce) are registered. -
Dispatcher emission — Three files are generated:
src/commands/exploit_gen.rssrc/commands/scanner_gen.rssrc/commands/creds_gen.rs
Each contains an exhaustive
matchmapping names →use crate::modules::...::run. -
Shell + CLI resolution —
use exploits/fooor--module fooboth resolve through the dispatcher.
Because it's generated at build time, there is no manual registry drift as long as modules live in the correct folder and export run.
Project Code Layout
rustsploit/
├── Cargo.toml
├── build.rs # Generates dispatcher by scanning src/modules
├── src/
│ ├── main.rs # Entry point — CLI or shell mode, input validation
│ ├── cli.rs # Clap-based CLI parser and dispatcher
│ ├── shell.rs # Interactive shell loop + UX helpers
│ ├── api.rs # REST API server — auth, rate limiting, hardening
│ ├── config.rs # Global config and target validation
│ ├── commands/
│ │ ├── mod.rs
│ │ ├── exploit.rs
│ │ ├── exploit_gen.rs # build.rs output
│ │ ├── scanner.rs
│ │ ├── scanner_gen.rs # build.rs output
│ │ ├── creds.rs
│ │ └── creds_gen.rs # build.rs output
│ ├── modules/
│ │ ├── exploits/ # Exploit modules
│ │ ├── scanners/ # Scanner modules
│ │ └── creds/ # Credential modules
│ └── utils.rs # Shared helpers — normalization, prompts, validation
├── docs/ # This wiki
├── lists/ # Wordlists and data files
└── README.md # Product overview
Required Module Signature
Every module must export:
use anyhow::Result;
pub async fn run(target: &str) -> Result<()> {
// ...
Ok(())
}
Optional: also expose pub async fn run_interactive(target: &str) -> Result<()> for modules with multiple code paths.
Adding a New Module — Checklist
- Choose a location under
src/modules/{exploits,scanners,creds}.
Use subfolders for vendor families (e.g.,exploits/cisco/). - Create the
.rsfile with the requiredpub async fn runsignature. - Register in
mod.rs— addpub mod your_module;to the siblingmod.rs.
Without this,build.rsignores the file. - Run
cargo check— the dispatcher is regenerated automatically.
Module Skeleton
use anyhow::{Context, Result};
use colored::Colorize;
use crate::utils::normalize_target;
pub async fn run(target: &str) -> Result<()> {
let target = normalize_target(target)?;
println!("{} Checking {}", "[*]".cyan(), target);
let url = format!("http://{}/status", target);
let body = reqwest::get(&url)
.await
.with_context(|| format!("Failed to reach {}", url))?
.text()
.await
.context("Failed to read response body")?;
if body.contains("vulnerable") {
println!("{} {} appears vulnerable", "[+]".green(), target);
} else {
println!("{} {} not vulnerable", "[-]".red(), target);
}
Ok(())
}
Output Conventions
| Prefix | Color | Meaning |
|---|---|---|
[+] |
Green | Success / found |
[-] |
Red | Not found / not vulnerable |
[!] |
Yellow | Warning |
[*] |
Cyan | Info / progress |
Use .green(), .red(), .yellow(), .cyan() from the colored crate. Keep messages short and actionable.
Async I/O Guidelines
- Prefer
reqwest,tokio::net,tokio::processfor async work. - Wrap synchronous blocking calls with
tokio::task::spawn_blocking(see the SSH module for reference). - For concurrency:
tokio::sync::Semaphore(wrapped inArc) for async modules.threadpool+crossbeam-channelfor synchronous protocols (Telnet, POP3).
Error Handling
Bubble up errors using anyhow::Context so the shell/CLI surface meaningful messages:
.with_context(|| format!("Failed to connect to {}", target))?
Avoid unwrap() and unwrap_or_default() in critical paths.
Wordlists & Resources
Store under lists/ and document them in lists/readme.md. Reference paths relative to the working directory.
0.0.0.0/0 Internet-Wide Scanning
Modules supporting mass-scan accept 0.0.0.0, 0.0.0.0/0, or random as targets. When detected, the module enters an infinite loop generating random public IPs using:
fn generate_random_public_ip() -> Ipv4Addr { ... }
fn is_excluded_ip(ip: Ipv4Addr) -> bool { ... }
The EXCLUDED_RANGES constant covers bogons, private, reserved, documentation CIDRs, and public DNS servers. Copy this pattern from an existing mass-scan module (e.g., telnet_hose or hikvision_rce).
Honeypot detection is disabled in mass-scan mode to avoid interactive prompts.