The following was received through the valhalla-spec-comments mailbox.
-------- Forwarded Message -------- Subject: JEP 303: Intrinsics for the LDC and INVOKEDYNAMIC Instructions Date: Wed, 26 Apr 2017 23:24:40 +0200 From: Jeremy Barrow <jeremy.a.bar...@gmail.com> To: valhalla-spec-comme...@openjdk.java.net I'll preface this with: I know that making a language construct for this has already been set as an explicit non-goal. If you're 100% set on that, then you can probably skip this email, but if you're interested in the opinions of some random who had a free afternoon, then read on. For the same reason that collection literals are a bad idea within the language; compiler intrinsics are a bad idea within the library. Assuming a class gets added to the standard library, how would other languages react to that? Are they going to have to implement some support for it, or instead explain to their userbase that some portion of the library is redundant, more so if the language already supports language level intrinsics. This would be the perfect time to finally use "const". const MethodType type = ...; (Side-note: this might start dipping into ConstantDynamic (condyn) territory, but bear with me.) The idea would allow the programmer to declare a field or a local variable with the const modifier. When the programmer does this, it should be treated as a compile time constant. As such, it doesn't make sense to be able to be able to declare a const field, as a static final const field. This might affect readability, and should probably be reviewed, but semantically, it makes sense. If the field/variable is used in a non-const context, then it should be treated as if it was written there. (Excluding some types, such as strings, classes, etc) Because it's a compile time constant, it raises some questions: Should the source code contain something that won't be present in the final runtime class? I think it makes sense, as it's not the only thing that java can omit from the runtime class. Annotations can have a non-runtime retention, so I don't think the concept is a shock to java programmers, and arguably, a field/local variable with const is easier to spot than a non-runtime annotation (because you have to inspect the annotation's class). I was originally going to also suggest maybe having support for const methods as well, and variables and parameters can only be const, etc, but I think that's far too much for this simple API, and would play very well into condyn's implementation. Should the compiler be intrinsically aware of the type, or be able to be made aware? (Intrinsic types or some way to communicate to the compiler how to convert a type into a constant) This is dangerously close to condyn, but I felt the need to bring it up just to show how well the two could go together. With this API, I think, initially, intrinsic types are perfect. Higher level types that can be known to the compiler, such as MethodType, Class, String, are more or less perfect for it. Now, the main problem: You can't declare a method with those constants without an intrinsic type, or if you could, it might not be too readable. That being said, I may have overlooked a nice way to declare methods with constants. The first solution that came to mind was representing MethodHandle as a const. Currently, there's no explicit creation mechanism, outside of the Lookup system itself, for obvious reasons. Should there be a const factory method for MethodHandles, that can only accept const parameters? We have method references, could we use them? I spent some time thinking about this, and it almost always boiled down to an intrinsic class. As even if we can define a MethodHandle in a const manner, we still have to deal with the compiler needing to be aware of the point where it needs to emit the invokedynamic instruction. In effect, const is a way to define the constants, not the instructions. I think that was the shortcoming, and having something at the language level for bytecode specific instructions is a potentially toxic idea. Now, all that being said, and the final result is in more or less the exact same position as before, I have suggested using const. Which means we can declare new semantics. What if we could define classes that _have_ to be entirely constant? What if we could attach a @Retention to it, or define a RetentionPolicy for it? This means the JVM could toss the class, much like it does annotations. This could make the way for a whole section of programmable constants later on with condyn. I will admit, this got much bigger than I originally planned, but hopefully, I got across my point, if I failed, I at least hope that I gave someone a good idea to work it. Thanks for reading this wall of text.