1
2
3
4
5
6 package mockit.asm;
7
8 import edu.umd.cs.findbugs.annotations.NonNull;
9 import edu.umd.cs.findbugs.annotations.Nullable;
10
11 import mockit.asm.annotations.AnnotationReader;
12 import mockit.asm.annotations.AnnotationVisitor;
13 import mockit.asm.jvmConstants.Access;
14 import mockit.asm.util.BytecodeReader;
15
16 import org.checkerframework.checker.index.qual.NonNegative;
17
18
19
20
21 public abstract class AnnotatedReader extends BytecodeReader {
22 @NonNull
23 private final AnnotationReader annotationReader = new AnnotationReader(this);
24
25 @NonNegative
26 private int annotationsCodeIndex;
27
28
29
30
31 protected int access;
32
33
34
35
36 @Nullable
37 protected String signature;
38
39 protected AnnotatedReader(@NonNull byte[] code) {
40 super(code);
41 }
42
43 protected AnnotatedReader(@NonNull AnnotatedReader another) {
44 super(another);
45 }
46
47 protected final void readAttributes() {
48 signature = null;
49 annotationsCodeIndex = 0;
50
51 for (int attributeCount = readUnsignedShort(); attributeCount > 0; attributeCount--) {
52 String attributeName = readNonnullUTF8();
53 int codeOffsetToNextAttribute = readInt();
54
55 if ("Signature".equals(attributeName)) {
56 signature = readNonnullUTF8();
57 continue;
58 }
59
60 Boolean outcome = readAttribute(attributeName);
61
62 if (outcome == Boolean.TRUE) {
63 continue;
64 }
65
66 if (outcome == null) {
67
68 switch (attributeName) {
69 case "RuntimeVisibleAnnotations":
70 annotationsCodeIndex = codeIndex;
71 break;
72 case "Deprecated":
73 access = Access.asDeprecated(access);
74 break;
75 case "Synthetic":
76 access = Access.asSynthetic(access);
77 }
78 }
79
80 codeIndex += codeOffsetToNextAttribute;
81 }
82 }
83
84
85
86
87
88
89
90
91
92
93
94
95 @Nullable
96 protected abstract Boolean readAttribute(@NonNull String attributeName);
97
98 protected final void readAnnotations(@NonNull BaseWriter visitor) {
99 if (annotationsCodeIndex > 0) {
100 int previousCodeIndex = codeIndex;
101 codeIndex = annotationsCodeIndex;
102
103 for (int annotationCount = readUnsignedShort(); annotationCount > 0; annotationCount--) {
104 String annotationTypeDesc = readNonnullUTF8();
105 AnnotationVisitor av = visitor.visitAnnotation(annotationTypeDesc);
106 readAnnotationValues(av);
107 }
108
109 codeIndex = previousCodeIndex;
110 }
111 }
112
113 protected final void readAnnotationValues(@Nullable AnnotationVisitor av) {
114 codeIndex = annotationReader.readNamedAnnotationValues(codeIndex, av);
115 }
116 }