JDK-8133118 : Incompatible static wildcard bounds
  • Type: Bug
  • Component: tools
  • Sub-Component: javac
  • Affected Version: 8u51,8u60
  • Priority: P3
  • Status: Closed
  • Resolution: Won't Fix
  • OS: linux_ubuntu
  • CPU: x86_64
  • Submitted: 2015-07-31
  • Updated: 2015-08-20
  • Resolved: 2015-08-20
Related Reports
Relates :  
Relates :  
Relates :  
Description
FULL PRODUCT VERSION :
java version "1.8.0_51"
Java(TM) SE Runtime Environment (build 1.8.0_51-b16)
Java HotSpot(TM) 64-Bit Server VM (build 25.51-b03, mixed mode)

A DESCRIPTION OF THE PROBLEM :
Attached example compiles with source 1.7, but not with source 1.8.
I don't know if it is legal according to JLS 1.7 or JLS 1.8. It seems however, that it should be.

Code compiles when wildcard
Interval<?> interval = (Interval<?>) object;
is replaced by raw
Interval interval = (Interval) object;

I'm aware that isValid could and should be instance method, Validator could be generic class and so on - but let's ignore that.

REGRESSION.  Last worked in version 8u51


ERROR MESSAGES/STACK TRACES THAT OCCUR :
IntervalValidator.java:8: error: method isValid in class Interval<C#2> cannot be applied to given types;
                        if (!Interval.isValid(interval)) {
                                     ^
  required: Interval<C#1>
  found: Interval<CAP#1>
  reason: inference variable C#1 has incompatible bounds
    equality constraints: CAP#1
    upper bounds: Comparable<? super C#1>
  where C#1,C#2 are type-variables:
    C#1 extends Comparable<? super C#1> declared in method <C#1>isValid(Interval<C#1>)
    C#2 extends Comparable<? super C#2> declared in class Interval
  where CAP#1 is a fresh type-variable:
    CAP#1 extends Comparable<? super CAP#1> from capture of ?


REPRODUCIBILITY :
This bug can be reproduced always.

---------- BEGIN SOURCE ----------
// Interval.java

public class Interval<C extends Comparable<? super C>> {
	public C lower;
	public C upper;
	
	public static <C extends Comparable<? super C>> boolean isValid(Interval<C> interval) {
		return interval.lower.compareTo(interval.upper) <= 0;
	}
}

// IntervalValidator.java

public class IntervalValidator implements Validator {
	@Override
	public void validate(Object object) {
		if (object instanceof Interval) {
			Interval<?> interval = (Interval<?>) object;
			if (!Interval.isValid(interval)) {
				throw new RuntimeException();
			}
		}
	}
}

// Validator.java

public interface Validator {
	void validate(Object object);
}

---------- END SOURCE ----------


Comments
Closing as Won't Fix for 8u: per JDK-8046762, the fix is known but breaks some other, more common use cases. The bug is already fixed in 9.
20-08-2015

This was addressed in 9 and 8u via JDK-8033718. For compatibility reasons, parts of the 8u fix were then reverted by JDK-8046762.
20-08-2015

- Compile the attached source in Windows 7 (64-bit). - Checked this for JDK 7u85, 8, 8u51, 8u60 ea b26, and 9 ea b75 7u85: OK 8: FAIL 8u51: FAIL 8u60 ea b26: FAIL 9 ea b75: OK - Output with JDK 8u51: > javac *.java IntervalValidator.java:6: error: method isValid in class Interval<C#2> cannot be applied to given types; if (!Interval.isValid(interval)) { ^ required: Interval<C#1> found: Interval<CAP#1> reason: inference variable C#1 has incompatible bounds equality constraints: CAP#1 upper bounds: Comparable<? super C#1> where C#1,C#2 are type-variables: C#1 extends Comparable<? super C#1> declared in method <C#1>isValid(Interval<C#1>) C#2 extends Comparable<? super C#2> declared in class Interval where CAP#1 is a fresh type-variable: CAP#1 extends Comparable<? super CAP#1> from capture of ? 1 error - The issue is reproducible with JDK 8-all. Though the code compiles fine with JDK 7u85 and 9 ea b75. This seems a duplicate of JDK-8039214 which has fix in JDK 9.
06-08-2015