I recently stumbled upon Change private static final field using Java reflection and tested polygenelubricants\' EverythingIsTrue
class, works fine, Syste
You can avoid compiler inlining by making the value a result of a method call, even a dummy one.
public class Main {
// value is not known at compile time, so not inlined
public static final boolean FLAG = Boolean.parseBoolean("false");
static void setFinalStatic(Class clazz, String fieldName, Object newValue) throws NoSuchFieldException, IllegalAccessException {
Field field = clazz.getDeclaredField(fieldName);
field.setAccessible(true);
Field modifiers = field.getClass().getDeclaredField("modifiers");
modifiers.setAccessible(true);
modifiers.setInt(field, field.getModifiers() & ~Modifier.FINAL);
field.set(null, newValue);
}
public static void main(String... args) throws Exception {
System.out.printf("Everything is %s%n", FLAG);
setFinalStatic(Main.class, "FLAG", true);
System.out.printf("Everything is %s%n", FLAG);
}
}
prints
Everything is false
Everything is true