blob: ce82f75db81a12046febbbb7278d74c070e536f6 [file]
// Copyright (c) 2021, the R8 project authors. Please see the AUTHORS file
// for details. All rights reserved. Use of this source code is governed by a
// BSD-style license that can be found in the LICENSE file.
package com.android.tools.r8.ir.desugar;
import com.android.tools.r8.cf.code.CfInstruction;
import com.android.tools.r8.contexts.CompilationContext.MethodProcessingContext;
import com.android.tools.r8.errors.CompilationError;
import com.android.tools.r8.graph.AppView;
import com.android.tools.r8.graph.ProgramMethod;
import com.android.tools.r8.ir.code.Position;
import com.android.tools.r8.ir.desugar.desugaredlibrary.apiconversion.DesugaredLibraryAPIConverter;
import com.android.tools.r8.ir.desugar.itf.InterfaceMethodProcessorFacade;
import com.android.tools.r8.ir.desugar.itf.InterfaceMethodRewriter;
import com.android.tools.r8.ir.desugar.itf.InterfaceProcessor;
import com.android.tools.r8.ir.desugar.nest.D8NestBasedAccessDesugaring;
import com.android.tools.r8.utils.InternalOptions;
import com.android.tools.r8.utils.ThrowingConsumer;
import java.util.Collection;
import java.util.function.Consumer;
import java.util.function.Function;
import java.util.function.Predicate;
/**
* Abstracts a collection of low-level desugarings (i.e., mappings from class-file instructions to
* new class-file instructions).
*
* <p>The combined set of low-level desugarings provide a way to desugar a method in full
*/
public abstract class CfInstructionDesugaringCollection {
public static CfInstructionDesugaringCollection create(AppView<?> appView) {
InternalOptions options = appView.options();
if (options.desugarState.isOff() && options.forceNestDesugaring) {
throw new CompilationError(
"Cannot combine -Dcom.android.tools.r8.forceNestDesugaring with desugaring turned off");
}
if (options.partialSubCompilationConfiguration != null
&& options.partialSubCompilationConfiguration.isR8()) {
return empty();
}
if (options.desugarState.isOn()) {
return new NonEmptyCfInstructionDesugaringCollection(appView);
}
// TODO(b/145775365): invoke-special desugaring is mandatory, since we currently can't map
// invoke-special instructions that require desugaring into IR.
if (options.isGeneratingClassFiles()) {
return NonEmptyCfInstructionDesugaringCollection.createForCfToCfNonDesugar(appView);
}
return NonEmptyCfInstructionDesugaringCollection.createForCfToDexNonDesugar(appView);
}
public static CfInstructionDesugaringCollection empty() {
return EmptyCfInstructionDesugaringCollection.getInstance();
}
public abstract void prepare(
ProgramMethod method,
CfInstructionDesugaringEventConsumer eventConsumer,
ProgramAdditions programAdditions);
/** Desugars the instructions in the given method. */
public abstract void desugar(
ProgramMethod method,
MethodProcessingContext methodProcessingContext,
CfInstructionDesugaringEventConsumer eventConsumer);
/** Selective desugaring of a single invoke instruction assuming a given context. */
public abstract Collection<CfInstruction> desugarInstruction(
CfInstruction instruction,
Position position,
FreshLocalProvider freshLocalProvider,
LocalStackAllocator localStackAllocator,
CfDesugaringInfo desugaringInfo,
CfInstructionDesugaringEventConsumer eventConsumer,
ProgramMethod context,
MethodProcessingContext methodProcessingContext);
public boolean isEmpty() {
return false;
}
/** Returns true if the given method needs desugaring. */
public abstract boolean needsDesugaring(ProgramMethod method);
public abstract <T extends Throwable> void withD8NestBasedAccessDesugaring(
ThrowingConsumer<D8NestBasedAccessDesugaring, T> consumer) throws T;
public abstract InterfaceMethodProcessorFacade getInterfaceMethodPostProcessingDesugaringR8(
Predicate<ProgramMethod> isLiveMethod, InterfaceProcessor processor);
public abstract void withDesugaredLibraryAPIConverter(
Consumer<DesugaredLibraryAPIConverter> consumer);
public abstract <T> T withInterfaceMethodRewriter(Function<InterfaceMethodRewriter, T> fn);
}