RFR: addressing several issues in the implementation of universal tvars [v5]
Maurizio Cimadamore
mcimadamore at openjdk.java.net
Mon May 23 09:12:24 UTC 2022
On Mon, 23 May 2022 08:52:00 GMT, Maurizio Cimadamore <mcimadamore at openjdk.org> wrote:
>> Vicente Romero has updated the pull request incrementally with one additional commit since the last revision:
>>
>> missed a case in unchecked conversions
>
> src/jdk.compiler/share/classes/com/sun/tools/javac/code/Types.java line 1824:
>
>> 1822: return true;
>> 1823: }
>> 1824: return (allowUniversalTVars &&
>
> This extra check feels outside the spirit of the rules discussed in https://openjdk.java.net/jeps/8261529.
> That is, I'd expect type containment to recurse using `isBoundedBy` instead of `isSubtype` (as the first branch of this code does).
I've been doing some scribbling - is the above change required because of code like this:
static class Box<__universal X> { }
static primitive class Atom { }
void test() {
Box<? extends Atom> val = null;
Box<Atom.ref> ref = null;
val = ref; // <------
}
```
With an older compiler I get an error here. Indeed, this `val = ref` conversion cannot be explained in terms of the "isBoundedBy" rule, at least not as defined in the JEP draft:
Box<Atom.ref> <: Box<? extends Atom>
--> Atom.ref <= ? extends Atom
--> Atom.ref is-bounded-by Atom
But here we hit a roadblock: is-bounded-by doesn't apply in this case:
We now say that a type S is bounded by a type T if any of the following is true:
[...]
S is a primitive class type whose corresponding reference type is bounded by T; or
But `S` is not a primitive class type here - only a reference projection of a primitive class type. So this rule doesn't apply and the type containment fails (and hence subtyping fails).
It seems like the code now rectifies this by trying `isBoundedBy` first and, if that fails, it uses a type conversion instead. But this feels like a big departure, with subtyping now depending on type conversion. If we want to support the above example, then the `isBoundedBy` routine needs to be updated to deal with this - otherwise other places using `isBoundedBy` will fail in a similar way, e.g. well-formedness of generic types:
class Foo<X extends Atom> { ... }
Foo<Atom.ref> // is this a legal type?
-------------
PR: https://git.openjdk.java.net/valhalla/pull/684
More information about the valhalla-dev
mailing list