Today I want to share a short write-up about a stored cross-site scripting (XSS) issue I found on the Google Cloud Console. I consider it a lucky find. Some of you may remember the tweet I sent to Frans Rosén after he discovered a vulnerability on Google Payments:

As it turned out, among the unsuccessful XSS payloads I saved on my Google account, there was one that actually fired. But unexpectedly. When I was originally testing my payloads, I never managed to trigger the execution until recently and inadvertently. But let’s start from the beginning.
Finding the bug#
As you may know, Google is offering a 60 day free trial with a budget of $300 and all that is required is entering (correct) payment information to prove you are not a robot. So, I did that a few weeks ago and started entering XSS payloads in every field I could find … and nothing fired, I failed. A situation I assume we’ve all been in, right? Well, after two months or so, I received an invoice from Google and a notification that my free trial was ending. Wanting to avoid the charges, I quickly logged into my account and deleted my project, which was titled “> <img src = x onerror = javascript: alert (1); … and boom, my payload got Executed!

The vulnerability#
As it turned out, Google was not filtering the error message once a project was canceled. Astute readers may question why this was not classified as a low level self XSS. This issue was escalated because the Google Cloud Platform can be used by multiple users; if a user creates a project with a malicious XSS payload, that payload could be used against the project administrator to execute malicious JavaScript (if they delete the project, which seems likely).
Proof of concept#
For those unfamiliar, and the knowledge hungry, here’s how the payload gets reflected in the content of the site: the first quote and angle bracket, “>” close the preceding HTML tag which allowed my injected tag to be rendered in the page source. For this POC, I simply used the img src = x payload. Since x is not a valid URL, this is designed to fail immediately with a 404 HTTP response, which will then invoke the onerror event to execute a JavaScript function. However, thanks to @Jobert from HackerOne for noting that it’s possible this could have returned a 2xx or 3xx redirecting to a 2xx in which case my payload would not have fired. In my testing, I just added the function alert to create a popup but malicious users could have used a cookie stealer or the Browser Exploitation Framework Project (BEEF) to escalate this issue (I did not have to demonstrate that to Google, though).

Here’s the video POC I sent in for the Google VRP:
That’s it 🙂
Disclosure#


Thanks to Peter @yaworsk for editing :-)! Follow him and support him by buying his book !




