Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

OpenSSL in runtime is outdated, update required #307

Closed
dthommes opened this issue Jun 13, 2018 · 14 comments
Closed

OpenSSL in runtime is outdated, update required #307

dthommes opened this issue Jun 13, 2018 · 14 comments

Comments

@dthommes
Copy link
Contributor

Issue details

RoboVM bundles and uses OpenSSL 1.0.1e (release in February 2013) as can be seen here:
https://github.com/MobiVM/robovm/blob/master/compiler/vm/rt/android/external/openssl/include/openssl/opensslv.h

This version is outdated and has currently 68 open CVEs:
https://www.cvedetails.com/version/157548/Openssl-Openssl-1.0.1e.html

One of them is the heartbleed bug:
http://heartbleed.com/

From a security standpoint, its urgent to update to a secure version of OpenSSL and find a way to keep it updated - this should be semi-automatic in the best case.

Versions:

  • Robovm: 2.3.4-SNAPSHOT

Build Targets:

ALL

Migration Plan
It is probably not possible to retrieve an update of OpenSSL from the official Android sources. In 2014, Google migrated to a custom version of OpenSSL named BoringSSL. They have made many changes and make clear, that BoringSSL "is not intended for general use" (https://github.com/google/boringssl).

Additionally, they introduced the new Open-JDK based runtime that changed, how the crypto functions are built into the VM in 2016. A back-port of their SSL implementation from the new runtime is probably too complicated, especially with the requirement of semi-automation.

I will investigate in replacing the existing OpenSSL source in RoboVM with a newer one from the official OpenSSL repo. However, it is not clear, whether this will suffice.

To stay updated on the one hand and reduce effort on the other hand, I propose to go with a LTS of OpenSSL. The current LTS release is 1.0.2 (until 2019). Then it will be followed by 1.1.1, which is currently in beta (https://www.openssl.org/blog/blog/2018/05/18/new-lts/).


@dthommes
Copy link
Contributor Author

dthommes commented Jun 13, 2018

Workaround for HttpsUrlConnection:

Instead of using Java with underlying OpenSSL:

try {
    HttpsURLConnection urlConnection = (HttpsURLConnection) new URL("https://www.google.com").openConnection();
    urlConnection.getResponseCode();
    System.out.println("Connected successfully via JAVA.");
} catch (IOException e) {
    e.printStackTrace();
}

Use iOS SDK instead

try {
    NSURL nsurl = new NSURL("https://www.google.com");
    NSURLSession.getSharedSession().newDataTask(nsurl, (data, response, error) -> {
        System.out.println("Connected successfully via iOS.");
    }).resume();
} catch (Exception e) {
    e.printStackTrace();
}

Please be aware, that the callback via iOS SDK comes via a different thread, while the above sample with HttpsUrlConnection is synchronous.

@cperez-infoboy
Copy link

Thanks for the help. I will try what you indicate to me

@cperez-infoboy
Copy link

I am trying to compile the project in MacOS but display this error message(Do you know what means this???):

INFO] ------------------------------------------------------------------------
[INFO] Reactor Summary:
[INFO]
[INFO] RoboVM Parent 2.3.4-SNAPSHOT ....................... SUCCESS [ 0.630 s]
[INFO] RoboVM Compiler Parent ............................. SUCCESS [ 0.160 s]
[INFO] RoboVM LLVM Bindings ............................... SUCCESS [ 19.215 s]
[INFO] RoboVM libimobiledevice Bindings ................... SUCCESS [ 12.680 s]
[INFO] RoboVM Runtime Library ............................. SUCCESS [ 40.371 s]
[INFO] RoboVM Compiler .................................... FAILURE [ 39.209 s]
[INFO] RoboVM cacerts parent .............................. SKIPPED
[INFO] RoboVM cacerts full ................................ SKIPPED
[INFO] RoboVM Objective-C Bridge .......................... SKIPPED
[INFO] RoboVM Cocoa Touch Bindings ........................ SKIPPED
[INFO] RoboVM Distribution ................................ SKIPPED
[INFO] RoboVM Distribution (compiler jars) ................ SKIPPED
[INFO] RoboVM Distribution (tar.gz package) ............... SKIPPED
[INFO] RoboVM Templates for Eclipse and Maven integration . SKIPPED
[INFO] ios-single-view-no-ib-template ..................... SKIPPED
[INFO] ios-framework-template ............................. SKIPPED
[INFO] console-template ................................... SKIPPED
[INFO] RoboVM Template Generator .......................... SKIPPED
[INFO] robovm-maven-resolver .............................. SKIPPED
[INFO] RoboVM Junit parent ................................ SKIPPED
[INFO] robovm-junit-protocol .............................. SKIPPED
[INFO] robovm-junit-server ................................ SKIPPED
[INFO] robovm-junit-client ................................ SKIPPED
[INFO] RoboVM Debugger .................................... SKIPPED
[INFO] RoboVM Maven ....................................... SKIPPED
[INFO] RoboVM Maven Plugin ................................ SKIPPED
[INFO] robovm-surefire-provider ........................... SKIPPED
[INFO] RoboVM XCode/IB project generator 2.3.4-SNAPSHOT ... SKIPPED
[INFO] ------------------------------------------------------------------------
[INFO] BUILD FAILURE
[INFO] ------------------------------------------------------------------------
[INFO] Total time: 01:53 min
[INFO] Finished at: 2018-06-13T16:51:22-04:00
[INFO] ------------------------------------------------------------------------
[ERROR] Failed to execute goal org.apache.maven.plugins:maven-surefire-plugin:2.11:test (default-test) on project robovm-compiler: There are test failures.
[ERROR]
[ERROR] Please refer to /Applications/java-oxygen/robovm-workspace/robovm/compiler/compiler/target/surefire-reports for the individual test results.
[ERROR] -> [Help 1]
[ERROR]
[ERROR] To see the full stack trace of the errors, re-run Maven with the -e switch.
[ERROR] Re-run Maven using the -X switch to enable full debug logging.
[ERROR]
[ERROR] For more information about the errors and possible solutions, please read the following articles:
[ERROR] [Help 1] http://cwiki.apache.org/confluence/display/MAVEN/MojoFailureException
[ERROR]
[ERROR] After correcting the problems, you can resume the build with the command
[ERROR] mvn -rf :robovm-compiler

This is the error en reports:


Test set: org.robovm.compiler.AppCompilerTest

Tests run: 5, Failures: 0, Errors: 5, Skipped: 0, Time elapsed: 0.132 sec <<< FAILURE!
testMultipleMetainfServiceImplsAdded(org.robovm.compiler.AppCompilerTest) Time elapsed: 0.12 sec <<< ERROR!
java.lang.NullPointerException
at org.robovm.compiler.AppCompiler.addMetaInfImplementations(AppCompiler.java:317)
at org.robovm.compiler.AppCompilerTest.testMultipleMetainfServiceImplsAdded(AppCompilerTest.java:66)
at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
at java.base/jdk.internal.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
at java.base/java.lang.reflect.Method.invoke(Method.java:564)
at org.junit.runners.model.FrameworkMethod$1.runReflectiveCall(FrameworkMethod.java:50)
at org.junit.internal.runners.model.ReflectiveCallable.run(ReflectiveCallable.java:12)
at org.junit.runners.model.FrameworkMethod.invokeExplosively(FrameworkMethod.java:47)
at org.junit.internal.runners.statements.InvokeMethod.evaluate(InvokeMethod.java:17)
at org.junit.runners.ParentRunner.runLeaf(ParentRunner.java:325)
at org.junit.runners.BlockJUnit4ClassRunner.runChild(BlockJUnit4ClassRunner.java:78)
at org.junit.runners.BlockJUnit4ClassRunner.runChild(BlockJUnit4ClassRunner.java:57)
at org.junit.runners.ParentRunner$3.run(ParentRunner.java:290)
at org.junit.runners.ParentRunner$1.schedule(ParentRunner.java:71)
at org.junit.runners.ParentRunner.runChildren(ParentRunner.java:288)
at org.junit.runners.ParentRunner.access$000(ParentRunner.java:58)
at org.junit.runners.ParentRunner$2.evaluate(ParentRunner.java:268)
at org.junit.runners.ParentRunner.run(ParentRunner.java:363)
at org.apache.maven.surefire.junit4.JUnit4Provider.execute(JUnit4Provider.java:234)
at org.apache.maven.surefire.junit4.JUnit4Provider.executeTestSet(JUnit4Provider.java:133)
at org.apache.maven.surefire.junit4.JUnit4Provider.invoke(JUnit4Provider.java:114)
at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
at java.base/jdk.internal.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
at java.base/java.lang.reflect.Method.invoke(Method.java:564)
at org.apache.maven.surefire.util.ReflectionUtils.invokeMethodWithArray(ReflectionUtils.java:188)
at org.apache.maven.surefire.booter.ProviderFactory$ProviderProxy.invoke(ProviderFactory.java:166)
at org.apache.maven.surefire.booter.ProviderFactory.invokeProvider(ProviderFactory.java:86)
at org.apache.maven.surefire.booter.ForkedBooter.runSuitesInProcess(ForkedBooter.java:101)
at org.apache.maven.surefire.booter.ForkedBooter.main(ForkedBooter.java:74)
testMetainfServiceImplIsAdded(org.robovm.compiler.AppCompilerTest) Time elapsed: 0.002 sec <<< ERROR!
java.lang.NullPointerException
at org.robovm.compiler.AppCompiler.addMetaInfImplementations(AppCompiler.java:317)
at org.robovm.compiler.AppCompilerTest.testMetainfServiceImplIsAdded(AppCompilerTest.java:51)
at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
at java.base/jdk.internal.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
at java.base/java.lang.reflect.Method.invoke(Method.java:564)
at org.junit.runners.model.FrameworkMethod$1.runReflectiveCall(FrameworkMethod.java:50)
at org.junit.internal.runners.model.ReflectiveCallable.run(ReflectiveCallable.java:12)
at org.junit.runners.model.FrameworkMethod.invokeExplosively(FrameworkMethod.java:47)
at org.junit.internal.runners.statements.InvokeMethod.evaluate(InvokeMethod.java:17)
at org.junit.runners.ParentRunner.runLeaf(ParentRunner.java:325)
at org.junit.runners.BlockJUnit4ClassRunner.runChild(BlockJUnit4ClassRunner.java:78)
at org.junit.runners.BlockJUnit4ClassRunner.runChild(BlockJUnit4ClassRunner.java:57)
at org.junit.runners.ParentRunner$3.run(ParentRunner.java:290)
at org.junit.runners.ParentRunner$1.schedule(ParentRunner.java:71)
at org.junit.runners.ParentRunner.runChildren(ParentRunner.java:288)
at org.junit.runners.ParentRunner.access$000(ParentRunner.java:58)
at org.junit.runners.ParentRunner$2.evaluate(ParentRunner.java:268)
at org.junit.runners.ParentRunner.run(ParentRunner.java:363)
at org.apache.maven.surefire.junit4.JUnit4Provider.execute(JUnit4Provider.java:234)
at org.apache.maven.surefire.junit4.JUnit4Provider.executeTestSet(JUnit4Provider.java:133)
at org.apache.maven.surefire.junit4.JUnit4Provider.invoke(JUnit4Provider.java:114)
at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
at java.base/jdk.internal.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
at java.base/java.lang.reflect.Method.invoke(Method.java:564)
at org.apache.maven.surefire.util.ReflectionUtils.invokeMethodWithArray(ReflectionUtils.java:188)
at org.apache.maven.surefire.booter.ProviderFactory$ProviderProxy.invoke(ProviderFactory.java:166)
at org.apache.maven.surefire.booter.ProviderFactory.invokeProvider(ProviderFactory.java:86)
at org.apache.maven.surefire.booter.ForkedBooter.runSuitesInProcess(ForkedBooter.java:101)
at org.apache.maven.surefire.booter.ForkedBooter.main(ForkedBooter.java:74)
testMultilineFile(org.robovm.compiler.AppCompilerTest) Time elapsed: 0.001 sec <<< ERROR!
java.lang.NullPointerException
at org.robovm.compiler.AppCompiler.addMetaInfImplementations(AppCompiler.java:317)
at org.robovm.compiler.AppCompilerTest.testMultilineFile(AppCompilerTest.java:88)
at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
at java.base/jdk.internal.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
at java.base/java.lang.reflect.Method.invoke(Method.java:564)
at org.junit.runners.model.FrameworkMethod$1.runReflectiveCall(FrameworkMethod.java:50)
at org.junit.internal.runners.model.ReflectiveCallable.run(ReflectiveCallable.java:12)
at org.junit.runners.model.FrameworkMethod.invokeExplosively(FrameworkMethod.java:47)
at org.junit.internal.runners.statements.InvokeMethod.evaluate(InvokeMethod.java:17)
at org.junit.runners.ParentRunner.runLeaf(ParentRunner.java:325)
at org.junit.runners.BlockJUnit4ClassRunner.runChild(BlockJUnit4ClassRunner.java:78)
at org.junit.runners.BlockJUnit4ClassRunner.runChild(BlockJUnit4ClassRunner.java:57)
at org.junit.runners.ParentRunner$3.run(ParentRunner.java:290)
at org.junit.runners.ParentRunner$1.schedule(ParentRunner.java:71)
at org.junit.runners.ParentRunner.runChildren(ParentRunner.java:288)
at org.junit.runners.ParentRunner.access$000(ParentRunner.java:58)
at org.junit.runners.ParentRunner$2.evaluate(ParentRunner.java:268)
at org.junit.runners.ParentRunner.run(ParentRunner.java:363)
at org.apache.maven.surefire.junit4.JUnit4Provider.execute(JUnit4Provider.java:234)
at org.apache.maven.surefire.junit4.JUnit4Provider.executeTestSet(JUnit4Provider.java:133)
at org.apache.maven.surefire.junit4.JUnit4Provider.invoke(JUnit4Provider.java:114)
at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
at java.base/jdk.internal.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
at java.base/java.lang.reflect.Method.invoke(Method.java:564)
at org.apache.maven.surefire.util.ReflectionUtils.invokeMethodWithArray(ReflectionUtils.java:188)
at org.apache.maven.surefire.booter.ProviderFactory$ProviderProxy.invoke(ProviderFactory.java:166)
at org.apache.maven.surefire.booter.ProviderFactory.invokeProvider(ProviderFactory.java:86)
at org.apache.maven.surefire.booter.ForkedBooter.runSuitesInProcess(ForkedBooter.java:101)
at org.apache.maven.surefire.booter.ForkedBooter.main(ForkedBooter.java:74)
testMissingImplIsIgnore(org.robovm.compiler.AppCompilerTest) Time elapsed: 0.001 sec <<< ERROR!
java.lang.NullPointerException
at org.robovm.compiler.AppCompiler.addMetaInfImplementations(AppCompiler.java:317)
at org.robovm.compiler.AppCompilerTest.testMissingImplIsIgnore(AppCompilerTest.java:105)
at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
at java.base/jdk.internal.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
at java.base/java.lang.reflect.Method.invoke(Method.java:564)
at org.junit.runners.model.FrameworkMethod$1.runReflectiveCall(FrameworkMethod.java:50)
at org.junit.internal.runners.model.ReflectiveCallable.run(ReflectiveCallable.java:12)
at org.junit.runners.model.FrameworkMethod.invokeExplosively(FrameworkMethod.java:47)
at org.junit.internal.runners.statements.InvokeMethod.evaluate(InvokeMethod.java:17)
at org.junit.runners.ParentRunner.runLeaf(ParentRunner.java:325)
at org.junit.runners.BlockJUnit4ClassRunner.runChild(BlockJUnit4ClassRunner.java:78)
at org.junit.runners.BlockJUnit4ClassRunner.runChild(BlockJUnit4ClassRunner.java:57)
at org.junit.runners.ParentRunner$3.run(ParentRunner.java:290)
at org.junit.runners.ParentRunner$1.schedule(ParentRunner.java:71)
at org.junit.runners.ParentRunner.runChildren(ParentRunner.java:288)
at org.junit.runners.ParentRunner.access$000(ParentRunner.java:58)
at org.junit.runners.ParentRunner$2.evaluate(ParentRunner.java:268)
at org.junit.runners.ParentRunner.run(ParentRunner.java:363)
at org.apache.maven.surefire.junit4.JUnit4Provider.execute(JUnit4Provider.java:234)
at org.apache.maven.surefire.junit4.JUnit4Provider.executeTestSet(JUnit4Provider.java:133)
at org.apache.maven.surefire.junit4.JUnit4Provider.invoke(JUnit4Provider.java:114)
at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
at java.base/jdk.internal.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
at java.base/java.lang.reflect.Method.invoke(Method.java:564)
at org.apache.maven.surefire.util.ReflectionUtils.invokeMethodWithArray(ReflectionUtils.java:188)
at org.apache.maven.surefire.booter.ProviderFactory$ProviderProxy.invoke(ProviderFactory.java:166)
at org.apache.maven.surefire.booter.ProviderFactory.invokeProvider(ProviderFactory.java:86)
at org.apache.maven.surefire.booter.ForkedBooter.runSuitesInProcess(ForkedBooter.java:101)
at org.apache.maven.surefire.booter.ForkedBooter.main(ForkedBooter.java:74)
allStreamsAreClosedInCaseOfFailure(org.robovm.compiler.AppCompilerTest) Time elapsed: 0.001 sec <<< ERROR!
java.lang.NullPointerException
at org.robovm.compiler.AppCompiler.addMetaInfImplementations(AppCompiler.java:317)
at org.robovm.compiler.AppCompilerTest.allStreamsAreClosedInCaseOfFailure(AppCompilerTest.java:123)
at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
at java.base/jdk.internal.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
at java.base/java.lang.reflect.Method.invoke(Method.java:564)
at org.junit.runners.model.FrameworkMethod$1.runReflectiveCall(FrameworkMethod.java:50)
at org.junit.internal.runners.model.ReflectiveCallable.run(ReflectiveCallable.java:12)
at org.junit.runners.model.FrameworkMethod.invokeExplosively(FrameworkMethod.java:47)
at org.junit.internal.runners.statements.InvokeMethod.evaluate(InvokeMethod.java:17)
at org.junit.runners.ParentRunner.runLeaf(ParentRunner.java:325)
at org.junit.runners.BlockJUnit4ClassRunner.runChild(BlockJUnit4ClassRunner.java:78)
at org.junit.runners.BlockJUnit4ClassRunner.runChild(BlockJUnit4ClassRunner.java:57)
at org.junit.runners.ParentRunner$3.run(ParentRunner.java:290)
at org.junit.runners.ParentRunner$1.schedule(ParentRunner.java:71)
at org.junit.runners.ParentRunner.runChildren(ParentRunner.java:288)
at org.junit.runners.ParentRunner.access$000(ParentRunner.java:58)
at org.junit.runners.ParentRunner$2.evaluate(ParentRunner.java:268)
at org.junit.runners.ParentRunner.run(ParentRunner.java:363)
at org.apache.maven.surefire.junit4.JUnit4Provider.execute(JUnit4Provider.java:234)
at org.apache.maven.surefire.junit4.JUnit4Provider.executeTestSet(JUnit4Provider.java:133)
at org.apache.maven.surefire.junit4.JUnit4Provider.invoke(JUnit4Provider.java:114)
at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
at java.base/jdk.internal.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
at java.base/java.lang.reflect.Method.invoke(Method.java:564)
at org.apache.maven.surefire.util.ReflectionUtils.invokeMethodWithArray(ReflectionUtils.java:188)
at org.apache.maven.surefire.booter.ProviderFactory$ProviderProxy.invoke(ProviderFactory.java:166)
at org.apache.maven.surefire.booter.ProviderFactory.invokeProvider(ProviderFactory.java:86)
at org.apache.maven.surefire.booter.ForkedBooter.runSuitesInProcess(ForkedBooter.java:101)
at org.apache.maven.surefire.booter.ForkedBooter.main(ForkedBooter.java:74)

@dkimitsa
Copy link
Contributor

@cperez-infoboy hi,
are you building master ? are you building with build.sh ?
just checked out master and was able to build and tests passed.

Running org.robovm.compiler.AppCompilerTest
Tests run: 5, Failures: 0, Errors: 0, Skipped: 0, Time elapsed: 0.465 sec

@keesvandieren
Copy link
Contributor

Does this mean that doing HTTPS calls using standard java API's / libraries are in fact currently unsafe?

@dkimitsa
Copy link
Contributor

there are some amount of vulnerabilities present but it is it is not always these can be used against client. For example heartbleed can be used in this scenario by server (client connects to). As long as your app is connects to know and secure servers chances are low that it happens.
it should be not big deal migrating to new version as api most cases stays solid. will give it a try next days/weeks.

@dthommes
Copy link
Contributor Author

I have tried to bring a newer OpenSSL into the project. Unfortunately, this is quite a lot of effort because OpenSSL has to be configured correctly. I have cancelled the attempt after several hours and am currently using my suggested work-around.

It would be great to have a fix, as one cannot modify the behavior of 3rd-party libraries easily.

@dkimitsa
Copy link
Contributor

@dthommes
didn't this #308 fix you issue ? why do you use workaround ?

as per updating OpenSSL, there is another problem is that runtime is outdated and there are moments in runtime. Runtime has to be migrated to OpenJDK once and updating openssl might use not required.
So at this moment I can't see that upgrade of openssl is highly required.

@dthommes
Copy link
Contributor Author

@dkimitsa
I agree, it would be preferrable to have an OpenJDK-based RoboVM. Then, the OpenSSL problem would be solved. I am looking forward to such a solution 👍- possibly one could make a move to OpenJDK 11 directly.

Until we have this peace of software, it might be wise to minimize the attack surface. It's correct, that #308 solves the connection problem with TLS 1.2 servers. That was a great move! To harden the client a bit more, the cipher suites could be limited. And the cacerts need a regular update.

These are all things, I can help with. Just let me know, whether I should (re-)open distinct issues for this.

BTW: Today, I have tested RoboVMs HTTPS Implementation with Jeff Hodge's great check service:

https://www.howsmyssl.com/

TL;DR: Please use Okhttp3 if you want to have a probably secure connection :-).

Here are the detailed results (rating at the end of the JSON files):

With RoboVM & HttpsUrlConnection

{
   "given_cipher_suites":[
      "TLS_RSA_WITH_RC4_128_MD5",
      "TLS_RSA_WITH_RC4_128_SHA",
      "TLS_RSA_WITH_AES_128_CBC_SHA",
      "TLS_RSA_WITH_AES_256_CBC_SHA",
      "TLS_ECDH_ECDSA_WITH_RC4_128_SHA",
      "TLS_ECDH_ECDSA_WITH_AES_128_CBC_SHA",
      "TLS_ECDH_ECDSA_WITH_AES_256_CBC_SHA",
      "TLS_ECDH_RSA_WITH_RC4_128_SHA",
      "TLS_ECDH_RSA_WITH_AES_128_CBC_SHA",
      "TLS_ECDH_RSA_WITH_AES_256_CBC_SHA",
      "TLS_ECDHE_ECDSA_WITH_RC4_128_SHA",
      "TLS_ECDHE_ECDSA_WITH_AES_128_CBC_SHA",
      "TLS_ECDHE_ECDSA_WITH_AES_256_CBC_SHA",
      "TLS_ECDHE_RSA_WITH_RC4_128_SHA",
      "TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA",
      "TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA",
      "TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384",
      "TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256",
      "TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA384",
      "TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA256",
      "TLS_DHE_RSA_WITH_AES_128_CBC_SHA",
      "TLS_DHE_RSA_WITH_AES_256_CBC_SHA",
      "TLS_DHE_DSS_WITH_AES_128_CBC_SHA",
      "TLS_DHE_DSS_WITH_AES_256_CBC_SHA",
      "TLS_RSA_WITH_3DES_EDE_CBC_SHA",
      "TLS_ECDH_ECDSA_WITH_3DES_EDE_CBC_SHA",
      "TLS_ECDH_RSA_WITH_3DES_EDE_CBC_SHA",
      "TLS_ECDHE_ECDSA_WITH_3DES_EDE_CBC_SHA",
      "TLS_ECDHE_RSA_WITH_3DES_EDE_CBC_SHA",
      "TLS_DHE_RSA_WITH_3DES_EDE_CBC_SHA",
      "TLS_DHE_DSS_WITH_3DES_EDE_CBC_SHA",
      "TLS_RSA_WITH_DES_CBC_SHA",
      "TLS_DHE_RSA_WITH_DES_CBC_SHA",
      "TLS_DHE_DSS_WITH_DES_CBC_SHA",
      "TLS_RSA_EXPORT_WITH_RC4_40_MD5",
      "TLS_RSA_EXPORT_WITH_DES40_CBC_SHA",
      "TLS_DHE_RSA_EXPORT_WITH_DES40_CBC_SHA",
      "TLS_DHE_DSS_EXPORT_WITH_DES40_CBC_SHA",
      "TLS_EMPTY_RENEGOTIATION_INFO_SCSV"
   ],
   "ephemeral_keys_supported":true,
   "session_ticket_supported":true,
   "tls_compression_supported":false,
   "unknown_cipher_suite_supported":false,
   "beast_vuln":false,
   "able_to_detect_n_minus_one_splitting":false,
   "insecure_cipher_suites":{
      "TLS_DHE_DSS_EXPORT_WITH_DES40_CBC_SHA":[
         "uses keys smaller than 128 bits in its encryption"
      ],
      "TLS_DHE_DSS_WITH_3DES_EDE_CBC_SHA":[
         "uses 3DES which is vulnerable to the Sweet32 attack but was not configured as a fallback in the ciphersuite order"
      ],
      "TLS_DHE_DSS_WITH_DES_CBC_SHA":[
         "uses keys smaller than 128 bits in its encryption"
      ],
      "TLS_DHE_RSA_EXPORT_WITH_DES40_CBC_SHA":[
         "uses keys smaller than 128 bits in its encryption"
      ],
      "TLS_DHE_RSA_WITH_3DES_EDE_CBC_SHA":[
         "uses 3DES which is vulnerable to the Sweet32 attack but was not configured as a fallback in the ciphersuite order"
      ],
      "TLS_DHE_RSA_WITH_DES_CBC_SHA":[
         "uses keys smaller than 128 bits in its encryption"
      ],
      "TLS_ECDHE_ECDSA_WITH_3DES_EDE_CBC_SHA":[
         "uses 3DES which is vulnerable to the Sweet32 attack but was not configured as a fallback in the ciphersuite order"
      ],
      "TLS_ECDHE_ECDSA_WITH_RC4_128_SHA":[
         "uses RC4 which has insecure biases in its output"
      ],
      "TLS_ECDHE_RSA_WITH_3DES_EDE_CBC_SHA":[
         "uses 3DES which is vulnerable to the Sweet32 attack but was not configured as a fallback in the ciphersuite order"
      ],
      "TLS_ECDHE_RSA_WITH_RC4_128_SHA":[
         "uses RC4 which has insecure biases in its output"
      ],
      "TLS_ECDH_ECDSA_WITH_3DES_EDE_CBC_SHA":[
         "uses 3DES which is vulnerable to the Sweet32 attack but was not configured as a fallback in the ciphersuite order"
      ],
      "TLS_ECDH_ECDSA_WITH_RC4_128_SHA":[
         "uses RC4 which has insecure biases in its output"
      ],
      "TLS_ECDH_RSA_WITH_3DES_EDE_CBC_SHA":[
         "uses 3DES which is vulnerable to the Sweet32 attack but was not configured as a fallback in the ciphersuite order"
      ],
      "TLS_ECDH_RSA_WITH_RC4_128_SHA":[
         "uses RC4 which has insecure biases in its output"
      ],
      "TLS_RSA_EXPORT_WITH_DES40_CBC_SHA":[
         "uses keys smaller than 128 bits in its encryption"
      ],
      "TLS_RSA_EXPORT_WITH_RC4_40_MD5":[
         "uses keys smaller than 128 bits in its encryption",
         "uses RC4 which has insecure biases in its output"
      ],
      "TLS_RSA_WITH_3DES_EDE_CBC_SHA":[
         "uses 3DES which is vulnerable to the Sweet32 attack but was not configured as a fallback in the ciphersuite order"
      ],
      "TLS_RSA_WITH_DES_CBC_SHA":[
         "uses keys smaller than 128 bits in its encryption"
      ],
      "TLS_RSA_WITH_RC4_128_MD5":[
         "uses RC4 which has insecure biases in its output"
      ],
      "TLS_RSA_WITH_RC4_128_SHA":[
         "uses RC4 which has insecure biases in its output"
      ]
   },
   "tls_version":"TLS 1.2",
   "rating":"Bad"
}

With RoboVM & Okhttp3

{
   "given_cipher_suites":[
      "TLS_RSA_WITH_AES_128_CBC_SHA",
      "TLS_RSA_WITH_AES_256_CBC_SHA",
      "TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA",
      "TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA",
      "TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384",
      "TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256",
      "TLS_RSA_WITH_3DES_EDE_CBC_SHA",
      "TLS_EMPTY_RENEGOTIATION_INFO_SCSV"
   ],
   "ephemeral_keys_supported":true,
   "session_ticket_supported":true,
   "tls_compression_supported":false,
   "unknown_cipher_suite_supported":false,
   "beast_vuln":false,
   "able_to_detect_n_minus_one_splitting":false,
   "insecure_cipher_suites":{

   },
   "tls_version":"TLS 1.2",
   "rating":"Probably Okay"
}

Android 9.0 with HttpsUrlConnection

{
   "given_cipher_suites":[
      "TLS_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256",
      "TLS_ECDHE_ECDSA_WITH_AES_256_GCM_SHA384",
      "TLS_ECDHE_ECDSA_WITH_CHACHA20_POLY1305_SHA256",
      "TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256",
      "TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384",
      "TLS_ECDHE_RSA_WITH_CHACHA20_POLY1305_SHA256",
      "TLS_ECDHE_ECDSA_WITH_AES_128_CBC_SHA",
      "TLS_ECDHE_ECDSA_WITH_AES_256_CBC_SHA",
      "TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA",
      "TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA",
      "TLS_RSA_WITH_AES_128_GCM_SHA256",
      "TLS_RSA_WITH_AES_256_GCM_SHA384",
      "TLS_RSA_WITH_AES_128_CBC_SHA",
      "TLS_RSA_WITH_AES_256_CBC_SHA"
   ],
   "ephemeral_keys_supported":true,
   "session_ticket_supported":true,
   "tls_compression_supported":false,
   "unknown_cipher_suite_supported":false,
   "beast_vuln":false,
   "able_to_detect_n_minus_one_splitting":false,
   "insecure_cipher_suites":{

   },
   "tls_version":"TLS 1.2",
   "rating":"Probably Okay"
}

Android 9.0 with OkHttp3

{
  "given_cipher_suites": [
    "TLS_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256",
    "TLS_ECDHE_ECDSA_WITH_AES_256_GCM_SHA384",
    "TLS_ECDHE_ECDSA_WITH_CHACHA20_POLY1305_SHA256",
    "TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256",
    "TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384",
    "TLS_ECDHE_RSA_WITH_CHACHA20_POLY1305_SHA256",
    "TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA",
    "TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA",
    "TLS_RSA_WITH_AES_128_GCM_SHA256",
    "TLS_RSA_WITH_AES_256_GCM_SHA384",
    "TLS_RSA_WITH_AES_128_CBC_SHA",
    "TLS_RSA_WITH_AES_256_CBC_SHA"
  ],
  "ephemeral_keys_supported": true,
  "session_ticket_supported": true,
  "tls_compression_supported": false,
  "unknown_cipher_suite_supported": false,
  "beast_vuln": false,
  "able_to_detect_n_minus_one_splitting": false,
  "insecure_cipher_suites": {},
  "tls_version": "TLS 1.2",
  "rating": "Probably Okay"
}

@dkimitsa
Copy link
Contributor

dkimitsa commented Nov 1, 2018

the only issue here is set of weak/insecure cipher suite that can be easily removed. also these ciphers are become a problem only when connecting to outdated/compromised servers and a subject for MIM attacks.
bottom line: it is not so critical as long as you don't develop server apps using robovm but some day it has to be handled, optimal case is OJDK

@dkimitsa
Copy link
Contributor

dkimitsa commented Oct 7, 2020

#527 delivers Android10 runtime. TLS1.3 is enabled there

@clydebarrow
Copy link
Contributor

Is Robovm still using openssl 1.0.1 and if so is the imminent expiration of one of the Lets Encrypt root certificates going to be an issue?

From https://letsencrypt.org/docs/dst-root-ca-x3-expiration-september-2021/ :

. If you provide an API or have to support IoT devices, you’ll need to make sure of two things: (1) all clients of your API must trust ISRG Root X1 (not just DST Root CA X3), and (2) if clients of your API are using OpenSSL, they must use version 1.1.0 or later. In OpenSSL 1.0.x, a quirk in certificate verification means that even clients that trust ISRG Root X1 will fail when presented with the Android-compatible certificate chain we are recommending by default.

@dkimitsa
Copy link
Contributor

@clydebarrow
seems like LetsEncrypt issue will not affect RoboVM as we were lucky enough to update root certs with ones from Android 7.1.1 years ago.
check #584 for details

@Tom-Ski
Copy link
Member

Tom-Ski commented Aug 18, 2023

Merging into #556

@Tom-Ski Tom-Ski closed this as completed Aug 18, 2023
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

6 participants