Refactor class signature creation to use its builder.
This also updates the builder to canonicalize the "no signature"
information.
Bug: b/280356274
Change-Id: I62f122fcaf26a84db4b98781cf54ea2b26be22ff
diff --git a/src/main/java/com/android/tools/r8/graph/DexClass.java b/src/main/java/com/android/tools/r8/graph/DexClass.java
index c79cb1b..82d48be 100644
--- a/src/main/java/com/android/tools/r8/graph/DexClass.java
+++ b/src/main/java/com/android/tools/r8/graph/DexClass.java
@@ -31,6 +31,7 @@
import java.util.ArrayList;
import java.util.Arrays;
import java.util.Collection;
+import java.util.Collections;
import java.util.Iterator;
import java.util.List;
import java.util.ListIterator;
@@ -817,8 +818,8 @@
}
public boolean validInterfaceSignatures() {
- return getClassSignature().superInterfaceSignatures().isEmpty()
- || interfaces.values.length == getClassSignature().superInterfaceSignatures.size();
+ return getClassSignature().getSuperInterfaceSignatures().isEmpty()
+ || interfaces.values.length == getClassSignature().getSuperInterfaceSignatures().size();
}
public void forEachImmediateInterfaceWithSignature(
@@ -826,7 +827,7 @@
assert validInterfaceSignatures();
// If there is no generic signature information don't pass any type arguments.
- if (getClassSignature().superInterfaceSignatures().isEmpty()) {
+ if (getClassSignature().getSuperInterfaceSignatures().isEmpty()) {
forEachImmediateInterface(
superInterface ->
consumer.accept(superInterface, new ClassTypeSignature(superInterface)));
@@ -835,7 +836,7 @@
Iterator<DexType> interfaceIterator = Arrays.asList(interfaces.values).iterator();
Iterator<ClassTypeSignature> interfaceSignatureIterator =
- getClassSignature().superInterfaceSignatures().iterator();
+ getClassSignature().getSuperInterfaceSignatures().iterator();
while (interfaceIterator.hasNext()) {
assert interfaceSignatureIterator.hasNext();
@@ -846,9 +847,9 @@
}
public void forEachImmediateSupertypeWithSignature(
- BiConsumer<DexType, ClassTypeSignature> consumer) {
+ DexItemFactory factory, BiConsumer<DexType, ClassTypeSignature> consumer) {
if (superType != null) {
- consumer.accept(superType, classSignature.superClassSignature);
+ consumer.accept(superType, classSignature.getSuperClassSignatureOrObject(factory));
}
forEachImmediateInterfaceWithSignature(consumer);
}
@@ -859,7 +860,7 @@
assert validInterfaceSignatures();
// If there is no generic signature information don't pass any type arguments.
- if (getClassSignature().superInterfaceSignatures().size() == 0) {
+ if (getClassSignature().getSuperInterfaceSignatures().isEmpty()) {
forEachImmediateInterface(
superInterface -> consumer.accept(superInterface, ImmutableList.of()));
return;
@@ -867,7 +868,7 @@
Iterator<DexType> interfaceIterator = Arrays.asList(interfaces.values).iterator();
Iterator<ClassTypeSignature> interfaceSignatureIterator =
- getClassSignature().superInterfaceSignatures().iterator();
+ getClassSignature().getSuperInterfaceSignatures().iterator();
while (interfaceIterator.hasNext()) {
assert interfaceSignatureIterator.hasNext();
@@ -890,17 +891,18 @@
BiConsumer<DexType, List<FieldTypeSignature>> consumer) {
if (superType != null) {
consumer.accept(
- superType, applyTypeArguments(getClassSignature().superClassSignature, typeArguments));
+ superType,
+ applyTypeArguments(getClassSignature().getSuperClassSignatureOrNull(), typeArguments));
}
forEachImmediateInterfaceWithAppliedTypeArguments(typeArguments, consumer);
}
private List<FieldTypeSignature> applyTypeArguments(
ClassTypeSignature superInterfaceSignatures, List<FieldTypeSignature> appliedTypeArguments) {
- ImmutableList.Builder<FieldTypeSignature> superTypeArgumentsBuilder = ImmutableList.builder();
- if (superInterfaceSignatures.type.toSourceString().equals("java.util.Map")) {
- System.currentTimeMillis();
+ if (superInterfaceSignatures == null) {
+ return Collections.emptyList();
}
+ ImmutableList.Builder<FieldTypeSignature> superTypeArgumentsBuilder = ImmutableList.builder();
superInterfaceSignatures
.typeArguments()
.forEach(
diff --git a/src/main/java/com/android/tools/r8/graph/DexProgramClass.java b/src/main/java/com/android/tools/r8/graph/DexProgramClass.java
index fc4c4a6..058aded 100644
--- a/src/main/java/com/android/tools/r8/graph/DexProgramClass.java
+++ b/src/main/java/com/android/tools/r8/graph/DexProgramClass.java
@@ -27,7 +27,6 @@
import com.android.tools.r8.utils.structural.StructuralItem;
import com.android.tools.r8.utils.structural.StructuralMapping;
import com.android.tools.r8.utils.structural.StructuralSpecification;
-import com.google.common.collect.ImmutableList;
import com.google.common.collect.Iterables;
import java.util.ArrayList;
import java.util.Arrays;
@@ -732,12 +731,12 @@
methodCollection.replaceVirtualMethod(virtualMethod, replacement);
}
- public void addExtraInterfaces(List<ClassTypeSignature> extraInterfaces) {
+ public void addExtraInterfaces(List<ClassTypeSignature> extraInterfaces, DexItemFactory factory) {
if (extraInterfaces.isEmpty()) {
return;
}
addExtraInterfacesToInterfacesArray(extraInterfaces);
- addExtraInterfacesToSignatureIfPresent(extraInterfaces);
+ addExtraInterfacesToSignatureIfPresent(extraInterfaces, factory);
}
private void addExtraInterfacesToInterfacesArray(List<ClassTypeSignature> extraInterfaces) {
@@ -749,21 +748,20 @@
interfaces = new DexTypeList(newInterfaces);
}
- private void addExtraInterfacesToSignatureIfPresent(List<ClassTypeSignature> extraInterfaces) {
+ private void addExtraInterfacesToSignatureIfPresent(
+ List<ClassTypeSignature> extraInterfaces, DexItemFactory factory) {
+ assert !extraInterfaces.isEmpty();
// We introduce the extra interfaces to the generic signature.
- if (classSignature.hasNoSignature() || extraInterfaces.isEmpty()) {
+ if (classSignature.hasNoSignature()) {
return;
}
- ImmutableList.Builder<ClassTypeSignature> interfacesBuilder =
- ImmutableList.<ClassTypeSignature>builder().addAll(classSignature.superInterfaceSignatures);
- for (ClassTypeSignature extraInterface : extraInterfaces) {
- interfacesBuilder.add(extraInterface);
- }
classSignature =
- new ClassSignature(
- classSignature.formalTypeParameters,
- classSignature.superClassSignature,
- interfacesBuilder.build());
+ ClassSignature.builder()
+ .addSuperInterfaceSignatures(classSignature.getSuperInterfaceSignatures())
+ .addSuperInterfaceSignatures(extraInterfaces)
+ .setSuperClassSignature(classSignature.getSuperClassSignatureOrNull())
+ .addFormalTypeParameters(classSignature.getFormalTypeParameters())
+ .build(factory);
}
@Override
diff --git a/src/main/java/com/android/tools/r8/graph/GenericSignature.java b/src/main/java/com/android/tools/r8/graph/GenericSignature.java
index f1122b8..d669d502 100644
--- a/src/main/java/com/android/tools/r8/graph/GenericSignature.java
+++ b/src/main/java/com/android/tools/r8/graph/GenericSignature.java
@@ -9,6 +9,7 @@
import com.android.tools.r8.DiagnosticsHandler;
import com.android.tools.r8.errors.Unreachable;
+import com.android.tools.r8.graph.GenericSignature.ClassSignature.ClassSignatureBuilder;
import com.android.tools.r8.naming.NamingLens;
import com.android.tools.r8.origin.Origin;
import com.android.tools.r8.utils.DescriptorUtils;
@@ -17,6 +18,7 @@
import java.nio.CharBuffer;
import java.util.ArrayList;
import java.util.List;
+import java.util.function.Consumer;
import java.util.function.Predicate;
/**
@@ -207,35 +209,44 @@
public static class ClassSignature implements DexDefinitionSignature<DexClass> {
private static final ClassSignature NO_CLASS_SIGNATURE =
- new ClassSignature(EMPTY_TYPE_PARAMS, NO_FIELD_TYPE_SIGNATURE, EMPTY_SUPER_INTERFACES);
+ new ClassSignature(EMPTY_TYPE_PARAMS, null, EMPTY_SUPER_INTERFACES);
- final List<FormalTypeParameter> formalTypeParameters;
- final ClassTypeSignature superClassSignature;
- final List<ClassTypeSignature> superInterfaceSignatures;
+ public static ClassSignature noSignature() {
+ return NO_CLASS_SIGNATURE;
+ }
+
+ private final List<FormalTypeParameter> formalTypeParameters;
+ private final ClassTypeSignature superClassSignatureOrNullForObject;
+ private final List<ClassTypeSignature> superInterfaceSignatures;
ClassSignature(
List<FormalTypeParameter> formalTypeParameters,
ClassTypeSignature superClassSignature,
List<ClassTypeSignature> superInterfaceSignatures) {
assert formalTypeParameters != null;
- assert superClassSignature != null;
assert superInterfaceSignatures != null;
this.formalTypeParameters = formalTypeParameters;
- this.superClassSignature = superClassSignature;
+ this.superClassSignatureOrNullForObject = superClassSignature;
this.superInterfaceSignatures = superInterfaceSignatures;
}
- public ClassTypeSignature superClassSignature() {
- return superClassSignature;
+ public ClassTypeSignature getSuperClassSignatureOrNull() {
+ return superClassSignatureOrNullForObject;
}
- public List<ClassTypeSignature> superInterfaceSignatures() {
+ public ClassTypeSignature getSuperClassSignatureOrObject(DexItemFactory factory) {
+ return superClassSignatureOrNullForObject != null
+ ? superClassSignatureOrNullForObject
+ : new ClassTypeSignature(factory.objectType);
+ }
+
+ public List<ClassTypeSignature> getSuperInterfaceSignatures() {
return superInterfaceSignatures;
}
@Override
public boolean hasSignature() {
- return this != NO_CLASS_SIGNATURE;
+ return this != noSignature();
}
@Override
@@ -258,21 +269,32 @@
return formalTypeParameters;
}
- public ClassSignature visit(GenericSignatureVisitor visitor) {
+ public ClassSignature visit(GenericSignatureVisitor visitor, DexItemFactory factory) {
if (hasNoSignature()) {
return this;
}
List<FormalTypeParameter> rewrittenParameters =
visitor.visitFormalTypeParameters(formalTypeParameters);
- ClassTypeSignature rewrittenSuperClass = visitor.visitSuperClass(superClassSignature);
+ ClassTypeSignature rewrittenSuperClass =
+ visitor.visitSuperClass(superClassSignatureOrNullForObject);
List<ClassTypeSignature> rewrittenInterfaces =
visitor.visitSuperInterfaces(superInterfaceSignatures);
if (formalTypeParameters == rewrittenParameters
- && superClassSignature == rewrittenSuperClass
+ && superClassSignatureOrNullForObject == rewrittenSuperClass
&& superInterfaceSignatures == rewrittenInterfaces) {
return this;
}
- return new ClassSignature(rewrittenParameters, rewrittenSuperClass, rewrittenInterfaces);
+ return ClassSignature.builder()
+ .addFormalTypeParameters(rewrittenParameters)
+ .setSuperClassSignature(rewrittenSuperClass)
+ .addSuperInterfaceSignatures(rewrittenInterfaces)
+ .build(factory);
+ }
+
+ public void visitWithoutRewrite(GenericSignatureVisitor visitor) {
+ visitor.visitFormalTypeParameters(formalTypeParameters);
+ visitor.visitSuperClass(superClassSignatureOrNullForObject);
+ visitor.visitSuperInterfaces(superInterfaceSignatures);
}
public String toRenamedString(NamingLens namingLens, Predicate<DexType> isTypeMissing) {
@@ -290,14 +312,12 @@
return toRenamedString(NamingLens.getIdentityLens(), alwaysTrue());
}
- public static ClassSignature noSignature() {
- return NO_CLASS_SIGNATURE;
- }
-
- public List<FieldTypeSignature> getGenericArgumentsToSuperType(DexType type) {
+ public List<FieldTypeSignature> getGenericArgumentsToSuperType(
+ DexType type, DexItemFactory factory) {
assert hasSignature();
- if (superClassSignature.type == type) {
- return superClassSignature.typeArguments;
+ ClassTypeSignature superClassSig = getSuperClassSignatureOrObject(factory);
+ if (superClassSig.type == type) {
+ return superClassSig.typeArguments;
}
for (ClassTypeSignature superInterfaceSignature : superInterfaceSignatures) {
if (superInterfaceSignature.type == type) {
@@ -319,6 +339,11 @@
private ClassSignatureBuilder() {}
+ public ClassSignatureBuilder addFormalTypeParameter(FormalTypeParameter formal) {
+ formalTypeParameters.add(formal);
+ return this;
+ }
+
public ClassSignatureBuilder addFormalTypeParameters(List<FormalTypeParameter> formals) {
formalTypeParameters.addAll(formals);
return this;
@@ -329,12 +354,32 @@
return this;
}
- public ClassSignatureBuilder addInterface(ClassTypeSignature iface) {
+ public ClassSignatureBuilder addSuperInterfaceSignature(ClassTypeSignature iface) {
superInterfaceSignatures.add(iface);
return this;
}
- public ClassSignature build() {
+ public ClassSignatureBuilder addSuperInterfaceSignatures(List<ClassTypeSignature> ifaces) {
+ superInterfaceSignatures.addAll(ifaces);
+ return this;
+ }
+
+ public ClassSignature build(DexItemFactory factory) {
+ // Any trivial super class signature is always represented by the null value.
+ if (superClassSignature != null) {
+ if (superClassSignature.type() == factory.objectType) {
+ assert !superClassSignature.hasTypeVariableArguments();
+ superClassSignature = null;
+ } else if (superClassSignature.hasNoSignature()) {
+ superClassSignature = null;
+ }
+ }
+ // Any trivial class signature is represented by the "no signature" singleton.
+ if (superClassSignature == null
+ && formalTypeParameters.isEmpty()
+ && superInterfaceSignatures.isEmpty()) {
+ return ClassSignature.noSignature();
+ }
return new ClassSignature(
formalTypeParameters, superClassSignature, superInterfaceSignatures);
}
@@ -346,7 +391,7 @@
private final String genericSignatureString;
InvalidClassSignature(String genericSignatureString) {
- super(EMPTY_TYPE_PARAMS, NO_FIELD_TYPE_SIGNATURE, EMPTY_SUPER_INTERFACES);
+ super(EMPTY_TYPE_PARAMS, null, EMPTY_SUPER_INTERFACES);
this.genericSignatureString = genericSignatureString;
}
@@ -367,12 +412,17 @@
}
@Override
- public ClassSignature visit(GenericSignatureVisitor visitor) {
+ public ClassSignature visit(GenericSignatureVisitor visitor, DexItemFactory factory) {
assert false : "Should not visit an invalid signature";
return this;
}
@Override
+ public void visitWithoutRewrite(GenericSignatureVisitor visitor) {
+ assert false : "Should not visit an invalid signature";
+ }
+
+ @Override
public boolean isInvalid() {
return true;
}
@@ -943,7 +993,7 @@
DexItemFactory factory,
DiagnosticsHandler diagnosticsHandler) {
if (signature == null || signature.isEmpty()) {
- return ClassSignature.NO_CLASS_SIGNATURE;
+ return ClassSignature.noSignature();
}
Parser parser = new Parser(factory);
try {
@@ -951,7 +1001,7 @@
} catch (GenericSignatureFormatError e) {
diagnosticsHandler.warning(
GenericSignatureFormatDiagnostic.invalidClassSignature(signature, className, origin, e));
- return ClassSignature.NO_CLASS_SIGNATURE;
+ return ClassSignature.noSignature();
}
}
@@ -1100,34 +1150,28 @@
private ClassSignature parseClassSignature() {
// ClassSignature ::= FormalTypeParameters? SuperclassSignature SuperinterfaceSignature*.
-
- List<FormalTypeParameter> formalTypeParameters = parseOptFormalTypeParameters();
-
+ ClassSignatureBuilder signatureBuilder = ClassSignature.builder();
+ parseOptFormalTypeParameters(signatureBuilder::addFormalTypeParameter);
// SuperclassSignature ::= ClassTypeSignature.
- ClassTypeSignature superClassSignature = parseClassTypeSignature();
-
- ImmutableList.Builder<ClassTypeSignature> builder = ImmutableList.builder();
+ signatureBuilder.setSuperClassSignature(parseClassTypeSignature());
while (symbol > 0) {
// SuperinterfaceSignature ::= ClassTypeSignature.
- builder.add(parseClassTypeSignature());
+ signatureBuilder.addSuperInterfaceSignature(parseClassTypeSignature());
}
-
- return new ClassSignature(formalTypeParameters, superClassSignature, builder.build());
+ return signatureBuilder.build(factory);
}
- private List<FormalTypeParameter> parseOptFormalTypeParameters() {
+ private void parseOptFormalTypeParameters(Consumer<FormalTypeParameter> consumer) {
// FormalTypeParameters ::= "<" FormalTypeParameter+ ">".
if (symbol != '<') {
- return EMPTY_TYPE_PARAMS;
+ return;
}
scanSymbol();
- ImmutableList.Builder<FormalTypeParameter> builder = ImmutableList.builder();
while ((symbol != '>') && (symbol > 0)) {
- builder.add(updateFormalTypeParameter());
+ consumer.accept(updateFormalTypeParameter());
}
expect('>');
- return builder.build();
}
private FormalTypeParameter updateFormalTypeParameter() {
@@ -1288,7 +1332,8 @@
private MethodTypeSignature parseMethodTypeSignature() {
// MethodTypeSignature ::=
// FormalTypeParameters? "(" TypeSignature* ")" ReturnType ThrowsSignature*.
- List<FormalTypeParameter> formalTypeParameters = parseOptFormalTypeParameters();
+ ImmutableList.Builder<FormalTypeParameter> formalsBuilder = ImmutableList.builder();
+ parseOptFormalTypeParameters(formalsBuilder::add);
expect('(');
@@ -1315,7 +1360,7 @@
}
return new MethodTypeSignature(
- formalTypeParameters,
+ formalsBuilder.build(),
parameterSignatureBuilder.build(),
returnType,
throwsSignatureBuilder.build());
diff --git a/src/main/java/com/android/tools/r8/graph/GenericSignatureCorrectnessHelper.java b/src/main/java/com/android/tools/r8/graph/GenericSignatureCorrectnessHelper.java
index 7864ee8..8bac211 100644
--- a/src/main/java/com/android/tools/r8/graph/GenericSignatureCorrectnessHelper.java
+++ b/src/main/java/com/android/tools/r8/graph/GenericSignatureCorrectnessHelper.java
@@ -250,26 +250,24 @@
return VALID;
}
SignatureEvaluationResult signatureEvaluationResult =
- evaluateFormalTypeParameters(classSignature.formalTypeParameters, typeParameterContext);
+ evaluateFormalTypeParameters(
+ classSignature.getFormalTypeParameters(), typeParameterContext);
if (signatureEvaluationResult.isInvalid()) {
return signatureEvaluationResult;
}
- if (context.superType == appView.dexItemFactory().objectType
- && classSignature.superClassSignature().hasNoSignature()) {
- // We represent no signature as object.
- } else if (context.superType != classSignature.superClassSignature().type()) {
+ ClassTypeSignature superClassSignature =
+ classSignature.getSuperClassSignatureOrObject(appView.dexItemFactory());
+ if (context.superType != superClassSignature.type()) {
assert mode.doNotVerify() : "Super type inconsistency in generic signature";
return INVALID_SUPER_TYPE;
}
signatureEvaluationResult =
evaluateTypeArgumentsAppliedToType(
- classSignature.superClassSignature().typeArguments(),
- context.superType,
- typeParameterContext);
+ superClassSignature.typeArguments(), context.superType, typeParameterContext);
if (signatureEvaluationResult.isInvalid()) {
return signatureEvaluationResult;
}
- List<ClassTypeSignature> superInterfaces = classSignature.superInterfaceSignatures();
+ List<ClassTypeSignature> superInterfaces = classSignature.getSuperInterfaceSignatures();
if (context.interfaces.size() != superInterfaces.size()) {
assert mode.doNotVerify();
return INVALID_INTERFACE_COUNT;
diff --git a/src/main/java/com/android/tools/r8/graph/GenericSignaturePartialTypeArgumentApplier.java b/src/main/java/com/android/tools/r8/graph/GenericSignaturePartialTypeArgumentApplier.java
index 12ca041..503000f 100644
--- a/src/main/java/com/android/tools/r8/graph/GenericSignaturePartialTypeArgumentApplier.java
+++ b/src/main/java/com/android/tools/r8/graph/GenericSignaturePartialTypeArgumentApplier.java
@@ -70,7 +70,7 @@
if (classSignature.hasNoSignature() || classSignature.isInvalid()) {
return classSignature;
}
- return classSignature.visit(this);
+ return classSignature.visit(this, appView.dexItemFactory());
}
@Override
@@ -206,8 +206,11 @@
}
@Override
- public ClassTypeSignature visitSuperClass(ClassTypeSignature classTypeSignature) {
- return classTypeSignature.visit(this);
+ public ClassTypeSignature visitSuperClass(ClassTypeSignature classTypeSignatureOrNullForObject) {
+ if (classTypeSignatureOrNullForObject == null) {
+ return classTypeSignatureOrNullForObject;
+ }
+ return classTypeSignatureOrNullForObject.visit(this);
}
@Override
diff --git a/src/main/java/com/android/tools/r8/graph/GenericSignaturePrinter.java b/src/main/java/com/android/tools/r8/graph/GenericSignaturePrinter.java
index 9d54705..cff0d21 100644
--- a/src/main/java/com/android/tools/r8/graph/GenericSignaturePrinter.java
+++ b/src/main/java/com/android/tools/r8/graph/GenericSignaturePrinter.java
@@ -31,7 +31,8 @@
@Override
public ClassSignature visitClassSignature(ClassSignature classSignature) {
- return classSignature.visit(this);
+ classSignature.visitWithoutRewrite(this);
+ return classSignature;
}
@Override
@@ -108,9 +109,13 @@
}
@Override
- public ClassTypeSignature visitSuperClass(ClassTypeSignature classTypeSignature) {
- printFieldTypeSignature(classTypeSignature, false);
- return classTypeSignature;
+ public ClassTypeSignature visitSuperClass(ClassTypeSignature classTypeSignatureOrNullForObject) {
+ if (classTypeSignatureOrNullForObject == null) {
+ sb.append("Ljava/lang/Object;");
+ } else {
+ printFieldTypeSignature(classTypeSignatureOrNullForObject, false);
+ }
+ return classTypeSignatureOrNullForObject;
}
@Override
diff --git a/src/main/java/com/android/tools/r8/graph/GenericSignatureTypeRewriter.java b/src/main/java/com/android/tools/r8/graph/GenericSignatureTypeRewriter.java
index 7f224bb..cdbc19b 100644
--- a/src/main/java/com/android/tools/r8/graph/GenericSignatureTypeRewriter.java
+++ b/src/main/java/com/android/tools/r8/graph/GenericSignatureTypeRewriter.java
@@ -61,7 +61,7 @@
if (classSignature.hasNoSignature() || classSignature.isInvalid()) {
return classSignature;
}
- return new GenericSignatureRewriter().visitClassSignature(classSignature);
+ return new GenericSignatureRewriter(factory).visitClassSignature(classSignature);
}
public FieldTypeSignature rewrite(FieldTypeSignature fieldTypeSignature) {
@@ -69,7 +69,7 @@
return fieldTypeSignature;
}
FieldTypeSignature rewrittenSignature =
- new GenericSignatureRewriter().visitFieldTypeSignature(fieldTypeSignature);
+ new GenericSignatureRewriter(factory).visitFieldTypeSignature(fieldTypeSignature);
return rewrittenSignature == null ? FieldTypeSignature.noSignature() : rewrittenSignature;
}
@@ -77,20 +77,20 @@
if (methodTypeSignature.hasNoSignature() || methodTypeSignature.isInvalid()) {
return methodTypeSignature;
}
- return new GenericSignatureRewriter().visitMethodSignature(methodTypeSignature);
+ return new GenericSignatureRewriter(factory).visitMethodSignature(methodTypeSignature);
}
private class GenericSignatureRewriter implements GenericSignatureVisitor {
+ private final DexItemFactory factory;
+
+ GenericSignatureRewriter(DexItemFactory factory) {
+ this.factory = factory;
+ }
+
@Override
public ClassSignature visitClassSignature(ClassSignature classSignature) {
- ClassSignature rewritten = classSignature.visit(this);
- if (rewritten.getFormalTypeParameters().isEmpty()
- && rewritten.superInterfaceSignatures.isEmpty()
- && rewritten.superClassSignature.type == factory.objectType) {
- return ClassSignature.noSignature();
- }
- return rewritten;
+ return classSignature.visit(this, factory);
}
@Override
@@ -142,14 +142,12 @@
}
@Override
- public ClassTypeSignature visitSuperClass(ClassTypeSignature classTypeSignature) {
- if (context.superType == factory.objectType) {
- return classTypeSignature.type == factory.objectType
- ? classTypeSignature
- : objectTypeSignature;
+ public ClassTypeSignature visitSuperClass(
+ ClassTypeSignature classTypeSignatureOrNullForObject) {
+ if (classTypeSignatureOrNullForObject == null) {
+ return classTypeSignatureOrNullForObject;
}
- ClassTypeSignature rewritten = classTypeSignature.visit(this);
- return rewritten == null ? objectTypeSignature : rewritten;
+ return classTypeSignatureOrNullForObject.visit(this);
}
@Override
diff --git a/src/main/java/com/android/tools/r8/graph/GenericSignatureTypeVisitor.java b/src/main/java/com/android/tools/r8/graph/GenericSignatureTypeVisitor.java
index a619129..66e9682 100644
--- a/src/main/java/com/android/tools/r8/graph/GenericSignatureTypeVisitor.java
+++ b/src/main/java/com/android/tools/r8/graph/GenericSignatureTypeVisitor.java
@@ -30,7 +30,8 @@
if (classSignature.hasNoSignature()) {
return classSignature;
}
- return classSignature.visit(this);
+ classSignature.visitWithoutRewrite(this);
+ return classSignature;
}
@Override
@@ -87,16 +88,16 @@
}
@Override
- public ClassTypeSignature visitSuperClass(ClassTypeSignature classTypeSignature) {
- return classTypeSignature.visit(this);
+ public ClassTypeSignature visitSuperClass(ClassTypeSignature classTypeSignatureOrNullForObject) {
+ if (classTypeSignatureOrNullForObject == null) {
+ return classTypeSignatureOrNullForObject;
+ }
+ return classTypeSignatureOrNullForObject.visit(this);
}
@Override
public List<ClassTypeSignature> visitSuperInterfaces(
List<ClassTypeSignature> interfaceSignatures) {
- if (interfaceSignatures == null) {
- return null;
- }
interfaceSignatures.forEach(this::visitSuperInterface);
return interfaceSignatures;
}
diff --git a/src/main/java/com/android/tools/r8/graph/GenericSignatureVisitor.java b/src/main/java/com/android/tools/r8/graph/GenericSignatureVisitor.java
index 37b3cbe..4072b82 100644
--- a/src/main/java/com/android/tools/r8/graph/GenericSignatureVisitor.java
+++ b/src/main/java/com/android/tools/r8/graph/GenericSignatureVisitor.java
@@ -49,7 +49,7 @@
throw new Unreachable("Implement if visited");
}
- default ClassTypeSignature visitSuperClass(ClassTypeSignature classTypeSignature) {
+ default ClassTypeSignature visitSuperClass(ClassTypeSignature classTypeSignatureOrNullForObject) {
throw new Unreachable("Implement if visited");
}
diff --git a/src/main/java/com/android/tools/r8/ir/desugar/desugaredlibrary/retargeter/DesugaredLibraryRetargeterPostProcessor.java b/src/main/java/com/android/tools/r8/ir/desugar/desugaredlibrary/retargeter/DesugaredLibraryRetargeterPostProcessor.java
index 98b707f..be8dd14 100644
--- a/src/main/java/com/android/tools/r8/ir/desugar/desugaredlibrary/retargeter/DesugaredLibraryRetargeterPostProcessor.java
+++ b/src/main/java/com/android/tools/r8/ir/desugar/desugaredlibrary/retargeter/DesugaredLibraryRetargeterPostProcessor.java
@@ -128,7 +128,8 @@
continue;
}
clazz.addExtraInterfaces(
- Collections.singletonList(new ClassTypeSignature(newInterface.type)));
+ Collections.singletonList(new ClassTypeSignature(newInterface.type)),
+ appView.dexItemFactory());
eventConsumer.acceptInterfaceInjection(clazz, newInterface);
DexMethod itfMethod =
syntheticHelper.emulatedInterfaceDispatchMethod(newInterface, descriptor);
diff --git a/src/main/java/com/android/tools/r8/ir/desugar/itf/ClassProcessor.java b/src/main/java/com/android/tools/r8/ir/desugar/itf/ClassProcessor.java
index 922fd4d..f69890a 100644
--- a/src/main/java/com/android/tools/r8/ir/desugar/itf/ClassProcessor.java
+++ b/src/main/java/com/android/tools/r8/ir/desugar/itf/ClassProcessor.java
@@ -529,7 +529,7 @@
eventConsumer.acceptEmulatedInterfaceMarkerInterface(
clazz, helper.ensureEmulatedInterfaceMarkerInterface(signature.type()));
}
- clazz.addExtraInterfaces(extraInterfaceSignatures);
+ clazz.addExtraInterfaces(extraInterfaceSignatures, appView.dexItemFactory());
}
});
}
@@ -698,6 +698,7 @@
// TODO(b/182329331): Only handle type arguments for Cf to Cf desugar.
if (appView.options().isCfDesugaring() && clazz.validInterfaceSignatures()) {
clazz.forEachImmediateSupertypeWithSignature(
+ appView.dexItemFactory(),
(type, signature) -> {
if (emulatesInterfaces.contains(type)) {
extraInterfaceSignatures.put(
diff --git a/src/main/java/com/android/tools/r8/ir/desugar/itf/EmulatedInterfaceApplicationRewriter.java b/src/main/java/com/android/tools/r8/ir/desugar/itf/EmulatedInterfaceApplicationRewriter.java
index 47a6d30..d33fcec 100644
--- a/src/main/java/com/android/tools/r8/ir/desugar/itf/EmulatedInterfaceApplicationRewriter.java
+++ b/src/main/java/com/android/tools/r8/ir/desugar/itf/EmulatedInterfaceApplicationRewriter.java
@@ -90,7 +90,7 @@
false,
emulatedInterface.getChecksumSupplier());
newEmulatedInterface.addExtraInterfaces(
- getRewrittenInterfacesOfEmulatedInterface(emulatedInterface));
+ getRewrittenInterfacesOfEmulatedInterface(emulatedInterface), appView.dexItemFactory());
return newEmulatedInterface;
}
@@ -106,7 +106,7 @@
typeArguments = Collections.emptyList();
} else {
GenericSignature.ClassTypeSignature classTypeSignature =
- classSignature.superInterfaceSignatures().get(i);
+ classSignature.getSuperInterfaceSignatures().get(i);
assert itf == classTypeSignature.type();
typeArguments = classTypeSignature.typeArguments();
}
diff --git a/src/main/java/com/android/tools/r8/shaking/VerticalClassMerger.java b/src/main/java/com/android/tools/r8/shaking/VerticalClassMerger.java
index 150e7c8..b1673ba 100644
--- a/src/main/java/com/android/tools/r8/shaking/VerticalClassMerger.java
+++ b/src/main/java/com/android/tools/r8/shaking/VerticalClassMerger.java
@@ -1208,12 +1208,12 @@
builder.addFormalTypeParameters(targetSignature.getFormalTypeParameters());
if (!source.isInterface()) {
if (rewrittenSource.hasSignature()) {
- builder.setSuperClassSignature(rewrittenSource.superClassSignature());
+ builder.setSuperClassSignature(rewrittenSource.getSuperClassSignatureOrNull());
} else {
builder.setSuperClassSignature(new ClassTypeSignature(source.superType));
}
} else {
- builder.setSuperClassSignature(targetSignature.superClassSignature());
+ builder.setSuperClassSignature(targetSignature.getSuperClassSignatureOrNull());
}
// Compute the seen set for interfaces to add. This is similar to the merging of interfaces
// but allow us to maintain the type arguments.
@@ -1221,26 +1221,26 @@
if (source.isInterface()) {
seenInterfaces.add(source.type);
}
- for (ClassTypeSignature iFace : targetSignature.superInterfaceSignatures()) {
+ for (ClassTypeSignature iFace : targetSignature.getSuperInterfaceSignatures()) {
if (seenInterfaces.add(iFace.type())) {
- builder.addInterface(iFace);
+ builder.addSuperInterfaceSignature(iFace);
}
}
if (rewrittenSource.hasSignature()) {
- for (ClassTypeSignature iFace : rewrittenSource.superInterfaceSignatures()) {
+ for (ClassTypeSignature iFace : rewrittenSource.getSuperInterfaceSignatures()) {
if (!seenInterfaces.contains(iFace.type())) {
- builder.addInterface(iFace);
+ builder.addSuperInterfaceSignature(iFace);
}
}
} else {
// Synthesize raw uses of interfaces to align with the actual class
for (DexType iFace : source.interfaces) {
if (!seenInterfaces.contains(iFace)) {
- builder.addInterface(new ClassTypeSignature(iFace));
+ builder.addSuperInterfaceSignature(new ClassTypeSignature(iFace));
}
}
}
- target.setClassSignature(builder.build());
+ target.setClassSignature(builder.build(appView.dexItemFactory()));
// Go through all type-variable references for members and update them.
CollectionUtils.forEach(
@@ -1273,7 +1273,9 @@
// We can assert proper structure below because the generic signature validator has run
// before and pruned invalid signatures.
List<FieldTypeSignature> genericArgumentsToSuperType =
- target.getClassSignature().getGenericArgumentsToSuperType(source.type);
+ target
+ .getClassSignature()
+ .getGenericArgumentsToSuperType(source.type, appView.dexItemFactory());
if (genericArgumentsToSuperType == null) {
assert false : "Type should be present in generic signature";
return null;
diff --git a/src/test/java/com/android/tools/r8/graph/GenericSignatureTest.java b/src/test/java/com/android/tools/r8/graph/GenericSignatureTest.java
index 4c92f65..e0f7e1d 100644
--- a/src/test/java/com/android/tools/r8/graph/GenericSignatureTest.java
+++ b/src/test/java/com/android/tools/r8/graph/GenericSignatureTest.java
@@ -118,8 +118,8 @@
classSignature = clazz.classSignature;
assertNotNull(classSignature);
- assertEquals(1, classSignature.formalTypeParameters.size());
- FormalTypeParameter formalTypeParameter = classSignature.formalTypeParameters.get(0);
+ assertEquals(1, classSignature.getFormalTypeParameters().size());
+ FormalTypeParameter formalTypeParameter = classSignature.getFormalTypeParameters().get(0);
assertEquals("T", formalTypeParameter.name);
assertTrue(formalTypeParameter.interfaceBounds.isEmpty());
assertTrue(formalTypeParameter.classBound.isClassTypeSignature());
@@ -135,8 +135,8 @@
.asTypeVariableSignature()
.typeVariable);
- assertTrue(classSignature.superInterfaceSignatures.isEmpty());
- classTypeSignature = classSignature.superClassSignature;
+ assertTrue(classSignature.getSuperInterfaceSignatures().isEmpty());
+ classTypeSignature = classSignature.getSuperClassSignatureOrNull();
assertEquals(cy.getDexProgramClass().type, classTypeSignature.type);
typeArguments = classTypeSignature.typeArguments;
assertEquals(1, typeArguments.size());