# Field Day With Protocol Handlers

Brave's protocol permission prompt is remembered globally and the url: handler wraps any scheme, letting any site launch mailto/bitcoin/telnet handlers without consent.

- Payout: hidden
- Severity: medium
- Program: Brave Software
- Found by: dudetechitout
- Disclosed: 2018-12-17
- Write-up quality: 6/10
- Original: https://hackerone.com/reports/416040
- Library page: https://bugbountylibrary.com/r/h1%3A416040
- Tags: area:os domain:browser impact:dos impact:integrity kind:bounty platform:hackerone sev:medium technique:chained vuln:access-control vuln:auth-bypass vuln:business-logic

**Target:** Brave browser protocol handler permission prompt (browser-laptop)
**Root cause:** Protocol allow/deny decisions are stored globally rather than per-origin, and the url: scheme handler forwards to arbitrary inner schemes without re-prompting.
**Steps:**
1. Open wallet_landing.html and click 'Click here to enable the bitcoin protocol in Brave.'
2. Select 'Remember this decision' and click 'Allow'.
3. Navigate to a second page that calls `window.open("bitcoin:" + address + "?amount=" + amount, "loader")` — wallet launches with no prompt.
4. To bypass all permissions, change payload to `window.open("url:mailto:" + address + "?amount=" + amount, "loader")` and allow the `url:` protocol once.
5. Any subsequent site can then launch mailto:, sms:, bitcoin:, acrobat:, search:, telnet:, ssh: etc. without prompting.
**How found:** Noticed Brave only prompts for the `url:` scheme and that remembered decisions apply globally; tested wrapping mailto/bitcoin inside `url:` and compared behavior against Firefox, IE and Chrome which ignore it.
**Exploitation:** Attacker page triggers a protocol launch once to get the user to tick 'Remember this decision'; afterwards any origin (e.g. malicious.com) can invoke the same or wrapped protocols via window.open or iframes, auto-filling bitcoin wallet address/amount or opening mail/telnet clients.
**Escalation:** Wrapping arbitrary schemes inside `url:` bypasses the permission prompt entirely; looping window.open every 300ms (removing clearInterval) exhausts resources and can crash browser/OS.
**Insight:** When a browser exposes a generic wrapper scheme (url:, or similar) that forwards to other registered handlers, test whether the wrapper's permission grant transitively authorizes the inner scheme — and whether 'remember' decisions are scoped per-origin or globally.

