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

[Native Image] Loading Mac keystore aka KeychainStore results into a runtime exception #10387

Open
2 tasks done
Hakky54 opened this issue Dec 29, 2024 · 10 comments
Open
2 tasks done
Assignees

Comments

@Hakky54
Copy link

Hakky54 commented Dec 29, 2024

Describe the Issue

I have built Certificate Ripper which is a CLI app to extract server certificates.

I recently added the option to also extract the Operating System trusted certificates. This works as a jar file, however if I compile it to a native image and run it then it will fail with a runtime exception.

Using the latest version of GraalVM can resolve many issues.

I could not use version 23.x as it is not supported yet with a library which I use, which is pico cli. So I can use atmost version 22.x

GraalVM Version

openjdk version "22.0.2" 2024-07-16
OpenJDK Runtime Environment GraalVM CE 22.0.2+9.1 (build 22.0.2+9-jvmci-b01)
OpenJDK 64-Bit Server VM GraalVM CE 22.0.2+9.1 (build 22.0.2+9-jvmci-b01, mixed mode, sharing)

Operating System and Version

Mac OS X 14.5

Troubleshooting Confirmation

Run Command

./crip export pem --extract-system-ca --combined=true

Expected Behavior

It should create a system.crt file in the current directory

Actual Behavior

Exception in thread "main" java.lang.UnsatisfiedLinkError: apple.security.KeychainStore._scanKeychain()V [symbol: Java_apple_security_KeychainStore__1scanKeychain or Java_apple_security_KeychainStore__1scanKeychain__]
        at org.graalvm.nativeimage.builder/com.oracle.svm.core.jni.access.JNINativeLinkage.getOrFindEntryPoint(JNINativeLinkage.java:152)
        at org.graalvm.nativeimage.builder/com.oracle.svm.core.jni.JNIGeneratedMethodSupport.nativeCallAddress(JNIGeneratedMethodSupport.java:54)
        at [email protected]/apple.security.KeychainStore._scanKeychain(Native Method)
        at [email protected]/apple.security.KeychainStore.engineLoad(KeychainStore.java:764)
        at [email protected]/java.security.KeyStore.load(KeyStore.java:1499)
        at nl.altindag.ssl.util.KeyStoreUtils.createKeyStore(KeyStoreUtils.java:165)
        at nl.altindag.ssl.util.KeyStoreUtils.createKeyStoreIfAvailable(KeyStoreUtils.java:280)
        at nl.altindag.ssl.util.KeyStoreUtils.loadSystemKeyStores(KeyStoreUtils.java:230)
        at nl.altindag.ssl.util.TrustManagerUtils.createTrustManagerWithSystemTrustedCertificates(TrustManagerUtils.java:93)
        at nl.altindag.ssl.util.CertificateUtils.getSystemTrustedCertificates(CertificateUtils.java:266)
        at nl.altindag.crip.command.SharedProperties.getCertificateHolder(SharedProperties.java:77)
        at nl.altindag.crip.command.export.PemExportCommand.run(PemExportCommand.java:57)
        at picocli.CommandLine.executeUserObject(CommandLine.java:2030)
        at picocli.CommandLine.access$1500(CommandLine.java:148)
        at picocli.CommandLine$RunLast.executeUserObjectOfLastSubcommandWithSameParent(CommandLine.java:2465)
        at picocli.CommandLine$RunLast.handle(CommandLine.java:2457)
        at picocli.CommandLine$RunLast.handle(CommandLine.java:2419)
        at picocli.CommandLine$AbstractParseResultHandler.execute(CommandLine.java:2277)
        at picocli.CommandLine$RunLast.execute(CommandLine.java:2421)
        at picocli.CommandLine.execute(CommandLine.java:2174)
        at nl.altindag.crip.App.main(App.java:32)
        at [email protected]/java.lang.invoke.LambdaForm$DMH/sa346b79c.invokeStaticInit(LambdaForm$DMH)

Steps to Reproduce

  1. git clone https://github.com/Hakky54/certificate-ripper.git
  2. git switch feature/support-system-trusted-certificates
  3. mvn clean install -Pnative-image
  4. ./target/crip export pem --extract-system-ca --combined=true

Additional Context

No response

Run-Time Log Output and Error Messages

No response

@selhagani
Copy link
Member

Hi @Hakky54,

Thank you for reaching out to us!
The issue you're facing could be due to some missing configuration. Could you please try generating the configuration files using the tracing agent and run your application again? You can find more information about this here

@Hakky54
Copy link
Author

Hakky54 commented Dec 30, 2024

Hi @selhagani

Sure, I have created the json file with the tracing agent. I have added as an attachment below:

reachability-metadata.json

@selhagani
Copy link
Member

Hi @Hakky54,

I just used the tracing agent and the generated native image works just fine.
You can do so by running the following commands after going to the target's folder:
java -agentlib:native-image-agent=config-output-dir=META-INF/native-image -jar crip.jar
native-image --no-fallback -H:ConfigurationFileDirectories=META-INF/native-image -jar crip.jar
./crip

@Hakky54
Copy link
Author

Hakky54 commented Jan 2, 2025

can you rerun your last step on a Mac OS X with the following command:

./crip export pem --combined=true --extract-system-ca

@selhagani
Copy link
Member

I just did and it does not print the error message you shared above

@Hakky54
Copy link
Author

Hakky54 commented Jan 2, 2025

So it created a system.crt file on your current directory?
What kind of mac do you happen to use, maybe I can try with a different one on my side.

I used the command you shared, I am still getting that exception

@Hakky54
Copy link
Author

Hakky54 commented Jan 2, 2025

I now also tried with a Apple M1 laptop with GraalVM 22, 21, 17 and I am getting the same error as shown below:

Exception in thread "main" java.lang.UnsatisfiedLinkError: apple.security.KeychainStore._scanKeychain()V [symbol: Java_apple_security_KeychainStore__1scanKeychain or Java_apple_security_KeychainStore__1scanKeychain__]
	at org.graalvm.nativeimage.builder/com.oracle.svm.core.jni.access.JNINativeLinkage.getOrFindEntryPoint(JNINativeLinkage.java:152)
	at org.graalvm.nativeimage.builder/com.oracle.svm.core.jni.JNIGeneratedMethodSupport.nativeCallAddress(JNIGeneratedMethodSupport.java:41)
	at [email protected]/apple.security.KeychainStore._scanKeychain(Native Method)
	at [email protected]/apple.security.KeychainStore.engineLoad(KeychainStore.java:763)
	at [email protected]/java.security.KeyStore.load(KeyStore.java:1500)
	at nl.altindag.ssl.util.KeyStoreUtils.createKeyStore(KeyStoreUtils.java:165)
	at nl.altindag.ssl.util.KeyStoreUtils.createKeyStoreIfAvailable(KeyStoreUtils.java:280)
	at nl.altindag.ssl.util.KeyStoreUtils.loadSystemKeyStores(KeyStoreUtils.java:230)
	at nl.altindag.ssl.util.TrustManagerUtils.createTrustManagerWithSystemTrustedCertificates(TrustManagerUtils.java:93)
	at nl.altindag.ssl.util.CertificateUtils.getSystemTrustedCertificates(CertificateUtils.java:266)
	at nl.altindag.crip.command.SharedProperties.getCertificateHolder(SharedProperties.java:77)
	at nl.altindag.crip.command.export.PemExportCommand.run(PemExportCommand.java:57)
	at picocli.CommandLine.executeUserObject(CommandLine.java:2030)
	at picocli.CommandLine.access$1500(CommandLine.java:148)
	at picocli.CommandLine$RunLast.executeUserObjectOfLastSubcommandWithSameParent(CommandLine.java:2465)
	at picocli.CommandLine$RunLast.handle(CommandLine.java:2457)
	at picocli.CommandLine$RunLast.handle(CommandLine.java:2419)
	at picocli.CommandLine$AbstractParseResultHandler.execute(CommandLine.java:2277)
	at picocli.CommandLine$RunLast.execute(CommandLine.java:2421)
	at picocli.CommandLine.execute(CommandLine.java:2174)
	at nl.altindag.crip.App.main(App.java:28)
	at [email protected]/java.lang.invoke.LambdaForm$DMH/sa346b79c.invokeStaticInit(LambdaForm$DMH)

I think the JNI for Apple is missing while creating the native image. The tool is trying to load KeychainStore and fails. Under the cover certificate ripper is calling my other library. That piece of code is here: https://github.com/Hakky54/sslcontext-kickstart/blob/master/sslcontext-kickstart/src/main/java/nl/altindag/ssl/util/KeyStoreUtils.java#L229-L237

I compile the same project on Windows and at runtime it is working. As for Windows it is also trying to load different native keystores as shown here: https://github.com/Hakky54/sslcontext-kickstart/blob/master/sslcontext-kickstart/src/main/java/nl/altindag/ssl/util/KeyStoreUtils.java#L251-L257

So my assumptions is that for the case of mac os x it is not resolving the native libraries for Apple. I am still not sure how it works on your machine, but I am open to have a video call with screen sharing to demonstrate the issue

@selhagani
Copy link
Member

When I run on my machine I get this error message here:

Missing required option: '--url=<urls>'
Usage: crip export pem [-chV] [--include-header] [--proxy-password]
                       [--resolve-ca] [-d] [--proxy-host] [--proxy-port]
                       [--proxy-user] [-t] -u [-u]...
Export the extracted certificate to a base64 encoded string also known as PEM
  -c, --combined         Indicator to either combine all of the certificate
                           into one file for a given url or export into
                           individual files.
  -d, --destination      Destination of the to be stored file. Default is
                           current directory if none is provided.
  -h, --help             Show this help message and exit.
      --include-header   Indicator to either omit or include additional
                           information above the BEGIN statement.
      --proxy-host       Proxy host
      --proxy-password   Password for authenticating the user for the given
                           proxy
      --proxy-port       Proxy port
      --proxy-user       User for authenticating the user for the given proxy
      --resolve-ca       Indicator to automatically resolve the root ca
                         Possible options: true, false
  -t, --timeout          Amount of milliseconds till the ripping should timeout
  -u, --url              Url of the target server to extract the certificates
  -V, --version          Print version information and exit. ```

and btw  have an Apple m1 Max chip on my machine.

@Hakky54
Copy link
Author

Hakky54 commented Jan 3, 2025

I think you are on the master branch. Can you switch to the feature branch with the following command:

git switch feature/support-system-trusted-certificates

And then run for example the following command:

./crip export p12 --extract-system-ca

@selhagani
Copy link
Member

I see, you're right. Now I get that error message as well. I will take a closer look into this and I'll make sure to keep you updated.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

No branches or pull requests

2 participants