[java] Properly handle 0-arg calls
- We no longer take all methods as applicable for a 0-arg method call during type resolution.
This commit is contained in:
@ -115,11 +115,10 @@ public final class MethodTypeResolution {
|
||||
for (int methodIndex = 0; methodIndex < methodsToSearch.size(); ++methodIndex) {
|
||||
MethodType methodType = methodsToSearch.get(methodIndex);
|
||||
|
||||
if (argList == null) {
|
||||
selectedMethods.add(methodType);
|
||||
final int argCount = argList == null ? 0 : argList.jjtGetNumChildren();
|
||||
|
||||
// vararg methods are considered fixed arity here - varargs are dealt with in the 3rd phase
|
||||
} else if (getArity(methodType.getMethod()) == argList.jjtGetNumChildren()) {
|
||||
// vararg methods are considered fixed arity here, see 3rd phase
|
||||
if (getArity(methodType.getMethod()) == argCount) {
|
||||
if (!methodType.isParameterized()) {
|
||||
// https://docs.oracle.com/javase/specs/jls/se8/html/jls-18.html#jls-18.5.1
|
||||
// ...
|
||||
@ -129,7 +128,7 @@ public final class MethodTypeResolution {
|
||||
// reference type, or ii) Fi is a primitive type but ei is not a standalone expression of a
|
||||
// primitive type; then the method is not applicable and there is no need to proceed with inference.
|
||||
Class<?>[] methodParameterTypes = methodType.getMethod().getParameterTypes();
|
||||
for (int argIndex = 0; argIndex < argList.jjtGetNumChildren(); ++argIndex) {
|
||||
for (int argIndex = 0; argIndex < argCount; ++argIndex) {
|
||||
if (((ASTExpression) argList.jjtGetChild(argIndex)).isStandAlonePrimitive()) {
|
||||
if (!methodParameterTypes[argIndex].isPrimitive()) {
|
||||
continue outter; // this method is not applicable
|
||||
@ -146,7 +145,7 @@ public final class MethodTypeResolution {
|
||||
boolean methodIsApplicable = true;
|
||||
|
||||
// try each arguments if it's subtypeable
|
||||
for (int argIndex = 0; argIndex < argList.jjtGetNumChildren(); ++argIndex) {
|
||||
for (int argIndex = 0; argIndex < argCount; ++argIndex) {
|
||||
if (!isSubtypeable(methodType.getParameterTypes().get(argIndex),
|
||||
(ASTExpression) argList.jjtGetChild(argIndex))) {
|
||||
methodIsApplicable = false;
|
||||
@ -193,7 +192,7 @@ public final class MethodTypeResolution {
|
||||
int typeParamIndex = -1;
|
||||
if (methodParameters[i] instanceof TypeVariable) {
|
||||
typeParamIndex = JavaTypeDefinition
|
||||
.getGenericTypeIndex(methodTypeParameters, ((TypeVariable) methodParameters[i]).getName());
|
||||
.getGenericTypeIndex(methodTypeParameters, ((TypeVariable<?>) methodParameters[i]).getName());
|
||||
}
|
||||
|
||||
if (typeParamIndex != -1) {
|
||||
@ -233,7 +232,7 @@ public final class MethodTypeResolution {
|
||||
int boundVarIndex = -1;
|
||||
if (bound instanceof TypeVariable) {
|
||||
boundVarIndex =
|
||||
JavaTypeDefinition.getGenericTypeIndex(typeVariables, ((TypeVariable) bound).getName());
|
||||
JavaTypeDefinition.getGenericTypeIndex(typeVariables, ((TypeVariable<?>) bound).getName());
|
||||
}
|
||||
|
||||
if (boundVarIndex != -1) {
|
||||
@ -268,16 +267,15 @@ public final class MethodTypeResolution {
|
||||
throw new ResolutionFailedException();
|
||||
}
|
||||
|
||||
if (argList == null) {
|
||||
selectedMethods.add(methodType);
|
||||
final int argCount = argList == null ? 0 : argList.jjtGetNumChildren();
|
||||
|
||||
// vararg methods are considered fixed arity here, see 3rd phase
|
||||
} else if (getArity(methodType.getMethod()) == argList.jjtGetNumChildren()) {
|
||||
// vararg methods are considered fixed arity here, see 3rd phase
|
||||
if (getArity(methodType.getMethod()) == argCount) {
|
||||
// check method convertability of each argument to the corresponding parameter
|
||||
boolean methodIsApplicable = true;
|
||||
|
||||
// try each arguments if it's method convertible
|
||||
for (int argIndex = 0; argIndex < argList.jjtGetNumChildren(); ++argIndex) {
|
||||
for (int argIndex = 0; argIndex < argCount; ++argIndex) {
|
||||
if (!isMethodConvertible(methodType.getParameterTypes().get(argIndex),
|
||||
(ASTExpression) argList.jjtGetChild(argIndex))) {
|
||||
methodIsApplicable = false;
|
||||
@ -311,37 +309,39 @@ public final class MethodTypeResolution {
|
||||
throw new ResolutionFailedException();
|
||||
}
|
||||
|
||||
if (argList == null) {
|
||||
selectedMethods.add(methodType);
|
||||
|
||||
// now we consider varargs as not fixed arity
|
||||
// if we reach here and the method is not a vararg, then we didn't find a resolution in earlier phases
|
||||
} else if (methodType.isVararg()) { // check subtypeability of each argument to the corresponding parameter
|
||||
// now we consider varargs as not fixed arity
|
||||
// if we reach here and the method is not a vararg, then we didn't find a resolution in earlier phases
|
||||
if (methodType.isVararg()) { // check subtypeability of each argument to the corresponding parameter
|
||||
boolean methodIsApplicable = true;
|
||||
|
||||
List<JavaTypeDefinition> methodParameters = methodType.getParameterTypes();
|
||||
JavaTypeDefinition varargComponentType = methodType.getVarargComponentType();
|
||||
|
||||
// try each arguments if it's method convertible
|
||||
for (int argIndex = 0; argIndex < argList.jjtGetNumChildren(); ++argIndex) {
|
||||
JavaTypeDefinition parameterType = argIndex < methodParameters.size() - 1
|
||||
? methodParameters.get(argIndex) : varargComponentType;
|
||||
|
||||
if (!isMethodConvertible(parameterType, (ASTExpression) argList.jjtGetChild(argIndex))) {
|
||||
methodIsApplicable = false;
|
||||
break;
|
||||
if (argList == null) {
|
||||
// There are no arguments, make sure the method has only a vararg
|
||||
methodIsApplicable = getArity(methodType.getMethod()) == 1;
|
||||
} else {
|
||||
// try each arguments if it's method convertible
|
||||
for (int argIndex = 0; argIndex < argList.jjtGetNumChildren(); ++argIndex) {
|
||||
JavaTypeDefinition parameterType = argIndex < methodParameters.size() - 1
|
||||
? methodParameters.get(argIndex) : varargComponentType;
|
||||
|
||||
if (!isMethodConvertible(parameterType, (ASTExpression) argList.jjtGetChild(argIndex))) {
|
||||
methodIsApplicable = false;
|
||||
break;
|
||||
}
|
||||
|
||||
// TODO: If k != n, or if k = n and An cannot be converted by method invocation conversion to
|
||||
// Sn[], then the type which is the erasure (§4.6) of Sn is accessible at the point of invocation.
|
||||
|
||||
// TODO: add unchecked conversion in an else if branch
|
||||
}
|
||||
|
||||
// TODO: If k != n, or if k = n and An cannot be converted by method invocation conversion to
|
||||
// Sn[], then the type which is the erasure (§4.6) of Sn is accessible at the point of invocation.
|
||||
|
||||
// TODO: add unchecked conversion in an else if branch
|
||||
}
|
||||
|
||||
if (methodIsApplicable) {
|
||||
selectedMethods.add(methodType);
|
||||
}
|
||||
} else if (!methodType.isVararg()) {
|
||||
} else {
|
||||
// TODO: Remove check for vararg here, once we can detect and use return types of method calls
|
||||
LOG.log(Level.FINE, "Method {0} couldn't be resolved", String.valueOf(methodType));
|
||||
}
|
||||
|
Reference in New Issue
Block a user