Refactor ReadKotlinClassHeaderAnnotationVisitor
Extract a hierarchy of four nested classes instead of anonymous
This commit is contained in:
+49
-48
@@ -96,11 +96,11 @@ public class ReadKotlinClassHeaderAnnotationVisitor implements AnnotationVisitor
|
|||||||
|
|
||||||
switch (newKind) {
|
switch (newKind) {
|
||||||
case CLASS:
|
case CLASS:
|
||||||
return kotlinClassOrPackageVisitor(annotation);
|
return new ClassHeaderReader();
|
||||||
case PACKAGE_FACADE:
|
case PACKAGE_FACADE:
|
||||||
return kotlinClassOrPackageVisitor(annotation);
|
return new PackageHeaderReader();
|
||||||
case SYNTHETIC_CLASS:
|
case SYNTHETIC_CLASS:
|
||||||
return syntheticClassAnnotationVisitor();
|
return new SyntheticClassHeaderReader();
|
||||||
default:
|
default:
|
||||||
throw new IllegalStateException("Unknown kind: " + newKind);
|
throw new IllegalStateException("Unknown kind: " + newKind);
|
||||||
}
|
}
|
||||||
@@ -118,17 +118,26 @@ public class ReadKotlinClassHeaderAnnotationVisitor implements AnnotationVisitor
|
|||||||
public void visitEnd() {
|
public void visitEnd() {
|
||||||
}
|
}
|
||||||
|
|
||||||
@NotNull
|
private abstract class HeaderAnnotationArgumentVisitor implements AnnotationArgumentVisitor {
|
||||||
private AnnotationArgumentVisitor kotlinClassOrPackageVisitor(@NotNull final JvmClassName annotationClassName) {
|
protected final JvmClassName annotationClassName;
|
||||||
return new AnnotationArgumentVisitor() {
|
|
||||||
|
public HeaderAnnotationArgumentVisitor(@NotNull JvmClassName annotationClassName) {
|
||||||
|
this.annotationClassName = annotationClassName;
|
||||||
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void visit(@Nullable Name name, @Nullable Object value) {
|
public void visit(@Nullable Name name, @Nullable Object value) {
|
||||||
visitIntValueForSupportedAnnotation(name, value, annotationClassName);
|
if (name != null && name.asString().equals(ABI_VERSION_FIELD_NAME)) {
|
||||||
|
version = value == null ? AbiVersionUtil.INVALID_VERSION : (Integer) value;
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
unexpectedArgument(name);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void visitEnum(@NotNull Name name, @NotNull ClassId enumClassId, @NotNull Name enumEntryName) {
|
public void visitEnum(@NotNull Name name, @NotNull ClassId enumClassId, @NotNull Name enumEntryName) {
|
||||||
unexpectedArgument(name, annotationClassName);
|
unexpectedEnumArgument(name, enumClassId, enumEntryName);
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
@@ -159,7 +168,7 @@ public class ReadKotlinClassHeaderAnnotationVisitor implements AnnotationVisitor
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void visitEnum(@NotNull ClassId enumClassId, @NotNull Name enumEntryName) {
|
public void visitEnum(@NotNull ClassId enumClassId, @NotNull Name enumEntryName) {
|
||||||
unexpectedArgument(null, annotationClassName);
|
unexpectedArgument(null);
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
@@ -170,18 +179,41 @@ public class ReadKotlinClassHeaderAnnotationVisitor implements AnnotationVisitor
|
|||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Nullable
|
||||||
|
protected AnnotationArrayArgumentVisitor unexpectedArgument(@Nullable Name name) {
|
||||||
|
if (isAbiVersionCompatible(version)) {
|
||||||
|
throw new IllegalStateException("Unexpected argument " + name + " for annotation " + annotationClassName);
|
||||||
|
}
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
|
||||||
|
protected void unexpectedEnumArgument(@NotNull Name name, @NotNull ClassId enumClassId, @NotNull Name enumEntryName) {
|
||||||
|
if (isAbiVersionCompatible(version)) {
|
||||||
|
throw new IllegalStateException("Unexpected enum entry for class annotation " + annotationClassName + ": " +
|
||||||
|
name + "=" + enumClassId + "." + enumEntryName);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void visitEnd() {
|
public void visitEnd() {
|
||||||
}
|
}
|
||||||
};
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@NotNull
|
private class ClassHeaderReader extends HeaderAnnotationArgumentVisitor {
|
||||||
private AnnotationArgumentVisitor syntheticClassAnnotationVisitor() {
|
public ClassHeaderReader() {
|
||||||
return new AnnotationArgumentVisitor() {
|
super(KotlinClass.CLASS_NAME);
|
||||||
@Override
|
}
|
||||||
public void visit(@Nullable Name name, @Nullable Object value) {
|
}
|
||||||
visitIntValueForSupportedAnnotation(name, value, KotlinSyntheticClass.CLASS_NAME);
|
|
||||||
|
private class PackageHeaderReader extends HeaderAnnotationArgumentVisitor {
|
||||||
|
public PackageHeaderReader() {
|
||||||
|
super(JvmClassName.byFqNameWithoutInnerClasses(KOTLIN_PACKAGE));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private class SyntheticClassHeaderReader extends HeaderAnnotationArgumentVisitor {
|
||||||
|
public SyntheticClassHeaderReader() {
|
||||||
|
super(KotlinSyntheticClass.CLASS_NAME);
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
@@ -190,41 +222,10 @@ public class ReadKotlinClassHeaderAnnotationVisitor implements AnnotationVisitor
|
|||||||
syntheticClassKind = valueOfOrNull(KotlinSyntheticClass.Kind.class, enumEntryName.asString());
|
syntheticClassKind = valueOfOrNull(KotlinSyntheticClass.Kind.class, enumEntryName.asString());
|
||||||
if (syntheticClassKind != null) return;
|
if (syntheticClassKind != null) return;
|
||||||
}
|
}
|
||||||
if (isAbiVersionCompatible(version)) {
|
unexpectedEnumArgument(name, enumClassId, enumEntryName);
|
||||||
throw new IllegalStateException("Unexpected enum entry for synthetic class annotation: " +
|
|
||||||
name + "=" + enumClassId + "." + enumEntryName);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@Nullable
|
|
||||||
@Override
|
|
||||||
public AnnotationArrayArgumentVisitor visitArray(@NotNull Name name) {
|
|
||||||
return unexpectedArgument(name, KotlinSyntheticClass.CLASS_NAME);
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void visitEnd() {
|
|
||||||
}
|
|
||||||
};
|
|
||||||
}
|
|
||||||
|
|
||||||
private void visitIntValueForSupportedAnnotation(@Nullable Name name, @Nullable Object value, @NotNull JvmClassName className) {
|
|
||||||
if (name != null && name.asString().equals(ABI_VERSION_FIELD_NAME)) {
|
|
||||||
version = value == null ? AbiVersionUtil.INVALID_VERSION : (Integer) value;
|
|
||||||
}
|
|
||||||
else {
|
|
||||||
unexpectedArgument(name, className);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
@Nullable
|
|
||||||
private AnnotationArrayArgumentVisitor unexpectedArgument(@Nullable Name name, @NotNull JvmClassName annotationClassName) {
|
|
||||||
if (isAbiVersionCompatible(version)) {
|
|
||||||
throw new IllegalStateException("Unexpected argument " + name + " for annotation " + annotationClassName);
|
|
||||||
}
|
|
||||||
return null;
|
|
||||||
}
|
|
||||||
|
|
||||||
// This function is needed here because Enum.valueOf() throws exception if there's no such value,
|
// This function is needed here because Enum.valueOf() throws exception if there's no such value,
|
||||||
// but we don't want to fail if we're loading the header with an _incompatible_ ABI version
|
// but we don't want to fail if we're loading the header with an _incompatible_ ABI version
|
||||||
@Nullable
|
@Nullable
|
||||||
|
|||||||
Reference in New Issue
Block a user