webcompat / web-bugs

A place to report bugs on websites.
https://webcompat.com
Mozilla Public License 2.0
747 stars 67 forks source link

rbt.ru - The page is blank #132643

Open webcompat-bot opened 9 months ago

webcompat-bot commented 9 months ago

URL: https://rbt.ru/

Browser / Version: Firefox 123.0 Operating System: Windows 10 Tested Another Browser: Yes Opera

Problem type: Site is not usable Description: Страница загружается некорректно Steps to Reproduce: Вместо сайта отображается белое пространство, в других браузерах отображается содержимое сайта. Загружал сайт в режиме, когда все аддоны отключены, в приватном окне, с отключением защиты от отслеживания - результат тот же.

View the screenshot Screenshot
Browser Configuration
  • None

From webcompat.com with ❤️

sv-calin commented 9 months ago

Thank you for reporting this issue, I was able to reproduce it.

FF Release vs FF Nightly image

Tested on: • Browser / Version: Firefox Nightly 124.0a1 (2024-01-24) / Firefox Release 122 / Chrome 121.0.6167.86 • Operating System: Windows 10

Notes:

  1. Reproducible on Firefox Nightly
  2. Not reproducible on Chrome and Firefox Release

Moving to Needsdiagnosis.

[qa_04/2024]

sv-calin commented 9 months ago

Regression

Last good revision: afc0ccc856c4631667978b6b64045f15b1f8ac3a First bad revision: 15f43f43c82c6898b77523687bb74d7d02665073 Pushlog: https://hg.mozilla.org/integration/autoland/pushloghtml?fromchange=afc0ccc856c4631667978b6b64045f15b1f8ac3a&tochange=15f43f43c82c6898b77523687bb74d7d02665073

[inv_04/2024]

denschub commented 9 months ago

I was slightly confused by the regression range, as the commits in question shouldn't be causing this. So I re-ran mozregression just to be sure, and got the exact same result. Fun times. This doesn't make sense on a first glance, as the changes to some User Agent handling scenario shouldn't be causing any performance issues in this way.

I recorded a profile, and it looks like the site spends all of its JS runtime inside a function called b.prototype.modPow, where the function names decrypt and setCookie appear in the stack. So it somehow sounds like it's trying to decrypt a cookie, and failing at that?

The JS on that page is setting three cookies, ipp_key, ipp_sign, and ipp_uid. It then does something, and ends up reloading the page. I see the same call to setCookie in a working version, but there, the entire process takes ~19ms, instead of multiple seconds in the broken version. It's interesting, however, that even the "working" version is doing this whole process of settings some cookies based on crypto operations, and then reloading the page.

When you access https://rbt.ru/ for the first time, you get a 307 redirect to itself, but with a ipp_uid_tst cookie set, which is a base64 payload that looks like some arbitrary binary data. With that cookie set, you get an HTML response with nothing but a bit of JavaScript. The JS there is, essentially, doing:

  1. Running this library, which is a fork from an older version of fingerprintjs, to get the browser's unique fingerprint.
  2. It then calls the setCookie() function that I noticed in the performance profile.
  3. This function attempts does two things: Setting the ipp_uid cookie to a predefined value (likely injected by server-side templating?), and setting the ipp_key cookie to "ipp_key=" + this.decrypt() + "; Path=/". This decrypt function is also noticeable in the perf profile.
  4. The decrypt function is then using jsencrypt in version 3.0.0-rc.1, it calls .setPrivateKey() on it with a pre-defined value, and it then returns the result of a .decrypt() call, also with a pre-defined payload.

This is all somewhat bizarre.

I captured the responses for the aforementioned "blank"-with-JS page in the Last Good and First Bad builds. they're mostly the same, but there are two very obvious differences:

so that would certainly explain why the operations take so much longer in First Bad.

... but why?

These commits aren't around a version uplift or anything else that would change the UA string. Both requests are made with the exact same UA string, Mozilla/5.0 (Macintosh; Intel Mac OS X 10.15; rv:123.0) Gecko/20100101 Firefox/123.0 in my case. In fact, all the request headers are the same. Exporting request from both builds into a .har and diff'ing them only shows one difference in the headers: the location of the UA header: in Last Good, the UA header is second, right after the Host header; in First Bad, the UA header is fifth, right after the Accept-Encoding header. So, uh, to the best of my knowledge, the difference is caused by that.

The weirdest thing here, however, is that I can't even reproduce this via cURL or anything. If I run the exact request without any cookies with curl, I do not get a 307 redirect at all - instead I immediately get one of those blank-page+JS responses with an even larger payload. Even replaying the captured request in Charles doesn't give ma a 307. So whatever kind of fingerprinting they're doing on the server does wonderfully exciting things.

Looking at the response headers had me notice the Server: Variti/0.9.3a response header. Running a quick Google search on that, I found this blog post from Plesk, naming "Variti" as some sort of DDoS protection. The post also links to this product page, but these days, it only shows "This extension is no longer available". Thanks to the magical powers of the Internet Archive, I was able to pull an old version from the Internet Archive, where the newest version without that red "unavailable" banner was from October 2021. the banner was there in 2022, so this product is clearly deprecated. Also, "Variti International GmbH" used to be a Swiss company, and according to another research run, that company is in liquidation. However, I found a UK/Russian company called Variti Limited that sells a similar service, so maybe they have purchased the assets from that Swiss company.

Ultimately, while this technically is a regression by definition, I cannot justify tracking it as such. It looks like there's some horribly horrible server-side fingerprinting going on, that somehow does weird things when headers are ordered differently, and it then blocks the client with excessively large crypto payloads that keep the CPU busy for a long time. This is a server-side issue, and unless we have evidence of this breaking multiple important sites, this is unlikely to be treated as a regression (although I'll check back with the rest of the team).

However, given the site reported here is ranked 983 in Russia, we should probably try to reach out to the site's dev team and let them know about this... I'll also attempt to get in touch with the new company linked above, as the whois data for the reported site's IP matches that company.

denschub commented 9 months ago

I sent an email to the Variti Limited company. I tried looking for a contact email address on the Russian website, but only found a contact form that requires information I'm unwilling to provide. I'll follow-up on that if the tech company doesn't get back to me. Moving into sitewait for now.