Quantcast
Channel: Issues for Drupal core
Viewing all articles
Browse latest Browse all 298646

Prevent XSS in data attributes

$
0
0

Problem/Motivation

It is a common mistake in contrib JS to use markup from a data attribute without sanitizing it.
Modules will store some description or caption in a data attribute then use it in JS without realizing an attacker could provide a data attribute containing malicious JS.

(There has been at least 5 vulnerabilities related to this fixed in contrib in the last 6 months.)

Other attributes could be vulnerable (most often alt and title) but I'm not sure we could cover every scenario, just make some exploits harder.

Steps to reproduce

Typically a module will generate this kind of markup:

<a data-title="Foo" href="https://example.com">Click me</a>

Then on click will use it like this:

$('.description').html($(this).data('title'));

If an attacker is able to insert links with data attributes in the page, it can be used to inject malicious JS:

<a data-title="&lt;img src=x onerror=alert()&gt;" href="https://example.com">Click me</a>

This is often mitigated by the fact the default CKE config does not allow data attributes.
But Xss::filter() does and it is used by several contrib modules to filter user input.

This is of course a vulnerability in the JS itself, but we could make it harder to exploit.

Proposed resolution

Standard::filterXssDataAttributes() already does this but for some reason it is not on the parent Xss class.
So it could be as simple as moving this method to the parent class.

The only caveat I see is that it could remove some legitimate strings that look like HTML from data attributes.
Data attributes can contain arbitrary strings so it is hard to sanitize them without breaking some legitimate strings.

Remaining tasks

User interface changes

Introduced terminology

API changes

Data model changes

Release notes snippet


Viewing all articles
Browse latest Browse all 298646


<script src="https://jsc.adskeeper.com/r/s/rssing.com.1596347.js" async> </script>