Correctly apply SAM conversions in superclass constructor calls
#KT-5452 Fixed
This commit is contained in:
@@ -1446,9 +1446,10 @@ public class ExpressionCodegen extends JetVisitor<StackValue, StackValue> implem
|
||||
if (superCall != null) {
|
||||
// For an anonymous object, we should also generate all non-default arguments that it captures for its super call
|
||||
ConstructorDescriptor superConstructor = superCall.getResultingDescriptor();
|
||||
ConstructorDescriptor constructorToCall = SamCodegenUtil.resolveSamAdapter(superConstructor);
|
||||
List<ValueParameterDescriptor> superValueParameters = superConstructor.getValueParameters();
|
||||
int params = superValueParameters.size();
|
||||
List<Type> superMappedTypes = typeMapper.mapToCallableMethod(superConstructor).getValueParameterTypes();
|
||||
List<Type> superMappedTypes = typeMapper.mapToCallableMethod(constructorToCall).getValueParameterTypes();
|
||||
assert superMappedTypes.size() >= params : String
|
||||
.format("Incorrect number of mapped parameters vs arguments: %d < %d for %s",
|
||||
superMappedTypes.size(), params, classDescriptor);
|
||||
@@ -1474,7 +1475,7 @@ public class ExpressionCodegen extends JetVisitor<StackValue, StackValue> implem
|
||||
assert constructors.size() == 1 : "Unexpected number of constructors for class: " + classDescriptor + " " + constructors;
|
||||
ConstructorDescriptor constructorDescriptor = KotlinPackage.single(constructors);
|
||||
|
||||
JvmMethodSignature constructor = typeMapper.mapSignature(constructorDescriptor);
|
||||
JvmMethodSignature constructor = typeMapper.mapSignature(SamCodegenUtil.resolveSamAdapter(constructorDescriptor));
|
||||
v.invokespecial(type.getInternalName(), "<init>", constructor.getAsmMethod().getDescriptor(), false);
|
||||
return Unit.INSTANCE$;
|
||||
}
|
||||
@@ -2313,8 +2314,7 @@ public class ExpressionCodegen extends JetVisitor<StackValue, StackValue> implem
|
||||
|
||||
@NotNull
|
||||
private CallableMethod resolveToCallableMethod(@NotNull FunctionDescriptor fd, boolean superCall, @NotNull CodegenContext context) {
|
||||
SimpleFunctionDescriptor originalOfSamAdapter = (SimpleFunctionDescriptor) SamCodegenUtil.getOriginalIfSamAdapter(fd);
|
||||
return typeMapper.mapToCallableMethod(originalOfSamAdapter != null ? originalOfSamAdapter : fd, superCall, context);
|
||||
return typeMapper.mapToCallableMethod(SamCodegenUtil.resolveSamAdapter(fd), superCall, context);
|
||||
}
|
||||
|
||||
public void invokeMethodWithArguments(
|
||||
@@ -3593,8 +3593,8 @@ public class ExpressionCodegen extends JetVisitor<StackValue, StackValue> implem
|
||||
// See StackValue.receiver for more info
|
||||
pushClosureOnStack(constructor.getContainingDeclaration(), dispatchReceiver == null, defaultCallGenerator);
|
||||
|
||||
ConstructorDescriptor originalOfSamAdapter = (ConstructorDescriptor) SamCodegenUtil.getOriginalIfSamAdapter(constructor);
|
||||
CallableMethod method = typeMapper.mapToCallableMethod(originalOfSamAdapter == null ? constructor : originalOfSamAdapter);
|
||||
constructor = SamCodegenUtil.resolveSamAdapter(constructor);
|
||||
CallableMethod method = typeMapper.mapToCallableMethod(constructor);
|
||||
invokeMethodWithArguments(method, resolvedCall, StackValue.none());
|
||||
|
||||
return Unit.INSTANCE$;
|
||||
|
||||
@@ -1466,7 +1466,7 @@ public class ImplementationBodyCodegen extends ClassBodyCodegen {
|
||||
return;
|
||||
}
|
||||
iv.load(0, OBJECT_TYPE);
|
||||
ConstructorDescriptor delegateConstructor = delegationConstructorCall.getResultingDescriptor();
|
||||
ConstructorDescriptor delegateConstructor = SamCodegenUtil.resolveSamAdapter(delegationConstructorCall.getResultingDescriptor());
|
||||
|
||||
CallableMethod delegateConstructorCallable = typeMapper.mapToCallableMethod(delegateConstructor);
|
||||
CallableMethod callable = typeMapper.mapToCallableMethod(constructorDescriptor);
|
||||
|
||||
@@ -42,6 +42,11 @@ public class SamCodegenUtil {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static <T extends FunctionDescriptor> T resolveSamAdapter(@NotNull T descriptor) {
|
||||
FunctionDescriptor original = getOriginalIfSamAdapter(descriptor);
|
||||
return original != null ? (T) original : descriptor;
|
||||
}
|
||||
|
||||
private SamCodegenUtil() {
|
||||
}
|
||||
}
|
||||
|
||||
+11
-1
@@ -386,6 +386,10 @@ class CodegenAnnotatingVisitor extends JetVisitorVoid {
|
||||
@Override
|
||||
public void visitCallExpression(@NotNull JetCallExpression expression) {
|
||||
super.visitCallExpression(expression);
|
||||
checkSamCall(expression);
|
||||
}
|
||||
|
||||
private void checkSamCall(@NotNull JetCallElement expression) {
|
||||
ResolvedCall<?> call = CallUtilPackage.getResolvedCall(expression, bindingContext);
|
||||
if (call == null) return;
|
||||
|
||||
@@ -416,7 +420,13 @@ class CodegenAnnotatingVisitor extends JetVisitorVoid {
|
||||
}
|
||||
}
|
||||
|
||||
private void recordSamConstructorIfNeeded(@NotNull JetCallExpression expression, @NotNull ResolvedCall<?> call) {
|
||||
@Override
|
||||
public void visitDelegationToSuperCallSpecifier(@NotNull JetDelegatorToSuperCall call) {
|
||||
super.visitDelegationToSuperCallSpecifier(call);
|
||||
checkSamCall(call);
|
||||
}
|
||||
|
||||
private void recordSamConstructorIfNeeded(@NotNull JetCallElement expression, @NotNull ResolvedCall<?> call) {
|
||||
CallableDescriptor callableDescriptor = call.getResultingDescriptor();
|
||||
if (!(callableDescriptor.getOriginal() instanceof SamConstructorDescriptor)) return;
|
||||
|
||||
|
||||
@@ -62,7 +62,7 @@ public class CodegenBinding {
|
||||
|
||||
public static final WritableSlice<JetExpression, SamType> SAM_VALUE = Slices.createSimpleSlice();
|
||||
|
||||
public static final WritableSlice<JetCallExpression, JetExpression> SAM_CONSTRUCTOR_TO_ARGUMENT = Slices.createSimpleSlice();
|
||||
public static final WritableSlice<JetCallElement, JetExpression> SAM_CONSTRUCTOR_TO_ARGUMENT = Slices.createSimpleSlice();
|
||||
|
||||
public static final WritableSlice<JetWhenExpression, WhenByEnumsMapping> MAPPING_FOR_WHEN_BY_ENUM =
|
||||
Slices.<JetWhenExpression, WhenByEnumsMapping>sliceBuilder().build();
|
||||
|
||||
@@ -924,7 +924,7 @@ public class JetTypeMapper {
|
||||
@NotNull ResolvedCall<ConstructorDescriptor> superCall,
|
||||
boolean hasOuter
|
||||
) {
|
||||
ConstructorDescriptor superDescriptor = superCall.getResultingDescriptor();
|
||||
ConstructorDescriptor superDescriptor = SamCodegenUtil.resolveSamAdapter(superCall.getResultingDescriptor());
|
||||
List<ResolvedValueArgument> valueArguments = superCall.getValueArgumentsByIndex();
|
||||
assert valueArguments != null : "Failed to arrange value arguments by index: " + superDescriptor;
|
||||
|
||||
|
||||
Reference in New Issue
Block a user