Created attachment 1949196 [details] minimal jar with sha256 signature and sha1 extra hashes Description of problem: If a signed jar contains SHA1 content hashes in addition to SHA-256 the content will be reported as unsigned (eg jarsigner -verify doesn't report an algorithm problem like it would with an SHA1 signed jar, instead list entries as unsigned). The problem seems to be in the platform verification code, but jarsigner is a convenient test case. OpenJDK 11 and OpenJDK 17 will validate the jar without issue. Additionally the problematic check seems to only be applied to the first entry in the jar file - if the first entry has SHA-256 only, then subsequent ones will verify ok even they they use deprecated algorithms. Version-Release number of selected component (if applicable): java-1.8.0-openjdk-devel-1.8.0.362.b09-2.fc37.x86_64 but seems to be an upstream OpenJDK 8u362 issue (eg Eclipse Temurin affected too) How reproducible: Issue seems to be consistently reproducible when conditions are met as described. Steps to Reproduce: 1. Given jar with the extra hashes (attached), or eg sign with sha1 (in a version that will let you) then re-sign with sha256 (need to have appropriate keystore config): jarsigner -digestalg SHA1 example-sha-both.jar dpipwe-code-sign jarsigner -digestalg SHA-256 example-sha-both.jar dpipwe-code-sign (Usually this will be due to a pre-existing jar sha1 signed sometime in the past getting resigned with SHA-256 subsequently) 2. try to verify it: jarsigner -verify -verbose example-sha-both.jar Actual results: jarsigner -verify reports unsigned entries Expected results: Jar passes as valid, eg what we see from Java 17 (earlier Java 8 same). Additional info: Additional debug logging can be seen by setting system properties eg: jarsigner -J-Djava.security.debug=jar -verify -verbose example-sha-both.jar or even more verbose showing algorithm check calls: jarsigner -J-Djava.security.debug=jar,certpath -verify -verbose example-sha-both.jar
Created attachment 1949199 [details] example jar with first entry having only SHA-256 hash, but subsequent ones having both SHA1 and SHA-256 Attached example jar where first sha-256 only entry allows jar to pass even when containing later SHA1 entries. debug logging reveals it validates both hashes for the later entries jarsigner -J-Djava.security.debug=jar -verify -verbose example-sha-both-shadowed.jar (snip) jar: beginEntry META-INF/1.txt jar: Manifest Entry: META-INF/1.txt digest=SHA-256 jar: manifest 4355a46b19d348dc2f57c046f8ef63d4538ebb936000f3c9ee954a27460dd865 jar: computed 4355a46b19d348dc2f57c046f8ef63d4538ebb936000f3c9ee954a27460dd865 jar: jar: beginEntry a.txt jar: Manifest Entry: a.txt digest=SHA-256 jar: manifest 87428fc522803d31065e7bce3cf03fe475096631e5e07bbd7a0fde60c4cf25c7 jar: computed 87428fc522803d31065e7bce3cf03fe475096631e5e07bbd7a0fde60c4cf25c7 jar: jar: Manifest Entry: a.txt digest=SHA1 jar: manifest 3f786850e387550fdab836ed7e6dc881de23001b jar: computed 3f786850e387550fdab836ed7e6dc881de23001b jar: jar: beginEntry b.txt jar: Manifest Entry: b.txt digest=SHA-256 jar: manifest 0263829989b6fd954f72baaf2fc64bc2e2f01d692d4de72986ea808f6e99813f jar: computed 0263829989b6fd954f72baaf2fc64bc2e2f01d692d4de72986ea808f6e99813f jar: jar: Manifest Entry: b.txt digest=SHA1 jar: manifest 89e6c98d92887913cadf06b2adb97f26cde4849b jar: computed 89e6c98d92887913cadf06b2adb97f26cde4849b jar: s 395 Wed Mar 08 17:11:06 AEDT 2023 META-INF/MANIFEST.MF 471 Wed Mar 08 17:11:06 AEDT 2023 META-INF/DPIPWE-C.SF 5762 Wed Mar 08 17:11:06 AEDT 2023 META-INF/DPIPWE-C.RSA 0 Wed Mar 08 16:53:16 AEDT 2023 META-INF/ sm 2 Wed Mar 08 17:08:32 AEDT 2023 META-INF/1.txt sm 2 Wed Mar 08 16:51:46 AEDT 2023 a.txt sm 2 Wed Mar 08 16:51:54 AEDT 2023 b.txt s = signature was verified m = entry is listed in manifest k = at least one certificate was found in keystore i = at least one certificate was found in identity scope - Signed by "CN=DPIPWE, O=DPIPWE, L=Hobart, ST=Tasmania, C=AU" Digest algorithm: SHA-256 Signature algorithm: SHA256withRSA, 4096-bit key jar verified.
For completeness debug logging from Java 8u362 on dual hash jar: Seems to validate HSA-256 hashes, then fail on encountering SHA1 /usr/lib/jvm/java-1.8.0-openjdk-1.8.0.362.b09-2.fc37.x86_64/bin/jarsigner -J-Djava.security.debug=jar -verify -verbose example-sha-both.jar (snip) jar: beginEntry a.txt jar: Manifest Entry: a.txt digest=SHA-256 jar: manifest 87428fc522803d31065e7bce3cf03fe475096631e5e07bbd7a0fde60c4cf25c7 jar: computed 87428fc522803d31065e7bce3cf03fe475096631e5e07bbd7a0fde60c4cf25c7 jar: jar: Digest algorithm is restricted: java.security.cert.CertPathValidatorException: denyAfter constraint check failed: SHA1 used with Constraint date: 2019-01-01; params date: 2023-03-09T02:41:52.208Z used with a.txt entry in META-INF/MANIFEST.MF file. jar: beginEntry b.txt jar: Manifest Entry: b.txt digest=SHA-256 jar: manifest 0263829989b6fd954f72baaf2fc64bc2e2f01d692d4de72986ea808f6e99813f jar: computed 0263829989b6fd954f72baaf2fc64bc2e2f01d692d4de72986ea808f6e99813f jar: jar: Digest algorithm is restricted: java.security.cert.CertPathValidatorException: denyAfter constraint check failed: SHA1 used with Constraint date: 2019-01-01; params date: 2023-03-09T02:41:52.213Z used with b.txt entry in META-INF/MANIFEST.MF file. s 309 Wed Mar 08 17:01:16 AEDT 2023 META-INF/MANIFEST.MF 385 Wed Mar 08 17:01:16 AEDT 2023 META-INF/DPIPWE-C.SF 5762 Wed Mar 08 17:01:16 AEDT 2023 META-INF/DPIPWE-C.RSA 0 Wed Mar 08 16:53:16 AEDT 2023 META-INF/ m ? 2 Wed Mar 08 16:51:46 AEDT 2023 a.txt m ? 2 Wed Mar 08 16:51:54 AEDT 2023 b.txt s = signature was verified m = entry is listed in manifest k = at least one certificate was found in keystore i = at least one certificate was found in identity scope ? = unsigned entry - Signed by "CN=DPIPWE, O=DPIPWE, L=Hobart, ST=Tasmania, C=AU" Digest algorithm: SHA-256 Signature algorithm: SHA256withRSA, 4096-bit key jar verified. Warning: This jar contains unsigned entries which have not been integrity-checked.
Thanks for the report. I'll look into it.
This appears to be a missing backport of https://bugs.openjdk.org/browse/JDK-8278851
Confirmed. It's caused by the missing backport of JDK-8278851. I'm going to propose it upstream and if all goes well it should be available in 8u382 (July). ./images/j2sdk-image/bin/jarsigner -J-showversion -verify -certs -verbose example-sha-both.jar openjdk version "1.8.0_372-internal-fastdebug" OpenJDK Runtime Environment (build 1.8.0_372-internal-fastdebug-b03) OpenJDK 64-Bit Server VM (build 25.372-b03-fastdebug, mixed mode) s 309 Wed Mar 08 17:01:16 CET 2023 META-INF/MANIFEST.MF >>> Signer X.509, CN=DPIPWE, O=DPIPWE, L=Hobart, ST=Tasmania, C=AU [certificate is valid from 1/18/23 1:00 AM to 1/29/24 12:59 AM] X.509, CN=DigiCert Trusted G4 Code Signing RSA4096 SHA384 2021 CA1, O="DigiCert, Inc.", C=US [certificate is valid from 4/29/21 2:00 AM to 4/29/36 1:59 AM] X.509, CN=DigiCert Trusted Root G4, OU=www.digicert.com, O=DigiCert Inc, C=US [trusted certificate] 385 Wed Mar 08 17:01:16 CET 2023 META-INF/DPIPWE-C.SF 5762 Wed Mar 08 17:01:16 CET 2023 META-INF/DPIPWE-C.RSA 0 Wed Mar 08 16:53:16 CET 2023 META-INF/ sm 2 Wed Mar 08 16:51:46 CET 2023 a.txt >>> Signer X.509, CN=DPIPWE, O=DPIPWE, L=Hobart, ST=Tasmania, C=AU [certificate is valid from 1/18/23 1:00 AM to 1/29/24 12:59 AM] X.509, CN=DigiCert Trusted G4 Code Signing RSA4096 SHA384 2021 CA1, O="DigiCert, Inc.", C=US [certificate is valid from 4/29/21 2:00 AM to 4/29/36 1:59 AM] X.509, CN=DigiCert Trusted Root G4, OU=www.digicert.com, O=DigiCert Inc, C=US [trusted certificate] sm 2 Wed Mar 08 16:51:54 CET 2023 b.txt >>> Signer X.509, CN=DPIPWE, O=DPIPWE, L=Hobart, ST=Tasmania, C=AU [certificate is valid from 1/18/23 1:00 AM to 1/29/24 12:59 AM] X.509, CN=DigiCert Trusted G4 Code Signing RSA4096 SHA384 2021 CA1, O="DigiCert, Inc.", C=US [certificate is valid from 4/29/21 2:00 AM to 4/29/36 1:59 AM] X.509, CN=DigiCert Trusted Root G4, OU=www.digicert.com, O=DigiCert Inc, C=US [trusted certificate] s = signature was verified m = entry is listed in manifest k = at least one certificate was found in keystore i = at least one certificate was found in identity scope - Signed by "CN=DPIPWE, O=DPIPWE, L=Hobart, ST=Tasmania, C=AU" Digest algorithm: SHA-256 Signature algorithm: SHA256withRSA, 4096-bit key jar verified. Warning: This jar contains signatures that do not include a timestamp. Without a timestamp, users may not be able to validate this jar after any of the signer certificates expire (as early as 2024-01-29). The signer certificate will expire on 2024-01-29.
The issue doesn't happen with an 8u352 build. So this is likely caused by https://bugs.openjdk.org/browse/JDK-8269039 ./jdk8u352-b08/bin/jarsigner -J-showversion -verify -certs -verbose example-sha-both.jar openjdk version "1.8.0_352" OpenJDK Runtime Environment (Temurin)(build 1.8.0_352-b08) OpenJDK 64-Bit Server VM (Temurin)(build 25.352-b08, mixed mode) s 309 Wed Mar 08 17:01:16 CET 2023 META-INF/MANIFEST.MF >>> Signer X.509, CN=DPIPWE, O=DPIPWE, L=Hobart, ST=Tasmania, C=AU [certificate is valid from 1/18/23 1:00 AM to 1/29/24 12:59 AM] X.509, CN=DigiCert Trusted G4 Code Signing RSA4096 SHA384 2021 CA1, O="DigiCert, Inc.", C=US [certificate is valid from 4/29/21 2:00 AM to 4/29/36 1:59 AM] X.509, CN=DigiCert Trusted Root G4, OU=www.digicert.com, O=DigiCert Inc, C=US [trusted certificate] 385 Wed Mar 08 17:01:16 CET 2023 META-INF/DPIPWE-C.SF 5762 Wed Mar 08 17:01:16 CET 2023 META-INF/DPIPWE-C.RSA 0 Wed Mar 08 16:53:16 CET 2023 META-INF/ sm 2 Wed Mar 08 16:51:46 CET 2023 a.txt >>> Signer X.509, CN=DPIPWE, O=DPIPWE, L=Hobart, ST=Tasmania, C=AU [certificate is valid from 1/18/23 1:00 AM to 1/29/24 12:59 AM] X.509, CN=DigiCert Trusted G4 Code Signing RSA4096 SHA384 2021 CA1, O="DigiCert, Inc.", C=US [certificate is valid from 4/29/21 2:00 AM to 4/29/36 1:59 AM] X.509, CN=DigiCert Trusted Root G4, OU=www.digicert.com, O=DigiCert Inc, C=US [trusted certificate] sm 2 Wed Mar 08 16:51:54 CET 2023 b.txt >>> Signer X.509, CN=DPIPWE, O=DPIPWE, L=Hobart, ST=Tasmania, C=AU [certificate is valid from 1/18/23 1:00 AM to 1/29/24 12:59 AM] X.509, CN=DigiCert Trusted G4 Code Signing RSA4096 SHA384 2021 CA1, O="DigiCert, Inc.", C=US [certificate is valid from 4/29/21 2:00 AM to 4/29/36 1:59 AM] X.509, CN=DigiCert Trusted Root G4, OU=www.digicert.com, O=DigiCert Inc, C=US [trusted certificate] s = signature was verified m = entry is listed in manifest k = at least one certificate was found in keystore i = at least one certificate was found in identity scope - Signed by "CN=DPIPWE, O=DPIPWE, L=Hobart, ST=Tasmania, C=AU" Digest algorithm: SHA-256 Signature algorithm: SHA256withRSA, 4096-bit key jar verified. Warning: This jar contains signatures that do not include a timestamp. Without a timestamp, users may not be able to validate this jar after any of the signer certificates expire (as early as 2024-01-29). The signer certificate will expire on 2024-01-29.
Upstream pr: https://github.com/openjdk/jdk8u-dev/pull/282
Thanks, that was fast.
This message is a reminder that Fedora Linux 37 is nearing its end of life. Fedora will stop maintaining and issuing updates for Fedora Linux 37 on 2023-12-05. It is Fedora's policy to close all bug reports from releases that are no longer maintained. At that time this bug will be closed as EOL if it remains open with a 'version' of '37'. Package Maintainer: If you wish for this bug to remain open because you plan to fix it in a currently maintained version, change the 'version' to a later Fedora Linux version. Note that the version field may be hidden. Click the "Show advanced fields" button if you do not see it. Thank you for reporting this issue and we are sorry that we were not able to fix it before Fedora Linux 37 is end of life. If you would still like to see this bug fixed and are able to reproduce it against a later version of Fedora Linux, you are encouraged to change the 'version' to a later version prior to this bug being closed.
Fixed in recent releases of OpenJDK 8u (8u382+ specifically).