Bug 293384 - Eclipse erroneously reports method "is ambiguous for type"
Summary: Eclipse erroneously reports method "is ambiguous for type"
Status: VERIFIED FIXED
Alias: None
Product: JDT
Classification: Eclipse Project
Component: Core (show other bugs)
Version: 3.6   Edit
Hardware: PC Windows XP
: P3 normal (vote)
Target Milestone: 3.6 M4   Edit
Assignee: Srikanth Sankaran CLA
QA Contact:
URL:
Whiteboard:
Keywords:
Depends on:
Blocks:
 
Reported: 2009-10-26 22:27 EDT by Tony Weddle CLA
Modified: 2009-12-08 03:23 EST (History)
3 users (show)

See Also:


Attachments
Potential patch (3.14 KB, patch)
2009-10-29 10:47 EDT, Srikanth Sankaran CLA
no flags Details | Diff
Revised patch (3.30 KB, patch)
2009-11-02 09:13 EST, Srikanth Sankaran CLA
no flags Details | Diff

Note You need to log in before you can comment on or make changes to this bug.
Description Tony Weddle CLA 2009-10-26 22:27:07 EDT
User-Agent:       Mozilla/5.0 (Windows; U; Windows NT 5.1; en-GB; rv:1.9.1.3) Gecko/20090824 Firefox/3.5.3 (.NET CLR 3.5.30729)
Build Identifier: 20090920-1017

A class which compiles fine with javac 1.6.0, doesn't compile without errors when using Eclipse. I've made up some test code with the essential conditions that can reproduce the error consistently. Note that the test code is a generic class though the generics class parameter isn't used in the code (using it in the code doesn't affect the error). If the class parameter is removed, the error goes away.

Reproducible: Always

Steps to Reproduce:
1. Create a class with the following code:

public class AmbiguousCallBug<Tout extends Object> {
	static public abstract class BaseA {};
	static public abstract class BaseB extends BaseA {};
	static public class Real extends BaseB {};
	
	static BaseA ask(String prompt) {
		Real impl = new Real();
		return (BaseA) ask(prompt, impl);
	}
	
	static BaseA ask(String prompt, Real impl) {
		return null;
	}
	
	static <T extends BaseA> T ask(String prompt, T impl) {
		return null;
	}
	
	static public void main(String[] args) {
		
	}
}

2. The editor now reports a problem with the line

		return (BaseA) ask(prompt, impl);

that "The method ask(String, AmbiguousCallBug.Real) is ambiguous for the type AmbiguousCallBug<Tout>" 

3. Simply removing the class parameter, <Tout extends Object>, from the class definition for AmbiguousCallBug, will result in a clean JDT compile.
Comment 1 Olivier Thomann CLA 2009-10-26 23:05:13 EDT
Srikanth, please investigate while Kent can still guide you through the code.
Thanks.
Comment 2 Srikanth Sankaran CLA 2009-10-28 01:52:48 EDT
Javac & eclipse behavior match upto 3.5M7 and started diverging
in 3.5RC1.

After preliminary investigation, this looks like is due to bad fix
for bug# 275471.

From bug# 275471 comment#3

> We no longer will force the hierarchy of every parameter type to be resolved
> for an exact method match to proceed in 1.5.
> Instead we will check to see if the parameter type's hierarchy has been
> connected, if not we will look for all possible method matches.

This changed behavior results in org.eclipse.jdt.internal.compiler.lookup.Scope.findExactMethod(ReferenceBinding, char[], TypeBinding[], InvocationSite) skipping
over the exact match.
Comment 3 Kent Johnson CLA 2009-10-28 12:49:56 EDT
Srikanth,

We need to skip the exact match in this case, but there is another problematic test when we try to decide if the two methods are 'equal' because of substitution.
Comment 4 Srikanth Sankaran CLA 2009-10-29 04:44:07 EDT
(In reply to comment #3)
> Srikanth,
> We need to skip the exact match in this case, but there is another problematic
> test when we try to decide if the two methods are 'equal' because of
> substitution.

Did you mean "we need to" or that "we will have to live with skipping
the exact match" ?
Comment 5 Kent Johnson CLA 2009-10-29 10:25:50 EDT
I mean 'we need to'.

We have to look for inherited methods that could match, so the exact match cannot be used in this case.

Once we skip the exact match, we then have to find the best match from the 2 possible matches.
Comment 6 Srikanth Sankaran CLA 2009-10-29 10:47:26 EDT
Created attachment 150825 [details]
Potential patch


Kent, please take a look. This fixes the problem without
breaking anything else. Let us discuss if something is
amiss tomorrow morning your time - Thanks.
Comment 7 Kent Johnson CLA 2009-10-29 11:21:14 EDT
1. Would normally add this test to AmbiguousMethodTest instead of GenericTypeTest

2. The change looks good, but you may want to rework it to be :

if (candidate.hasSubstitutedParameters()) {
  for (int j = i + 1; j < visiblesCount; j++) {
    MethodBinding otherCandidate = candidates[j];
    if (otherCandidate.hasSubstitutedParameters()) {
      if (otherCandidate == candidate
        || (candidate.declaringClass == otherCandidate.declaringClass && ...))
          return new ProblemMethodBinding(candidates[i], ...);
    }
  }
}
Comment 8 Srikanth Sankaran CLA 2009-10-30 02:22:34 EDT
(In reply to comment #7)
> 1. Would normally add this test to AmbiguousMethodTest instead of
> GenericTypeTest
> 2. The change looks good, but you may want to rework it to be :
> if (candidate.hasSubstitutedParameters()) {
>   for (int j = i + 1; j < visiblesCount; j++) {
>     MethodBinding otherCandidate = candidates[j];
>     if (otherCandidate.hasSubstitutedParameters()) {
>       if (otherCandidate == candidate
>         || (candidate.declaringClass == otherCandidate.declaringClass && ...))
>           return new ProblemMethodBinding(candidates[i], ...);
>     }
>   }
> }

Agree on both counts, I'll take it from there, Thanks!
Comment 9 Srikanth Sankaran CLA 2009-11-02 04:44:04 EST
(In reply to comment #2)
> Javac & eclipse behavior match upto 3.5M7 and started diverging
> in 3.5RC1.
> After preliminary investigation, this looks like is due to bad fix
> for bug# 275471.

For the record, this defect was latent and pre-existent and started
manifesting after the checkin for the fix of bug# 275471, but was
not caused by it.

Olivier, do you want this for 3.5.2 ? (a regression relative to 3.4.2
or to 3.5 M7)
Comment 10 Olivier Thomann CLA 2009-11-02 09:09:47 EST
(In reply to comment #9)
> Olivier, do you want this for 3.5.2 ? (a regression relative to 3.4.2
> or to 3.5 M7)
Yes depending on the risk's assessment.
Comment 11 Srikanth Sankaran CLA 2009-11-02 09:13:19 EST
Created attachment 151069 [details]
Revised patch

Revised patch incorporting review comments
Comment 12 Srikanth Sankaran CLA 2009-11-02 09:23:16 EST
Released in HEAD for 3.6M4
Comment 13 Srikanth Sankaran CLA 2009-11-03 03:52:50 EST
Released.
Comment 14 Jay Arthanareeswaran CLA 2009-12-08 02:15:38 EST
Verified for 3.6M4 using build I20091207-1800