– The web developer’s perspective –
Just a few days into 2018, security researchers have published a number of extremely serious hardware vulnerabilities that affect virtually all systems with Intel, AMD or ARM processors. As operating system vendors rush to fix the problem in software, the developers of popular internet browsers have also been busy – there have been announcements from all major players:
- The SharedArrayBuffer object has been disabled without replacement. This object has been introduced in ES2017, but the few web applications already using it will break with the next browser update. While disabling this functionality is supposed to be a temporary measure, there is no date set for its reintroduction. Significant redesign might be required to make existing applications relying on this feature compatible – lacking the shared buffer, web workers need to fall back to message passing for synchronization and data transfer.
- The resolution of the performance.now() timer has been reduced from 5 µs to 20 µs, but the method itself will continue to work. If your application relies on sub-millisecond timings, this might be a problem for you; otherwise, you can keep using the timer as usual.
Using SharedArrayBuffer to build a precise timer [see link for full paper above]
By disabling these features, browsers made it effectively impossible to measure time beyond a certain precision. This is just a stop-gap measure, and since attackers might come up with new ways to take advantage of the underlying vulnerability, in the upcoming months browser developers will be working on ways to prevent a successful exploit from extracting meaningful data even if precise timing functions are available.
The Chromium team also has a few recommendations for all web developers to limit the impact of these (and any related future) vulnerabilities. These best practices help keep sensitive data (like credentials and tokens) outside the memory of the renderer process – as the process might be shared between pages, malicious scripts can use the hardware vulnerabilities to read data from parts of that memory that would otherwise be inaccessible to them.
- Prevent cookies from being loaded into the memory of the renderer using options present in the Set-Cookie header.
- Mark cookies that should only ever be sent by first-party requests as strict SameSite – these cookies will only be sent when the origin of the request is from the same site as the target URL.
- For cookies that cannot be marked HTTPOnly, make sure to only access the cookie variable on pages where and when it is explicitly required. Cookies are only loaded into the renderer right before the first access to this variable.
- Make it hard to guess and access the URL of pages that contain sensitive information. All API endpoints that return sensitive data using GET requests need to be protected. If the URL is known to the attacker, the renderer might be forced to load it into its memory. Same-origin policies alone do not protect against these attacks.
- Use random, unique, expiring URLs that are hard to guess and have no discernible pattern that an attacker can learn.
- Deploy and require anti-CSRF tokens for all requests to API endpoints.
- Place and validate the presence and content of SameSite cookies to ensure that the request comes from a first-party site.
- Ensure that all responses are returned with the correct MIME type, and that the content type is marked as nosniff. This will prevent the browser from reinterpreting the contents of the response, and can prevent it from being loaded into the memory of the renderer when a malicious site tries to load it in certain ways. This works great in conjunction with the Site Isolation feature of Chrome, which can separate the different pages by origin into different renderer processes.
These best practices have been around for a while now, but their importance has just skyrocketed as the fundamental assumptions underlying the security model of the data stored in browser memory are being challenged. In general, learning and following industry standard secure coding best practices play an important role in protecting against current and future threats, even when such threats originate from outside the traditional domain of web applications.
To learn more about secure web development, check out our courses here.