| Summary: | [1.8] Incorrect parameters in resolved method binding for LambdaExpression | ||||||||||||||
|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
| Product: | [Eclipse Project] JDT | Reporter: | Noopur Gupta <noopur_gupta> | ||||||||||||
| Component: | Core | Assignee: | Manoj N Palat <manoj.palat> | ||||||||||||
| Status: | RESOLVED FIXED | QA Contact: | |||||||||||||
| Severity: | normal | ||||||||||||||
| Priority: | P3 | CC: | daniel_megert, manoj.palat, markus.kell.r, srikanth_sankaran | ||||||||||||
| Version: | 4.4 | Flags: | manoj.palat:
review?
(srikanth_sankaran) manoj.palat: review+ |
||||||||||||
| Target Milestone: | BETA J8 | ||||||||||||||
| Hardware: | All | ||||||||||||||
| OS: | All | ||||||||||||||
| Whiteboard: | |||||||||||||||
| Bug Depends on: | |||||||||||||||
| Bug Blocks: | 407985 | ||||||||||||||
| Attachments: |
|
||||||||||||||
Manoj, please follow up. Created attachment 235490 [details]
Test case with modification as a patch
Test case as a patch with correction.
The behaviour is as expected for lambda. In the case of LambdaExpressions, the two additional parameterTypes are added for enclosing outer local variable accesses, namely i1 and foo, by the function LambdaExpression.addSyntheticArgument().
Further note, if it helps: Assuming there are n parameters for lambda, and there are m (m >= n) parameterTypes, the last n of those parameterTypes correspond to the parameters in actual source code, since all the outer local variable access bindings are added to the front of the list.
Srikanth: Any further pointers/comments?
(In reply to Manoj Palat from comment #2) > Created attachment 235490 [details] > Test case with modification as a patch > > Test case as a patch with correction. > > The behaviour is as expected for lambda. No. Please see the javadoc for org.eclipse.jdt.core.dom.IMethodBinding.getParameterTypes() Created attachment 235788 [details]
Proposed Patch
Created attachment 236060 [details]
Proposed Patch
Corrected a cce plus made the patch up-to-date with latest code.
Created attachment 236064 [details]
Proposed Patch
Added the test case which caused CCE at getParameterTypes() in the initial patch
Created attachment 236088 [details]
Alternate patch
Here is an alternate patch that addresses some issues in original patch:
- Tests: should not just assert on parameter count, also go ahead and
verify types.
- We should not use synthetic methods in DBR in the first place. Instead
of working with what infrastructure exists, some times we can get cleaner
solution by adding more infrastructure. I added a getMethodBinding() call
on Lambda/ReferenceExpressions that returns the method binding void of all
synthetics (except where impossible).
- Same problem exists for ReferenceExpressions also, instead of waiting
for it be discovered and reported, let us go ahead and fix it.
- Method name (now defunct) getActualStart() is not a good choice of name
in MethodBinding class.
Manoj, I ran only the ASTConverter18Tests. If you agree with the patch, please run all Java8 tests and release if green. Otherwise, let us discuss. Thanks. (In reply to Srikanth Sankaran from comment #8) > Manoj, I ran only the ASTConverter18Tests. If you agree with the patch, > please > run all Java8 tests and release if green. Otherwise, let us discuss. Thanks. Thanks Srikanth. Patch looks good. Committed (after deleting a few extra whitespaces) via http://git.eclipse.org/c/jdt/eclipse.jdt.core.git/commit/?id=f5937020c6b957eed03745f57cfee671f23dd9b8 |
--------------------------- package test.bugs; @FunctionalInterface interface FI { int foo1(int a); } class FI_1 { void fun(int a) { FI i1 = x1-> x1; FI i2 = xxx-> { i1.foo1(a); return xxx; }; } } --------------------------- Steps: 1. To get the JLS8 AST, set org.eclipse.jdt.internal.ui.javaeditor.ASTProvider.SHARED_AST_LEVEL to AST.JLS8. 2. Open the file with above example or edit it so that reconciler is called. 3. Run this code after the call to unit.reconcile(..) in org.eclipse.jdt.internal.ui.text.java.JavaReconcilingStrategy#reconcile(ICompilationUnit, boolean): AbstractTypeDeclaration test= (AbstractTypeDeclaration) ast.types().get(1); MethodDeclaration meth= (MethodDeclaration) test.bodyDeclarations().get(0); VariableDeclarationFragment vdf= (VariableDeclarationFragment) ((VariableDeclarationStatement) meth.getBody().statements().get(1)).fragments().get(0); LambdaExpression lambda= (LambdaExpression) vdf.getInitializer(); List<VariableDeclaration> parameters= lambda.parameters(); System.out.println(parameters.size()); ITypeBinding[] parameterTypes= lambda.resolveMethodBinding().getParameterTypes(); System.out.println(parameterTypes.length); for (ITypeBinding paramType : parameterTypes) { System.out.println(paramType.getName()); } 4. You can see that the number of parameters obtained from resolved method binding for lambda expr ('i2' in the example) is 3 instead of 1, which is incorrect.