[java] typeresolution: support varags with generics

This commit is contained in:
Andreas Dangel
2017-10-06 18:04:17 +02:00
parent acc05d4c9c
commit afae1385aa
5 changed files with 36 additions and 2 deletions

View File

@ -118,7 +118,7 @@ public final class MethodTypeResolution {
if (argList == null) {
selectedMethods.add(methodType);
// vararg methods are considered fixed arity here
// vararg methods are considered fixed arity here - varargs are dealt with in the 3rd phase
} else if (getArity(methodType.getMethod()) == argList.jjtGetNumChildren()) {
if (!methodType.isParameterized()) {
// https://docs.oracle.com/javase/specs/jls/se8/html/jls-18.html#jls-18.5.1
@ -271,7 +271,7 @@ public final class MethodTypeResolution {
if (argList == null) {
selectedMethods.add(methodType);
// vararg methods are considered fixed arity here
// vararg methods are considered fixed arity here, see 3rd phase
} else if (getArity(methodType.getMethod()) == argList.jjtGetNumChildren()) {
// check method convertability of each argument to the corresponding parameter
boolean methodIsApplicable = true;

View File

@ -9,6 +9,8 @@ import static net.sourceforge.pmd.lang.java.typeresolution.typedefinition.TypeDe
import static net.sourceforge.pmd.lang.java.typeresolution.typedefinition.TypeDefinitionType.LOWER_WILDCARD;
import static net.sourceforge.pmd.lang.java.typeresolution.typedefinition.TypeDefinitionType.UPPER_WILDCARD;
import java.lang.reflect.Array;
import java.lang.reflect.GenericArrayType;
import java.lang.reflect.Method;
import java.lang.reflect.ParameterizedType;
import java.lang.reflect.Type;
@ -180,6 +182,10 @@ import java.util.Set;
final Type[] wildcardUpperBounds = ((WildcardType) type).getUpperBounds();
return forClass(UPPER_WILDCARD, resolveTypeDefinition(wildcardUpperBounds[0], method, methodTypeArgs));
}
} else if (type instanceof GenericArrayType) {
JavaTypeDefinition component = resolveTypeDefinition(((GenericArrayType) type).getGenericComponentType());
// TODO: retain the generic types of the array component...
return forClass(Array.newInstance(component.getType(), 0).getClass());
}
// TODO : Shall we throw here?

View File

@ -103,6 +103,7 @@ import net.sourceforge.pmd.typeresolution.testdata.Promotion;
import net.sourceforge.pmd.typeresolution.testdata.SubTypeUsage;
import net.sourceforge.pmd.typeresolution.testdata.SuperExpression;
import net.sourceforge.pmd.typeresolution.testdata.ThisExpression;
import net.sourceforge.pmd.typeresolution.testdata.VarArgsMethodUseCase;
import net.sourceforge.pmd.typeresolution.testdata.dummytypes.Converter;
import net.sourceforge.pmd.typeresolution.testdata.dummytypes.GenericClass;
import net.sourceforge.pmd.typeresolution.testdata.dummytypes.JavaTypeDefinitionEquals;
@ -1677,6 +1678,11 @@ public class ClassTypeResolverTest {
parseAndTypeResolveForClass(OverloadedMethodsUsage.class, "1.8");
}
@Test
public void testVarArgsMethodUseCase() throws Exception {
parseAndTypeResolveForClass(VarArgsMethodUseCase.class, "1.8");
}
private JavaTypeDefinition getChildTypeDef(Node node, int childIndex) {
return ((TypeNode) node.jjtGetChild(childIndex)).getTypeDefinition();
}

View File

@ -21,6 +21,14 @@ public class MethodFirstPhase {
return null;
}
void stringVarargs(String... s) {
}
void classVarargs(Class<?>... c) {
}
Exception subtype(short a, int b, String c) {
return null;

View File

@ -0,0 +1,14 @@
/**
* BSD-style license; for more info see http://pmd.sourceforge.net/license.html
*/
package net.sourceforge.pmd.typeresolution.testdata;
public class VarArgsMethodUseCase {
public void foo() {
MethodFirstPhase methods = new MethodFirstPhase();
methods.stringVarargs("a", "b");
methods.classVarargs(String.class, VarArgsMethodUseCase.class);
}
}