iPhone Support Scam Analysis

August 11, 2017

While trolling on shady websites without adblock, I thought I was finally on to something when Chromium asked to open a link with xdg-open. I'm using Chromium with the responsive device layout set to iPhone 6, so I'm triggering all the iOS-specific advertisements and popups.

What I found was an iPhone support scamming website, safari-care[.]xyz/11.html (square brackets mine to prevent clicking). This is the second URL hosting the same HTML I've found. I'll hopefully include a list of these at the end of this post.

So what is 11.html doing opening xdg-open? Let's look at the page source.

<p id="result" style="color:red"></p> ... <script type="text/javascript"> ... var extraData = ""; for (itxextraData = 0; itxextraData < 1; itxextraData++) { var extraData = extraData + "hello"; } jQuery('#result').append('<a href="itunes:' + extraData + '%00">.</a>'); document.querySelector('a').click(); document.querySelector('a').click(); document.querySelector('a').click(); document.querySelector('a').click(); // 57 in total ...

As a result of those jQuery clicks, Chromium asks to open a link with xdg-open, but only once. Maybe something else will happen if I try on my iPhone? I opened the page in Brave, but nothing popped up. Next I tried Safari, and bam!

Safari cannot open the page because the address is invalid.

Every time you click OK, another dialog will open. To a non-savvy user, they might truly think they've been locked out of their phone, or at least Safari.

So what is the underlying issue here? I'll attempt to make a PoC later, and will link to it from this post. Right now, I'll guess that the %00 null byte at the end of the URL is the issue. (See update) That would definitely mess with string parsing if it's not handled correctly. Another issue that makes this whole scam possible is the jQuery click handler. Being able to repeatedly call click on behalf of the user to mimic legitimate user interaction is clearly broken.

Thanks for reading.


From making my proof of concept, I have shown that the null byte is not necessary for this bug to be abused.