Bytecode features not available in the Java language
stackoverflow.com
stackoverflow.com
if (dangerousFlag == true) doCheck();
...
foo(dangerousFlag ? bar : baz);> Overflow and implicitly assign byte, short, char and boolean values
bool(2) == true
will fail but bool(2) ? a : b
will act as if bool(2) were true and this inconsistency could lead to unintended execution paths.But the Java compiler assumes values will be in range - i.e. that a boolean will be zero or one, that sort of thing.
And as such it makes some optimizations that are... questionable, if you're interfacing with bytecode that wasn't produced by the Java compiler.
For example, if `flag` is supposedly a boolean, but you gave it the value `2` directly via bytecode, flag==true is false, as it gets compiled down to flag == 1, which is false, but flag?bar:baz will return bar.
This can seriously break static analysis, among other things.
public class Dangerous {
public static void main (String ... args) {
Dangerous.<RuntimeException>throwUnchecked(new IOException("Forgot to catch me!"));
}
static <T extends Exception> void throwUnchecked(Exception e) throws T{
throw (T) e;
}
}Here's an example:
class CovariantReturn extends CovariantReturnBase {
public Integer produce() {
return 5;
}
}
class CovariantReturnBase {
public Number produce() {
return 4.5;
}
}
And the relevant javap output for CovariantReturn: public java.lang.Integer produce();
flags: ACC_PUBLIC
Code:
...
public java.lang.Number produce();
flags: ACC_PUBLIC, ACC_BRIDGE, ACC_SYNTHETIC
Code:
...