1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19 package org.apache.bcel.classfile;
20
21 import java.io.DataInput;
22 import java.io.DataOutputStream;
23 import java.io.IOException;
24 import java.util.Objects;
25
26 import org.apache.bcel.Const;
27 import org.apache.bcel.util.BCELComparator;
28
29
30
31
32
33 public abstract class Constant implements Cloneable, Node {
34
35 static final Constant[] EMPTY_ARRAY = {};
36
37 private static BCELComparator<Constant> bcelComparator = new BCELComparator<Constant>() {
38
39 @Override
40 public boolean equals(final Constant a, final Constant b) {
41 return a == b || a != null && b != null && Objects.equals(a.toString(), b.toString());
42 }
43
44 @Override
45 public int hashCode(final Constant o) {
46 return o != null ? Objects.hashCode(o.toString()) : 0;
47 }
48 };
49
50
51
52
53 public static BCELComparator<Constant> getComparator() {
54 return bcelComparator;
55 }
56
57
58
59
60
61
62
63
64
65
66 public static Constant readConstant(final DataInput dataInput) throws IOException, ClassFormatException {
67 final byte b = dataInput.readByte();
68 switch (b) {
69 case Const.CONSTANT_Class:
70 return new ConstantClass(dataInput);
71 case Const.CONSTANT_Fieldref:
72 return new ConstantFieldref(dataInput);
73 case Const.CONSTANT_Methodref:
74 return new ConstantMethodref(dataInput);
75 case Const.CONSTANT_InterfaceMethodref:
76 return new ConstantInterfaceMethodref(dataInput);
77 case Const.CONSTANT_String:
78 return new ConstantString(dataInput);
79 case Const.CONSTANT_Integer:
80 return new ConstantInteger(dataInput);
81 case Const.CONSTANT_Float:
82 return new ConstantFloat(dataInput);
83 case Const.CONSTANT_Long:
84 return new ConstantLong(dataInput);
85 case Const.CONSTANT_Double:
86 return new ConstantDouble(dataInput);
87 case Const.CONSTANT_NameAndType:
88 return new ConstantNameAndType(dataInput);
89 case Const.CONSTANT_Utf8:
90 return ConstantUtf8.getInstance(dataInput);
91 case Const.CONSTANT_MethodHandle:
92 return new ConstantMethodHandle(dataInput);
93 case Const.CONSTANT_MethodType:
94 return new ConstantMethodType(dataInput);
95 case Const.CONSTANT_Dynamic:
96 return new ConstantDynamic(dataInput);
97 case Const.CONSTANT_InvokeDynamic:
98 return new ConstantInvokeDynamic(dataInput);
99 case Const.CONSTANT_Module:
100 return new ConstantModule(dataInput);
101 case Const.CONSTANT_Package:
102 return new ConstantPackage(dataInput);
103 default:
104 throw new ClassFormatException("Invalid byte tag in constant pool: " + b);
105 }
106 }
107
108
109
110
111 public static void setComparator(final BCELComparator<Constant> comparator) {
112 bcelComparator = comparator;
113 }
114
115
116
117
118
119
120
121
122
123
124
125 @java.lang.Deprecated
126 protected byte tag;
127
128 Constant(final byte tag) {
129 this.tag = tag;
130 }
131
132
133
134
135
136
137
138 @Override
139 public abstract void accept(Visitor v);
140
141 @Override
142 public Object clone() {
143 try {
144 return super.clone();
145 } catch (final CloneNotSupportedException e) {
146 throw new UnsupportedOperationException("Clone Not Supported", e);
147 }
148 }
149
150
151
152
153 public Constant copy() {
154 try {
155 return (Constant) super.clone();
156 } catch (final CloneNotSupportedException e) {
157
158 }
159 return null;
160 }
161
162 public abstract void dump(DataOutputStream file) throws IOException;
163
164
165
166
167
168
169
170 @Override
171 public boolean equals(final Object obj) {
172 return obj instanceof Constant && bcelComparator.equals(this, (Constant) obj);
173 }
174
175
176
177
178 public final byte getTag() {
179 return tag;
180 }
181
182
183
184
185
186
187
188 @Override
189 public int hashCode() {
190 return bcelComparator.hashCode(this);
191 }
192
193
194
195
196 @Override
197 public String toString() {
198 return Const.getConstantName(tag) + "[" + tag + "]";
199 }
200 }