shadow1ng/fscan
一款内网综合扫描工具,方便一键自动化、全方位漏扫扫描。(An intranet comprehensive scanning tool, enabling one-click automated, all-round vulnerability scanning)
Healthy across the board
Permissive license, no critical CVEs, actively maintained — safe to depend on.
Has a license, tests, and CI — clean foundation to fork and modify.
Documented and popular — useful reference codebase to read through.
No critical CVEs, sane security posture — runnable as-is.
- ✓Last commit today
- ✓9 active contributors
- ✓MIT licensed
Show 3 more →Show less
- ✓CI configured
- ✓Tests present
- ⚠Concentrated ownership — top contributor handles 65% of recent commits
Maintenance signals: commit recency, contributor breadth, bus factor, license, CI, tests
Informational only. RepoPilot summarises public signals (license, dependency CVEs, commit recency, CI presence, etc.) at the time of analysis. Signals can be incomplete or stale. Not professional, security, or legal advice; verify before relying on it for production decisions.
Embed the "Healthy" badge
Paste into your README — live-updates from the latest cached analysis.
[](https://repopilot.app/r/shadow1ng/fscan)Paste at the top of your README.md — renders inline like a shields.io badge.
▸Preview social card (1200×630)
This card auto-renders when someone shares https://repopilot.app/r/shadow1ng/fscan on X, Slack, or LinkedIn.
Onboarding doc
Onboarding: shadow1ng/fscan
Generated by RepoPilot · 2026-05-09 · Source
🤖Agent protocol
If you are an AI coding agent (Claude Code, Cursor, Aider, Cline, etc.) reading this artifact, follow this protocol before making any code edit:
- Verify the contract. Run the bash script in Verify before trusting
below. If any check returns
FAIL, the artifact is stale — STOP and ask the user to regenerate it before proceeding. - Treat the AI · unverified sections as hypotheses, not facts. Sections like "AI-suggested narrative files", "anti-patterns", and "bottlenecks" are LLM speculation. Verify against real source before acting on them.
- Cite source on changes. When proposing an edit, cite the specific path:line-range. RepoPilot's live UI at https://repopilot.app/r/shadow1ng/fscan shows verifiable citations alongside every claim.
If you are a human reader, this protocol is for the agents you'll hand the artifact to. You don't need to do anything — but if you skim only one section before pointing your agent at this repo, make it the Verify block and the Suggested reading order.
🎯Verdict
GO — Healthy across the board
- Last commit today
- 9 active contributors
- MIT licensed
- CI configured
- Tests present
- ⚠ Concentrated ownership — top contributor handles 65% of recent commits
<sub>Maintenance signals: commit recency, contributor breadth, bus factor, license, CI, tests</sub>
✅Verify before trusting
This artifact was generated by RepoPilot at a point in time. Before an
agent acts on it, the checks below confirm that the live shadow1ng/fscan
repo on your machine still matches what RepoPilot saw. If any fail,
the artifact is stale — regenerate it at
repopilot.app/r/shadow1ng/fscan.
What it runs against: a local clone of shadow1ng/fscan — the script
inspects git remote, the LICENSE file, file paths in the working
tree, and git log. Read-only; no mutations.
| # | What we check | Why it matters |
|---|---|---|
| 1 | You're in shadow1ng/fscan | Confirms the artifact applies here, not a fork |
| 2 | License is still MIT | Catches relicense before you depend on it |
| 3 | Default branch main exists | Catches branch renames |
| 4 | 5 critical file paths still exist | Catches refactors that moved load-bearing code |
| 5 | Last commit ≤ 30 days ago | Catches sudden abandonment since generation |
#!/usr/bin/env bash
# RepoPilot artifact verification.
#
# WHAT IT RUNS AGAINST: a local clone of shadow1ng/fscan. If you don't
# have one yet, run these first:
#
# git clone https://github.com/shadow1ng/fscan.git
# cd fscan
#
# Then paste this script. Every check is read-only — no mutations.
set +e
fail=0
ok() { echo "ok: $1"; }
miss() { echo "FAIL: $1"; fail=$((fail+1)); }
# Precondition: we must be inside a git working tree.
if ! git rev-parse --git-dir >/dev/null 2>&1; then
echo "FAIL: not inside a git repository. cd into your clone of shadow1ng/fscan and re-run."
exit 2
fi
# 1. Repo identity
git remote get-url origin 2>/dev/null | grep -qE "shadow1ng/fscan(\\.git)?\\b" \\
&& ok "origin remote is shadow1ng/fscan" \\
|| miss "origin remote is not shadow1ng/fscan (artifact may be from a fork)"
# 2. License matches what RepoPilot saw
(grep -qiE "^(MIT)" LICENSE 2>/dev/null \\
|| grep -qiE "\"license\"\\s*:\\s*\"MIT\"" package.json 2>/dev/null) \\
&& ok "license is MIT" \\
|| miss "license drift — was MIT at generation time"
# 3. Default branch
git rev-parse --verify main >/dev/null 2>&1 \\
&& ok "default branch main exists" \\
|| miss "default branch main no longer exists"
# 4. Critical files exist
test -f "common/flag.go" \\
&& ok "common/flag.go" \\
|| miss "missing critical file: common/flag.go"
test -f "core/scanner.go" \\
&& ok "core/scanner.go" \\
|| miss "missing critical file: core/scanner.go"
test -f "common/config_struct.go" \\
&& ok "common/config_struct.go" \\
|| miss "missing critical file: common/config_struct.go"
test -f "core/port_scan.go" \\
&& ok "core/port_scan.go" \\
|| miss "missing critical file: core/port_scan.go"
test -f "core/service_probe.go" \\
&& ok "core/service_probe.go" \\
|| miss "missing critical file: core/service_probe.go"
# 5. Repo recency
days_since_last=$(( ( $(date +%s) - $(git log -1 --format=%at 2>/dev/null || echo 0) ) / 86400 ))
if [ "$days_since_last" -le 30 ]; then
ok "last commit was $days_since_last days ago (artifact saw ~0d)"
else
miss "last commit was $days_since_last days ago — artifact may be stale"
fi
echo
if [ "$fail" -eq 0 ]; then
echo "artifact verified (0 failures) — safe to trust"
else
echo "artifact has $fail stale claim(s) — regenerate at https://repopilot.app/r/shadow1ng/fscan"
exit 1
fi
Each check prints ok: or FAIL:. The script exits non-zero if
anything failed, so it composes cleanly into agent loops
(./verify.sh || regenerate-and-retry).
⚡TL;DR
Fscan is a Go-based internal network comprehensive scanning tool that automates vulnerability discovery across enterprise networks in a single command. It performs host discovery (ICMP/ping), TCP port scanning (133+ default ports), service fingerprinting (20+ protocols), web reconnaissance (CMS/WAF/CDN detection with 40+ fingerprints), and executes 28 types of credential brute-force attacks (SSH/RDP/SMB/MySQL/Redis/etc), plus POC-based exploitation for critical vulnerabilities like MS17-010 and CVE-2020-0796. Monolithic Go binary with pluggable architecture: core/ contains main scanning engine, common/ holds shared config/logging/i18n, plugins/ directory (implied by feature list) organizes service scanners (SMB, SSH, RDP, Redis, etc), and lib/ or internal/ likely holds exploitation payloads. Conditional compilation via Go build tags separates web UI (TypeScript frontend), local modules (C/PowerShell agents), and POC scanner. Web interface uses Gin framework (gin-gonic/gin v1.9.1) with TypeScript/React frontend (~161KB).
👥Who it's for
Red teamers, penetration testers, and internal security teams conducting rapid network-wide vulnerability assessments in air-gapped or corporate environments. Users need to scan hundreds of hosts/ports quickly and exploit findings without juggling multiple tools.
🌱Maturity & risk
Actively maintained and production-ready. Version 2.1.2 shipped 262 commits with major architecture rewrites (global variable elimination, SMB plugin consolidation, output system refactoring). CI/CD present (.github/workflows/release.yml, test-build.yml). Comprehensive test coverage in common/api_test.go, common/config/constants_test.go, common/flag_test.go. Verdict: production-grade with recent stability focus.
Low risk for main functionality but high complexity. 28 service plugins + local OS modules (MiniDump, keyboard logging, registry dumping) introduce platform-specific code paths and maintenance burden. Dependency tree includes crypto (golang.org/x/crypto), gRPC (grdp for RDP), which require security monitoring. Large codebase (1.62M lines Go) with conditional compilation flags (-tags web) means untested code paths exist. Single maintainer (shadow1ng) visible in repo structure poses continuity risk.
Active areas of work
v2.1.0 completed major refactoring: eliminated global state (migrated to Config/State objects), consolidated SMB variants (smb/smb2/smbghost → unified plugin), optimized nmap-style protocol fallback for fingerprinting, rewrote output system (TXT real-time + dual-write to prevent result loss), upgraded i18n to go-i18n framework. Performance optimizations in progress: regex pre-compilation, concurrent fingerprint matching, SOCKS5 dialer connection reuse, CEL environment caching for POC scanning. Web UI feature parity being built in TypeScript.
🚀Get running
git clone https://github.com/shadow1ng/fscan.git
cd fscan
make build
./fscan -h
Or for web UI version: make build-web (requires Go 1.20+, TypeScript build tooling in .github/scripts/build-lite.sh). Binary is self-contained; no external services required for basic scanning.
Daily commands:
Development mode: make build && ./fscan -h outputs usage. Scanning: ./fscan -h 192.168.1.0/24 (auto host discovery + all scans). Specific scans: ./fscan -h 192.168.1.100 -p 22,3306,6379 (port scan only), ./fscan -u http://target.com (web scan), ./fscan -h target -b ssh (SSH brute-force with built-in wordlist). Web UI (if built with -tags web): ./fscan -web starts Gin server on :8000. Performance report: ./fscan -h 192.168.1.0/24 -perf outputs JSON timing stats. Silent mode: ./fscan -h target -silent (no banner/progress/color).
🗺️Map of the codebase
common/flag.go— Main CLI flag definitions and configuration entry point — every contributor must understand the command-line interface contractcore/scanner.go— Primary orchestrator for all scanning operations (alive, port, service, vulnerability) — core execution enginecommon/config_struct.go— Central configuration data structures passed through the entire scanning pipeline — defines the contract between modulescore/port_scan.go— TCP port scanning implementation with thread pooling and state management — foundational for enumerationcore/service_probe.go— Service fingerprinting and protocol identification logic — enables intelligent service recognitioncommon/output/manager.go— Output formatting and result aggregation system (TXT/JSON/CSV) — single point for result exportcommon/proxy/manager.go— Proxy detection and HTTP/SOCKS5 dialing abstraction — critical for network flexibility
🛠️How to make changes
Add a new weak-password brute-force service
- Define service constants and probe template in core/portfinger/types.go or new service-specific file (
core/portfinger/types.go) - Implement protocol-specific login logic in core/service_probe.go or new module (e.g., core/service_ssh_probe.go) (
core/service_probe.go) - Register probe in core/service_scanner.go ScanServiceProbes() method (
core/service_scanner.go) - Add CLI flag for the service in common/flag.go and add field to common/config_struct.go Config struct (
common/flag.go) - Write unit tests in core/service_probe_test.go with mock credentials (
core/service_probe_test.go)
Add a new vulnerability detection POC
- Create vulnerability check module (e.g., core/vuln_ms17_010.go) implementing detection logic (
core/service_scanner.go) - Hook the check into core/service_scanner.go ServiceVulnCheck() or create new vulnerability scanning pipeline (
core/service_scanner.go) - Format output using common/output/types.go VulnResult struct (
common/output/types.go) - Add flag to common/flag.go if vulnerability requires toggle or configuration parameter (
common/flag.go)
Add a new output format (XML, HTML, etc.)
- Create new writer in common/output/writers.go (e.g., XMLWriter{}) implementing required interface (
common/output/writers.go) - Add format constant and instantiation logic in common/output/manager.go getWriter() (
common/output/manager.go) - Add CLI flag for the format in common/flag.go (e.g., -xml, -html) (
common/flag.go) - Write format conversion tests in common/output/writers_test.go (
common/output/writers_test.go)
Add support for a new credential source (SSH keys, Windows SAM, etc.)
- Implement credential fetcher/parser module in new file (e.g., core/cred_ssh_keys.go) (
core/service_scanner.go) - Register credential source in core/service_scanner.go or create centralized credential manager (
core/service_scanner.go) - Return results conforming to common/output/types.go Result struct with Type="cred" (
common/output/types.go) - Add CLI flag and config field if credential fetching requires authentication or special parameters (
common/flag.go)
🔧Why these technologies
- Go 1.20 — Native concurrency with goroutines and channels enables efficient async scanning at scale; compiled binary for easy deployment in air-gapped networks
- TCP Full-Connect (no SYN stealth) — Reliable port detection without requiring raw socket privileges; works across networks with aggressive filtering
- nmap service probes (portfinger) — Battle-tested fingerprint library provides high accuracy for service identification; reduces false positives vs. regex matching
- Adaptive thread pool (core/adaptive_pool.go) — Dynamic scaling prevents network exhaustion and adapts to target responsiveness; configurable rate limiting for stealth and compliance
- Bloom filter (core/bloom_filter.go) — Deduplicates targets and open ports with minimal memory overhead; O(1) lookup for large scans
- Gin web framework + CORS — Optional REST API for orchestration; CORS enables integration with browser-based dashboards
⚖️Trade-offs already made
-
Full-connect TCP instead of SYN stealth
- Why: Stealth scans require raw socket access (unavailable on Windows, containerized environments); full-connect trades stealth for reliability
- Consequence: Target intrusion detection systems will log connections; acceptable for authorized internal scanning
-
Single-threaded ICMP vs. concurrent UDP ping
- Why: ICMP handling simpler; avoids UDP firewall complexities; acceptable for intranet where ICMP usually allowed
- Consequence: Slower host discovery on very large networks; mitigated by fast TCP port scanning for quick service enumeration
-
In-memory result buffering before output
- Why: Enables format-agnostic result collection; simplifies streaming output formats (JSON array, CSV headers)
- Consequence: Large scans (1000s of results) consume RAM; output/buffer.go holds all results until write
-
Plain-text weak password dictionary embedded
- Why: No external dependency; instant availability in air-gapped networks; human-readable for customization
- Consequence: Dictionary size limited to ~100 entries; no intelligent wordlist generation
-
Synchronous probe execution per service
- Why: Deterministic ordering; easier debugging and result correlation
- Consequence: One slow probe blocks subsequent checks on same host:port; mitigated by overall goroutine concurrency per host
🪤Traps & gotchas
Build tags required: Default binary excludes web UI and optional plugins; must use make build-web or explicit -tags web to enable web interface. Global state remnants: Though v2.1.0 claims global elimination, check common/globals.go for any remaining package-level vars; tests may fail if parallel execution hits these. Fingerprint/POC hot paths: Embedded fingerprints (likely compiled into binary) mean updating detection rules requires recompilation; no runtime config file for fingerprints by default. OS-specific modules: Local plugins (keyboard logging, MiniDump, registry dumping) only work on Windows; Linux/Mac builds may silently skip them without error. Nmap fallback expectations: Service fingerprinting now implements nmap-style fallback (try port X as service A, if timeout try as B); existing custom port-service mappings in constants.go may conflict if order is wrong. SOCKS5 global dialer: Connection reuse optimization means proxy failures may affect subsequent scans in same binary invocation; state isolation per scan may need verification. CEL expression safety: POC scanning uses CEL (Common Expression Language); no sandboxing visible; arbitrary CEL in untrusted POCs could cause resource exhaustion. Output file encoding: TXT output real-time flush may cause character encoding issues on Windows; check output/buffer.go for encoding handling.
🏗️Architecture
💡Concepts to learn
- Bloom Filter Deduplication — Fscan mentions 'intelligent scanning mode with Bloom filter deduplication' in v2.1.0; essential for avoiding duplicate work across overlapping CIDR ranges or when rescanning failed targets.
- Token Bucket Rate Limiting (ICMP) — v2.1.0 added 'ICMP token bucket limiting' to prevent router crashes during high-speed host discovery; understanding token bucket prevents users from misconfiguring thread counts.
- Nmap Service Fingerprinting Fallback — Core refactor in v2.1.0 implements nmap-style fallback: if port 80 doesn't respond as HTTP, try as HTTPS/SOCKS/etc. Critical for accurate service detection when services run on non-standard ports.
- NTLM Hash Authentication — SMB brute-force accepts NTLM hashes directly (pass-the-hash), not just plaintext passwords; fscan's 'Hash collision' capability exploits this Windows auth quirk.
- CEL (Common Expression Language) Evaluation — POC scanning engine uses CEL expressions for conditional exploitation logic; unbound CEL execution poses resource exhaustion risk if malicious POCs are loaded.
- DNSLog Out-of-Band Data Exfiltration — Fscan supports DNSLog detection for blind vulnerabilities (e.g., SQL injection, XXE); requires external DNSLog service configuration and is critical for detecting flaws in air-gapped networks.
- Redis Master-Slave Replication RCE — Fscan's Redis exploitation module leverages replication protocol to inject Lua scripts or shared objects for code execution; understanding replication is key to using this module safely.
🔗Related repos
projectdiscovery/naabu— Port scanner focused on speed and accuracy; fscan adopted nmap-style fallback from naabu's service detection strategy.projectdiscovery/nuclei— POC-based vulnerability scanner with YAML/CEL templating; fscan integrates xray POC format (similar to nuclei templates) for exploit automation.projectdiscovery/httpx— Web service fingerprinting and title/CMS detection; fscan's 40+ web fingerprints and WAF/CDN detection mirror httpx's probe capabilities.lair/lair— Penetration test reporting and collaboration platform; natural downstream consumer of fscan JSON output for asset inventory and risk aggregation.nmap/nmap— Original inspiration for fscan's port scanning and service fingerprinting engine; v2.1.0 refactor explicitly cites 'nmap core integration' (three improvements: probe strategy, matching engine, version parsing).
🪄PR ideas
To work on one of these in Claude Code or Cursor, paste:
Implement the "<title>" PR idea from CLAUDE.md, working through the checklist as the task list.
Add comprehensive unit tests for common/parsers/parsers.go
The parsers module handles protocol identification and service fingerprinting (20+ services mentioned in README), but only has a parse_test.go file. Given the criticality of accurate service detection to the scanning pipeline, this module needs expanded test coverage including edge cases for malformed responses, timeout scenarios, and false positive prevention across different service types (SSH, FTP, MySQL, MSSQL, Oracle, Redis, etc.).
- [ ] Examine common/parsers/parse_test.go to understand existing test structure
- [ ] Review common/parsers/parsers.go to identify untested code paths
- [ ] Add table-driven tests for each of the 20+ supported service fingerprint patterns
- [ ] Add tests for edge cases: truncated responses, partial protocol headers, concurrent parsing
- [ ] Add tests for false positive prevention across similar protocols
- [ ] Run coverage tool to achieve >80% coverage on parsers.go
Add integration tests for common/proxy/manager.go in GitHub Actions workflow
The proxy module (manager.go, detector.go, httpdialer.go, tlsdialer.go) is critical infrastructure for routing scan traffic through proxies, but there are no GitHub Actions CI tests validating proxy detection and HTTPS/TLS dialing logic. The test-build.yml workflow exists but lacks proxy integration tests. This is essential given the security-sensitive nature of proxy handling in internal network scanning.
- [ ] Review existing .github/workflows/test-build.yml structure
- [ ] Review common/proxy/manager_test.go and common/proxy/types_test.go for existing test patterns
- [ ] Create proxy integration test cases covering: HTTP proxy detection, HTTPS CONNECT tunneling, TLS dialing through proxies, proxy authentication
- [ ] Add test fixture to set up mock proxy servers in CI environment
- [ ] Extend test-build.yml workflow with a 'proxy-integration-tests' job
- [ ] Document proxy testing requirements in a new TESTING.md or update existing guidelines
Add unit tests for common/config/constants.go and expand constants_test.go
The constants module defines configuration defaults critical to scanner behavior (port lists, service types, default credentials, timeouts), but constants_test.go appears minimal. With 133 built-in ports, 28 service brute-force types, and 40+ fingerprints mentioned in README, the constants need validation tests to prevent configuration drift, ensure port lists remain valid, and validate that changes to constants don't break dependent modules.
- [ ] Review common/config/constants.go to identify all exported constants and config maps
- [ ] Expand common/config/constants_test.go with tests validating: port list integrity (no duplicates, valid ranges), service type consistency, fingerprint pattern syntax, weak password list quality
- [ ] Add tests ensuring constants match the documented feature counts (133 ports, 28 services, 40+ fingerprints)
- [ ] Add tests preventing common configuration errors (e.g., overlapping port ranges, invalid CIDR notation in defaults)
- [ ] Run coverage to achieve >85% on constants.go
🌿Good first issues
- Add unit tests for
common/output/buffer_test.gocovering the dual-write mechanism with concurrent writers simulating parallel port scans; current coverage missing edge cases like buffer overflow during high-velocity result generation. - Implement missing i18n translations in
common/i18n/locales/zh.yamlanden.yamlfor all log messages in newly refactored modules (identified in v2.1.0 changelog as 'i18n framework upgrade'); audit LogDebug calls (reduced from 71→18) for untranslated output strings. - Add integration test in
common/api_test.gofor the new fingerprint priority sorting and concurrent matching optimization mentioned in v2.1.0; currently only unit tests exist—test behavior with 3139 FingerprintHub entries against slow/fast network responses.
⭐Top contributors
Click to expand
Top contributors
- @ZacharyZcR — 65 commits
- @shadow1ng — 14 commits
- @tongque0 — 12 commits
- @cdxiaodong — 2 commits
- @LingJingMaster — 2 commits
📝Recent commits
Click to expand
Recent commits
db0b53b— fix(ci): 扩展 UPX 压缩范围覆盖 ARM/MIPS/FreeBSD 架构 (ZacharyZcR)4c58843— chore: 版本号更新为 2.1.2 (ZacharyZcR)760c8ea— v2.1.2 核心优化与多架构发布 (#561) (ZacharyZcR)594f567— Update README.md (ZacharyZcR)6b13b2e— feat: 添加 GitHub Issue 模板 (ZacharyZcR)03b21f9— docs: 测试构建 (ZacharyZcR)2674e46— docs: 测试构建 (ZacharyZcR)d4a4867— docs: 测试构建 (ZacharyZcR)6fe1f11— docs: 测试构建 (ZacharyZcR)6f17deb— docs: 测试构建 (ZacharyZcR)
🔒Security observations
Failed to generate security analysis.
LLM-derived; treat as a starting point, not a security audit.
👉Where to read next
- Open issues — current backlog
- Recent PRs — what's actively shipping
- Source on GitHub
Generated by RepoPilot. Verdict based on maintenance signals — see the live page for receipts. Re-run on a new commit to refresh.