private static void generateLocalVariableTable( @NotNull MethodVisitor mv, @NotNull JvmMethodSignature jvmMethodSignature, @NotNull FunctionDescriptor functionDescriptor, @Nullable Type thisType, @NotNull Label methodBegin, @NotNull Label methodEnd, @NotNull OwnerKind ownerKind) { Iterator<ValueParameterDescriptor> valueParameters = functionDescriptor.getValueParameters().iterator(); List<JvmMethodParameterSignature> params = jvmMethodSignature.getValueParameters(); int shift = 0; boolean isStatic = AsmUtil.isStaticMethod(ownerKind, functionDescriptor); if (!isStatic) { // add this if (thisType != null) { mv.visitLocalVariable( "this", thisType.getDescriptor(), null, methodBegin, methodEnd, shift); } else { // TODO: provide thisType for callable reference } shift++; } for (int i = 0; i < params.size(); i++) { JvmMethodParameterSignature param = params.get(i); JvmMethodParameterKind kind = param.getKind(); String parameterName; if (kind == JvmMethodParameterKind.VALUE) { ValueParameterDescriptor parameter = valueParameters.next(); parameterName = parameter.getName().asString(); } else { String lowercaseKind = kind.name().toLowerCase(); parameterName = needIndexForVar(kind) ? "$" + lowercaseKind + "$" + i : "$" + lowercaseKind; } Type type = param.getAsmType(); mv.visitLocalVariable( parameterName, type.getDescriptor(), null, methodBegin, methodEnd, shift); shift += type.getSize(); } }
public void visitLocalVariable( String name, String desc, String signature, Label start, Label end, int index, MethodVisitor mv) { RemapInfo info = doRemap(index); // add entries only for shifted vars or remapped to locals if (SHIFT == info.status || REMAPPED == info.status && info.value instanceof StackValue.Local) { int newIndex = ((StackValue.Local) info.value).index; mv.visitLocalVariable(name, desc, signature, start, end, newIndex); } }
public static void generateMethodBody( @NotNull MethodVisitor mv, @NotNull FunctionDescriptor functionDescriptor, @NotNull MethodContext context, @NotNull JvmMethodSignature signature, @NotNull FunctionGenerationStrategy strategy, @NotNull MemberCodegen<?> parentCodegen) { mv.visitCode(); Label methodBegin = new Label(); mv.visitLabel(methodBegin); JetTypeMapper typeMapper = parentCodegen.typeMapper; if (BuiltinSpecialBridgesUtil.shouldHaveTypeSafeBarrier( functionDescriptor, getSignatureMapper(typeMapper))) { generateTypeCheckBarrierIfNeeded( new InstructionAdapter(mv), functionDescriptor, signature.getReturnType(), /* delegateParameterType = */ null); } Label methodEnd; int functionFakeIndex = -1; int lambdaFakeIndex = -1; if (context.getParentContext() instanceof MultifileClassFacadeContext) { generateFacadeDelegateMethodBody( mv, signature.getAsmMethod(), (MultifileClassFacadeContext) context.getParentContext()); methodEnd = new Label(); } else { FrameMap frameMap = createFrameMap( parentCodegen.state, functionDescriptor, signature, isStaticMethod(context.getContextKind(), functionDescriptor)); if (context.isInlineMethodContext()) { functionFakeIndex = frameMap.enterTemp(Type.INT_TYPE); } if (context instanceof InlineLambdaContext) { lambdaFakeIndex = frameMap.enterTemp(Type.INT_TYPE); } Label methodEntry = new Label(); mv.visitLabel(methodEntry); context.setMethodStartLabel(methodEntry); if (!JetTypeMapper.isAccessor(functionDescriptor)) { genNotNullAssertionsForParameters( new InstructionAdapter(mv), parentCodegen.state, functionDescriptor, frameMap); } methodEnd = new Label(); context.setMethodEndLabel(methodEnd); strategy.generateBody(mv, frameMap, signature, context, parentCodegen); } mv.visitLabel(methodEnd); Type thisType = getThisTypeForFunction(functionDescriptor, context, typeMapper); generateLocalVariableTable( mv, signature, functionDescriptor, thisType, methodBegin, methodEnd, context.getContextKind()); if (context.isInlineMethodContext() && functionFakeIndex != -1) { mv.visitLocalVariable( JvmAbi.LOCAL_VARIABLE_NAME_PREFIX_INLINE_FUNCTION + functionDescriptor.getName().asString(), Type.INT_TYPE.getDescriptor(), null, methodBegin, methodEnd, functionFakeIndex); } if (context instanceof InlineLambdaContext && thisType != null && lambdaFakeIndex != -1) { String name = thisType.getClassName(); int indexOfLambdaOrdinal = name.lastIndexOf("$"); if (indexOfLambdaOrdinal > 0) { int lambdaOrdinal = Integer.parseInt(name.substring(indexOfLambdaOrdinal + 1)); mv.visitLocalVariable( JvmAbi.LOCAL_VARIABLE_NAME_PREFIX_INLINE_ARGUMENT + lambdaOrdinal, Type.INT_TYPE.getDescriptor(), null, methodBegin, methodEnd, lambdaFakeIndex); } } }