Welcome to OGeek Q&A Community for programmer and developer-Open, Learning and Share
Welcome To Ask or Share your Answers For Others

Categories

0 votes
1.3k views
in Technique[技术] by (71.8m points)

java - How to use javac to create binary identical class files across different platforms?

I write my AWS Lambda functions in Java. The tool I use to upload my lambdas (Terraform) wants to use the SHA-256 hash of my jar file to track if a new version of a lambda needs to by uploaded.

The problem is, different JDKs on different OS platforms (Windows and Linux) create slightly different bytecode (even when using the same "update" version of the JDK). This means, if I upload a lambda on Windows, then re-run the process on Linux - it will detect a different hash code for the jar and re-upload the lambda jar unnecessarily.

The question: How do I force javac to create identical bytecode on different OS platforms?

See Question&Answers more detail:os

与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
Welcome To Ask or Share your Answers For Others

1 Reply

0 votes
by (71.8m points)

You can’t enforce that. There are several unspecified details about the generated class files, like how the byte code of certain source code expressions has to look exactly or the order of members or attributes.

Since there is no requirement to produce exactly the same file in each run, the compiler implementation does not even try. It’s fair to assume that when you execute the same software with exactly the same input (not only the same source code, but also the same options), it will produce the same output, but that does not only require the same compiler version, but also the same JRE.

Unfortunately, there might be different behavior even with the same implementation and input. E.g., there were attempts to randomize the hashing of java.util.HashMap in some Java?7 implementations and it wouldn’t be surprising if javac stores certain artifacts in a HashMap. This does not apply to Java?8, but might apply to the immutable maps to be introduced in Java?9. Whether the compiler will use that feature is not predictable.

So if you found a particular jdk version that reproducibly generates exactly the same byte code, you might be fine with it now, but have to be aware that the next version might not have that property.

It has not been addressed so far that even having the same bytecode does not guaranty to have the same jar file, as the order of the files within the jar files is unspecified. It might depend on the system specific file iteration order. Further, since jar files are zip files which store timestamps, newly compiled class file do definitely yield a different file, unless you are taking additional measures, e.g. enforce a particular timestamp for all entries.


与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
OGeek|极客中国-欢迎来到极客的世界,一个免费开放的程序员编程交流平台!开放,进步,分享!让技术改变生活,让极客改变未来! Welcome to OGeek Q&A Community for programmer and developer-Open, Learning and Share
Click Here to Ask a Question

...