У моего работодателя есть бизнес-необходимость сделать воспроизводимые побайтные сборки Java.Я знаю о трудностях создания воспроизводимых файлов JAR (из-за порядка и меток архивирования), но сейчас я говорю о файлах классов.
У меня есть сборки того же кода с использованием Java 8u65,как на Mac, так и на Linux.Файлы классов отличаются друг от друга.Оба класса декомпилируются обратно в один и тот же источник;чтобы увидеть разницу, требуется дизассемблер javap.
Исходный код выглядит следующим образом:
final TrustStrategy acceptingTrustStrategy =
(X509Certificate[] chain, String authType) -> true;
В одной сборке результат:
private static boolean lambda$restTemplate$38(java.security.cert.X509Certificate[], java.lang.String) throws java.security.cert.CertificateException;
Code:
0: iconst_1
1: ireturn
Надругое:
private static boolean lambda$restTemplate$15(java.security.cert.X509Certificate[], java.lang.String) throws java.security.cert.CertificateException;
Code:
0: iconst_1
1: ireturn
Анонимные лямбды получают имена с разными номерами (lambda$restTemplate$15
против lambda$restTemplate$38
).
Похоже, что когда я перестраиваю на том жехост, я получаю те же байты.Когда хост отличается, номера меняются;два хоста Linux выдавали разные байты.
Что определяет эти числа?Есть ли способ заставить каждую компиляцию использовать одни и те же числа в этом месте и, таким образом, создавать одинаковые файлы классов?Или компиляция файла класса Java 8 является неопределенной?