Safari Mobile sometimes not loading script files when using a Self-Signed Certificate

I have found a bug in Mobile Safari on iOS 11 (details see below) which I have also reported via the Apple bug reporter (Problem ID 36238559). However, there has not been an answer so far in the bug reporter and we do need some response urgently because it is intended to roll out this software very soon. Most tests have been done using iOS 10 where this bug did not occur, so the problem was only found now when repeating tests on iOS 11.


Currently, the available infrastructure means that we have to support webservers with self-signed certificates. So, question is whether this is a known issue and there will maybe be a fix available in the near future or whether someone else knows a different workaround we could try.


Summary


I have found a bug in Mobile Safari in iOS 11 (but not iOS 10) that causes javascript applications to fail when they are loaded from a webserver using a self-signed certificate, are loaded soon after Safari was started and work by including other javascript files from the same host.

How to reproduce the bug


My setup uses an IIS (Microsoft Internet Information Services) which has SSL enabled and uses a self-signed certificate create from within IIS. There is a directory with the content of this ZIP archive.


There is basically one simple html page that looks like this:


<
html
>
<
head
>

<
script
>

var counter = 0;

</
script
>

<
script
src
=
"JS/1.js"
></
script
>

<
script
src
=
"JS/2.js"
></
script
>

<
script
src
=
"JS/3.js"
></
script
>

<
script
src
=
"JS/4.js"
></
script
>

<
script
src
=
"JS/5.js"
></
script
>

<
script
src
=
"JS/6.js"
></
script
>

<
script
src
=
"JS/7.js"
></
script
>

<
script
src
=
"JS/8.js"
></
script
>

<
script
src
=
"JS/9.js"
></
script
>

<
script
src
=
"JS/10.js"
></
script
>

<
script
src
=
"JS/11.js"
></
script
>

<
script
src
=
"JS/12.js"
></
script
>

<
script
src
=
"JS/13.js"
></
script
>

<
script
src
=
"JS/14.js"
></
script
>

<
script
src
=
"JS/15.js"
></
script
>

<
script
src
=
"JS/16.js"
></
script
>

<
script
src
=
"JS/17.js"
></
script
>

<
script
src
=
"JS/18.js"
></
script
>

<
script
src
=
"JS/19.js"
></
script
>

</
head
>

<
body
>

Hello World!

<
script
>

document.write(counter);

</
script
>

</
body
>

</
html
>


And all the referrenced JavaScript files exist all with the same content:



document.write(
"X"
);


counter++;


What we expect to happen when opening the html page with a browser is that we see 19 lines with an X, a row saying “Hello World!” and then the number 19. When this specific bug occurs, we do see fewer lines with an X and a lower number at the end, because some of the included javascript files are not loaded.


How to see the bug in Safari


Open the web page in Safari (on iOS 11) by entering the correct url like in my case on the test server in my local network “https:/ to allow opening this site that does not have a trusted certificate. Confirm that.


When the page was opened and correctly shows the expected result, close Safari by showing the list of running apps on the iOS device and swipe away the Safari app. Then open Safari again. Safari will automatically try to open the same page again. In most cases when doing this, the bug will occur and you will see fewer than expected lines with X and lower number than 19 at the end.


Waiting some time and refreshing the page will then always produce the correct result until you restart Safari again.


This video shows the described behaviour on an iPad: https://www.youtube.com/watch?v=H-_1NM0LEHI


What the developer tools see


When using the Safari developer tools on a Mac connected to the iOS device, we can see what goes wrong:


Image at https://www.neunbeere.de/blog/wp-content/uploads/2017/12/iOSBugErrors.png


Some of the referenced javascript files could not be loaded. The set of javascript files that fail loading changes at every attempt. Sometimes when we are quick enough in opening the developer tools, the console will also give the following error message: “Failed to load resource: The certificate for this server is invalid. You might be connecting to a server that is pretending to be 10.50.75.208 which could put your confidential information at risk.”


Speculation: What’s the bug?


My speculation as to what is happening in Safari internally is the following: When Safari starts, it will try to load the list of accepted untrusted ssl certificates in a background task. For some reason, accessing this list and loading this list is not correctly synchronized so that during a short period after starting Safari, a check will be made against the list although is has not been fully loaded and the loading of some referrenced resources will then fail because the untrusted certificate used is not found in the incompletely loaded list..

Workaround

The only solution to this problem I have found is to not use a self-signed certificate. You need to actually create your own local CA (Certiciate Authority), install this CA’s public certificate on the iPad, manually enable that it is trusted as a CA, then use this CA to create an SSL certificate and then install and use this SSL certificate in IIS (or some other webserver software)

Replies

You got any solution for this?