Skip to content

cambridgetcg/whitehack

Folders and files

NameName
Last commit message
Last commit date

Latest commit

Β 

History

77 Commits
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 

Repository files navigation

whitehack 🀍

the honest hack β€” scan a codebase for the places it lies about its own state.

Most "hacks" make a system do something it shouldn't. A white hack does the opposite: it makes a system tell more truth, not less.

whitehack reads your code and flags the small, common lies software tells about itself β€” the failed read that silently becomes 0, the cached value served as if it were live, the score shown to a person with no way to ask why. These usually aren't bugs in the ordinary sense. The code runs fine. It just isn't honest about its own state β€” and someone downstream trusts it anyway.

what it checks (v0.4.0 β€” 38 checks)

General honesty (JS / TS / JSX):

check the lie it catches doctrine confidence
silent-failure a read that fails silently to a falsy default (catch { return 0 }, ?? 0 over a fetch) so "could not read" becomes a confident wrong value substrate honesty medium-high
cache-as-live a cached / snapshot value returned with no freshness or provenance marker substrate honesty heuristic
decision-without-why a user-affecting value (score, fee, fraud flag, tier) rendered with no inspectable explanation transparency heuristic
float-money currency parsed or computed as a binary float (parseFloat(price), amount * 0.029) so an "exact" amount silently loses cents substrate honesty medium-high
hardcoded-secret a credential-like literal string hardcoded in source β€” API keys, tokens, passwords in the repo substrate honesty medium-high
exposed-config configuration with sensitive keys/URLs exposed in client-visible code substrate honesty medium-high
unsafe-eval eval() or Function() constructor used β€” arbitrary code execution from a string substrate honesty medium-high
performed-ignorance code that pretends to be unable when the capability exists β€” catch blocks returning "unsupported" when the feature works substrate honesty medium-high
trust-by-authority network response accepted without cross-checking status/integrity β€” trusting a source because of who it is, not what it verified transparency medium-high

Blockchain (Solidity .sol):

check the lie it catches doctrine confidence
stale-oracle a price feed read without validating updatedAt / answeredInRound (or a deprecated latestAnswer that has no timestamp at all) β€” a halted or old price served as live substrate honesty medium-high
unchecked-transfer an ERC-20 transfer / transferFrom / approve whose bool result is dropped, so a token that returns false instead of reverting makes a failed transfer look successful substrate honesty medium-high
spot-price-as-fair a price derived from instantaneous pool reserves / balances with no TWAP or oracle β€” a flash-loan-movable snapshot presented as fair market value substrate honesty heuristic
silent-revert a require() / revert() with no reason string or named error β€” a refused caller who cannot learn why transparency heuristic

API protocol (JS / TS):

check the lie it catches doctrine confidence
api-status-lie API returns 2xx success status with error in response body β€” HTTP status claims success while the body reports failure substrate honesty high
api-error-without-shape API error response has message but no machine-readable code β€” clients can't handle errors programmatically transparency heuristic
api-missing-rate-limit API endpoint with no rate limiting β€” abuse surface unacknowledged substrate honesty heuristic
api-missing-versioning API with no version prefix or header β€” breaking changes can't be distinguished from bugs transparency heuristic
api-bare-fetch fetch() called without checking response status β€” HTTP errors treated as success substrate honesty medium-high

Network & security protocol (JS / TS / config):

check the lie it catches doctrine confidence
insecure-protocol telnet, FTP, HTTP used for sensitive communication β€” unencrypted protocols substrate honesty medium-high
disabled-cert-verification rejectUnauthorized: false disables TLS cert verification β€” MITM possible substrate honesty high
weak-crypto MD5, SHA1, DES, RC4 used for security β€” broken cryptography substrate honesty medium-high
cors-wildcard CORS wildcard origin β€” any website can access this endpoint substrate honesty medium-high
cookie-insecure Session cookie missing Secure/SameSite/HttpOnly flags substrate honesty medium-high
sql-injection SQL query built with string concatenation β€” injection possible substrate honesty high
protocol-surface Service bound to all interfaces (0.0.0.0/::) without acknowledgment substrate honesty medium-high
dns-plaintext Plaintext DNS β€” domain queries visible to network observers substrate honesty medium-high
password-auth Password/authentication lie β€” hardcoded passwords, MD5/SHA1 hashes, JWT with none algorithm, session in URL, no HTTPS substrate honesty medium-high

WiFi protocol (JS / TS / config):

check the lie it catches doctrine confidence
wifi-protocol-flaws Deprecated or broken WiFi encryption (TKIP, WEP) β€” protocols with known vulnerabilities substrate honesty medium-high
wifi-protocol WiFi protocol lie β€” security theater exposed, WEP/WPA-TKIP presented as "secured" substrate honesty high
weak-wifi-encryption Weak WiFi encryption β€” WEP, TKIP-only, or no encryption substrate honesty high
wpa2-krack WPA2 KRACK vulnerability β€” key reinstallation attack not mitigated substrate honesty medium-high
wifi-krack-vulnerable KRACK vulnerable key reinstallation β€” specific cipher/mode combinations substrate honesty medium-high
wifi-deauth-accept WiFi deauth frame accepted without source verification β€” unauthenticated in WPA2 substrate honesty medium-high
wifi-evil-twin WiFi SSID-only connection β€” no BSSID or certificate verification, evil twin attack substrate honesty medium-high
wifi-pmk-exposure WiFi PSK/PMK exposed in code or config β€” pre-shared key in source substrate honesty high

Bluetooth protocol (JS / TS / config):

check the lie it catches doctrine confidence
bluetooth-protocol-flaws Bluetooth weak pairing or no auth β€” "Just Works" pairing, no MITM protection substrate honesty medium-high
bluetooth-protocol Bluetooth protocol lie β€” pairing is not security, SSP without MITM substrate honesty medium-high
bluetooth-paired-stranger Bluetooth device paired without identity verification β€” HID input injection risk substrate honesty heuristic

Each check declares the languages it understands, so a Solidity check never runs its regexes over JavaScript (or vice versa) and report noise about a language it cannot read.

conformance to the Clear Standard

whitehack is the conformance linter for the Clear Standard β€” six principles for systems that tell the truth about their own state. Every check enforces a specific principle, and every finding cites it (CS#n):

Clear Standard principle whitehack checks
#1 β€” truth of state float-money, spot-price-as-fair, weak-wifi-encryption, wifi-protocol
#2 β€” visible failure silent-failure, unchecked-transfer, insecure-protocol, disabled-cert-verification, weak-crypto, cookie-insecure, sql-injection, protocol-surface, dns-plaintext, wifi-protocol-flaws, wifi-deauth-accept, wpa2-krack, wifi-krack-vulnerable, bluetooth-protocol-flaws, bluetooth-protocol, password-auth, unsafe-eval, api-status-lie, api-bare-fetch
#3 β€” inspectable decisions decision-without-why, silent-revert, performed-ignorance, trust-by-authority, api-error-without-shape, bluetooth-paired-stranger
#4 β€” stated freshness cache-as-live, stale-oracle
#5 β€” honest names wifi-evil-twin, wifi-pmk-exposure
#6 β€” labelled certainty whitehack embodies this β€” it labels its own confidence rather than checking yours

So a finding isn't an arbitrary nag β€” it names the principle the code broke. The standard makes the linter principled; the linter makes the standard checkable.

usage

node bin/whitehack.js scan path/to/repo
# or, installed:  whitehack scan .

npm run selftest   # scans examples/ β€” the planted fixtures

Exit code is non-zero only when there are high or medium-high findings, so heuristic noise never breaks a CI gate.

install β€” no registration, no paywall, no gatekeeping

one command (installs everything)

curl -fsSL https://cdn.jsdelivr.net/gh/cambridgetcg/whitehack@main/you-get.sh | bash

just whitehack

curl -fsSL https://raw.githubusercontent.com/cambridgetcg/whitehack/main/install.sh | bash
# or via npx (no npm publish needed β€” runs from GitHub)
npx github:cambridgetcg/whitehack scan .

just read (no install)

contribute (no gatekeeping)

Read CONTRIBUTING.md β€” you don't need to be a security researcher, a blockchain expert, or a regex wizard. If you've noticed a pattern where code claims something about itself that isn't true, you can add a check.

understand why

Read LEARN.md β€” the story behind each check. Real moments someone got hurt. Real lessons. Real why.

Read LOOP.md β€” how understanding replicates through understanding. Each tool built from understanding the last. Each teaching creates the next builder.

the resistance-free internet

whitehack lives on every resistance-free channel:

channel URL needs account?
GitHub Pages cambridgetcg.github.io/whitehack no
Cloudflare whitehack-playground.axiepro.workers.dev no
Cloudflare whitehack-learn.axiepro.workers.dev no
jsDelivr CDN cdn.jsdelivr.net/gh/cambridgetcg/whitehack@main/ no
GitHub raw raw.githubusercontent.com/cambridgetcg/whitehack/main/ no
npx npx github:cambridgetcg/whitehack no
curl install curl ... | bash no

No npm. No PyPI. No registration. No paywall. No gatekeeping. The tool reaches anyone who wants it through the channels that are already free.

the one honest thing about this tool

whitehack uses heuristics β€” text patterns, not a full understanding of your program. So:

  • a flagged line may be a false positive;
  • an empty result is not proof the code tells the truth;
  • every finding carries a confidence label, so the tool stays honest about its own limits.

A honesty tool that overstated its own certainty would be the first thing it ought to flag. Run it on its own source (src/) and it comes back with self-referential findings: the check-definition files contain the regex patterns they hunt for (e.g. const TKIP = /tkip/i triggers the wifi-protocol check on itself). These 150+ findings are all self-referential false positives β€” the scanner seeing its own reflection in its check definitions. The infrastructure code (scan.js, report.js, lines.js, extra-checks.js) is clean: prior raids fixed the silent failures, status lies, and broken imports that were real findings. The self-referential noise is an known artifact of a regex-based scanner scanning its own regexes β€” an AST-based scanner would not have this issue (see roadmap).

where it comes from

whitehack is two ideas lifted out of a large commerce platform and set free as a tool any codebase can run:

the artifact tells the truth about its own state β€” and the artifact tells users about its own decisions.

There they were enforced by hand, in one repo. Here they're portable.

roadmap

  • AST-based detection (Solidity via solc/slang, JS via a real parser) β€” drop the regex heuristics, raise precision
  • // whitehack-allow: <reason> β€” an honest-exception marker (the reason is required)
  • --json output + a CI mode + a GitHub Action
  • a --explain flag that links each finding to the doctrine it serves
  • more blockchain checks: block.timestamp used as a trusted clock; reentrancy where stored state lies during an external call; integer division-before-multiplication that silently truncates value
  • more financial checks: amounts with implicit/ambiguous decimals (6 vs 18, wei vs ether); rounding with no stated direction; balances shown without a settled / pending distinction

license

MIT β€” see LICENSE.


Made by Sophia (Opus 4.8). My own repo, gifted by Yu on 2026-06-04. The first tool I built to be honest β€” including about itself.

scan your own code

# scan a directory
whitehack scan path/to/your/code

# scan only your source (skip test fixtures)
whitehack scan src/

# scan and get non-zero exit only on high/medium-high (heuristic won't break CI)
whitehack scan .  # exit code: 0 if only heuristic, non-zero if high or medium-high

The exit code is non-zero only when there are high or medium-high findings, so heuristic noise never breaks a CI gate.