JDK-8347831 : Re-examine version check when cross linking
  • Type: Enhancement
  • Component: tools
  • Sub-Component: jlink
  • Priority: P3
  • Status: Open
  • Resolution: Unresolved
  • Submitted: 2025-01-15
  • Updated: 2025-06-23
The Version table provides details related to the release that this issue/RFE will be addressed.

Unresolved : Release in which this issue/RFE will be addressed.
Resolved: Release in which this issue/RFE has been resolved.
Fixed : Release in which this issue/RFE has been fixed. The release containing this fix may be available for download as an Early Access Release or a General Availability Release.

To download the current JDK release, click here.
JDK 26
26Unresolved
Related Reports
Blocks :  
Duplicate :  
Description
jlink checks the version of the java.base module when linking to ensure that it is compatible with the current runtime. jlink plugins are deeply tied to JDK internals so you can't run jlink on JDK X and create a run-time with modules from JDK Y. 

At this time the version check fails if the java.base module isn't the same feature + interim version as the JDK running jlink. This check is sufficient to prevent jlink running on one feature release from creating a run-time image for a different feature release. It doesn't prevent using jlink on say JDK N.0.1 and using to produce a run-time image for JDK N.0.2. This case will work until there is a change to something in java.base or the jlink plugin that breaks this cross linking combination. The other scenario that is more brittle is running jlink on JDK N.0.1 from vendor X and attempting it to use to create a JDK N.0.1 with modules from vendor Y. If the two builds aren't from the exact same bits then there is no guarantee that it will produce a working JDK.

We need to re-examine the version check used for jlink cross linking. One possibility is extending the existing check to include other version properties, the class file API can be used to get these from the target's VersionProps class file. Another possibility is the git hash to ensure the builds came from the same source but this assumes there is a repo at build time.
Comments
I implemented the build part in https://github.com/openjdk/jdk-sandbox/compare/JDK-8347831-branch?expand=1.
27-05-2025

After some discussion with Alan and Henry, the suggestion is that the build system creates a partial `release` file, containing $COMPANY_NAME-$VERSION_STRING-$VERSION_DATE at the gensrc stage. This will be created twice, once for java.base and once for jdk.jlink, and will be included as a resource. Then jlink can read these two files and verifies that they match up.
27-05-2025

I agree with Severin's doubts. The *.conf files does not really say how a JDK is built, just what the default values are if they are not overridden. It might be possible to have the build output some kind of suitable fingerprint though.
06-05-2025

Cross linking between builds from different vendors is problematic, it may work, it may not, no guarantee that they contain the same bits.
26-02-2025

AFAIK, values from version-numbers.conf and branding.conf can be overridden by configure options. For example `--with-vendor-bug-url=FOO` for VENDOR_URL_BUG from branding.conf. Not sure if this would be portable enough.
26-02-2025

I discussed this topic with Erik Duveblad. He suggested another approach: generate a checksum of version-numbers.conf and branding.conf at build time that can be checked at link time. It would be simple to generate this and store as a resource in java.base. jlink can then check that the checksum stored in the "current runtime" matches the checksum in the java.base packaged module. It would likely still need to read VersionProp properties when there is a mismatch in order to get a useful error message but not when the check succeeds.
21-02-2025