A stored XSS vulnerability in Yahoo Mail was patched earlier this month. The flaw allowed malicious JavaScript code to be embedded in a specially formatted email message. The code would be automatically evaluated when the message was viewed. The JavaScript could be used to e.g. compromise the account, change its settings, and forward or send email without the user’s consent.
We provided Yahoo with a proof of concept email that would forward the victim user’s inbox to an external website, and an email virus which infects the Yahoo Mail account and attaches itself to all outgoing emails. The bug was fixed before any known exploits “in the wild”.
The bug has affected all versions of Yahoo’s webmail but not the mobile app. Yahoo Mail is reportedly the second-largest email service globally with almost 300 million email accounts as of February 2014.
Details
As most email solutions these days, Yahoo Mail displays HTML-formatted email messages after filtering any potentially malicious code. The problem lies in this process. Certain malformed HTML code could pass the filter.
As a starting point for our investigation, a message containing all known HTML tags and attributes was created to see which of them the Yahoo filter lets through. After viewing the resulting email on Yahoo Mail, we noticed that if certain, supposedly “boolean” HTML attributes were given a value, the value was removed by the filter, but the equals sign was not. For example
<INPUT TYPE="checkbox" CHECKED="hello" NAME="check box">
would become
<INPUT TYPE="checkbox" CHECKED= NAME="check box">
This may seem pretty harmless on the first look, but web browsers handle this case rather unintuitively: this is interpreted as CHECKED having the value NAME=”check, plus the tag containing a third attribute named box without a value. The behavior is based on the HTML specification which allows “zero or more space characters” around the equals sign in an unquoted attribute value.
The confusion can be exploited to insert unrestricted HTML attributes in tags that allow a “boolean” attribute. In the PoCs we used the <IMG> tag. Example:
<img ismap='xxx' itemtype='yyy style=width:100%;height:100%;position:fixed;left:0px;top:0px; onmouseover=alert(/XSS/)//'>
After Yahoo Mail filtering this would effectively become (some of the quote symbols edited for clarity):
<img ismap=itemtype=yyy style=width:100%;height:100%;position:fixed;left:0px;top:0px; onmouseover=alert(/XSS/)//>
On viewing this Yahoo Mail message, the browser would render an IMG tag filling the entire window. The JavaScript code in the onmouseover attribute would be immediately executed, without further user interaction. Blocking or allowing images in mail settings didn’t affect this behaviour.
Vendor response
The bug was found and reported to Yahoo on December 26, 2015 via the HackerOne bug bounty platform. The bug was fixed on January 6, 2016. Yahoo awarded a bounty of $10,000 for finding and reporting the flaw.
Demo
Credits
The vulnerability was discovered and researched by Jouko Pynnönen of Klikki Oy, Finland.
Updated January 19, 9:30 EET: Added a link to HTML specification.