The Unazoomer

CSS Fingerprinting

by Oliver Brotchie

An experimental method for CSS based fingerprinting and a pure CSS "supercookie".

What is it?

CSS Fingerprinting is a technique of tracking and gathering information on site visitors. This method exploits the nature of CSS to collect various characteristics about the visitor’s browser and device, which can later be used to either identify or track said visitor.

How does it work?

By sending a variety of media queries that apply to specific browser characteristics, the browser will select a set of styles that apply to itself. We then trick the browser into sending this information back to the server by setting the background-image of these styles to a specific URL. The server will then respond with HTTP Status 410 (Gone) to avoid any requests of these characteristics on subsequent reloads.

Font detection works a little differently; every font not installed on device will send a request. By comparing the differences between the requests and the full list of fonts, we can conclude what fonts are installed.

We can also track visitors cross-origin by requesting an endpoint on the server that will return a permanent redirect (HTTP status 308) to a unique address. The browser will then permanently make requests to the previously generated unique address whenever the endpoint is requested. This creates a pure CSS cookie that is reminisent of the ’supercookie’ exploit. This cookie is stored for an unlimited amount of time; the only way to remove it is to fully clear the browser’s cache.

Why is this important?

This technique avoids anti-tracking methods such as NoScript, VPNs or browser extensions, as it requires no Javascript or Cookies to function.

Currently, this method is not scalable as it requires over 1MB of CSS downloads and hundreds of requests per user. However, with the next upcoming draft of the CSS specification, CSS Values 4, it may dramatically shrink the number of requests per user by allowing the use of custom variables in URLs.

Not only will the upcoming draft make this method scalable, but it will also increase its precision. Currently, without alternative means, it is hard to conclusively link every request to a specific visitor as the only feasible way to determine their origin is to group the requests by the IP address of the connection. However, with the new draft, by generating a randomized string and interpolating it into the URL tag for every visitor, we can accurately identify all requests from said visitor.

Why this method beats all current anti-fingerprinting methods

Current anti-fingerprinting mostly focuses on the blocking or spoofing JavaScript APIs. If JavaScript is blocked we can detect it with CSS, at which point you could use server-side code to inject the CSS-based fingerprinting to detect the other characteristics of the device.

The other problem is the way in which most major browser currently treat permanent redirects in CSS files. CSS permenant redirects will always uniquely identify a user on a single origin without the need for client side code, however, currently most browsers cache permenant redirects in relation to the CSS document not the page origin - allowing for cross-origin tracking.

Read more and see some examples over at OliverBrotchie/CSS-Fingerprint.