16 * distributed under the License is distributed on an "AS IS" BASIS, |
15 * distributed under the License is distributed on an "AS IS" BASIS, |
17 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. |
16 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. |
18 * See the License for the specific language governing permissions and |
17 * See the License for the specific language governing permissions and |
19 * limitations under the License. |
18 * limitations under the License. |
20 */ |
19 */ |
21 |
|
22 package com.sun.org.apache.bcel.internal.classfile; |
20 package com.sun.org.apache.bcel.internal.classfile; |
23 |
21 |
24 import com.sun.org.apache.bcel.internal.Constants; |
22 import java.io.DataInput; |
25 import java.io.*; |
23 import java.io.DataInputStream; |
|
24 import java.io.DataOutputStream; |
|
25 import java.io.IOException; |
|
26 |
|
27 import com.sun.org.apache.bcel.internal.Const; |
26 |
28 |
27 /** |
29 /** |
28 * Abstract super class for fields and methods. |
30 * Abstract super class for fields and methods. |
29 * |
31 * |
30 * @author <A HREF="mailto:markus.dahm@berlin.de">M. Dahm</A> |
32 * @version $Id: FieldOrMethod.java 1750029 2016-06-23 22:14:38Z sebb $ |
31 */ |
33 */ |
32 public abstract class FieldOrMethod extends AccessFlags implements Cloneable, Node { |
34 public abstract class FieldOrMethod extends AccessFlags implements Cloneable, Node { |
33 protected int name_index; // Points to field name in constant pool |
35 private int name_index; // Points to field name in constant pool |
34 protected int signature_index; // Points to encoded signature |
36 private int signature_index; // Points to encoded signature |
35 protected int attributes_count;// No. of attributes |
37 private Attribute[] attributes; // Collection of attributes |
36 protected Attribute[] attributes; // Collection of attributes |
38 private int attributes_count; // No. of attributes |
37 protected ConstantPool constant_pool; |
39 |
38 |
40 // @since 6.0 |
39 FieldOrMethod() {} |
41 private AnnotationEntry[] annotationEntries; // annotations defined on the field or method |
40 |
42 |
41 /** |
43 private ConstantPool constant_pool; |
42 * Initialize from another object. Note that both objects use the same |
44 |
43 * references (shallow copy). Use clone() for a physical copy. |
45 private String signatureAttributeString = null; |
44 */ |
46 private boolean searchedForSignatureAttribute = false; |
45 protected FieldOrMethod(FieldOrMethod c) { |
47 |
46 this(c.getAccessFlags(), c.getNameIndex(), c.getSignatureIndex(), |
48 FieldOrMethod() { |
47 c.getAttributes(), c.getConstantPool()); |
49 } |
48 } |
50 |
49 |
51 /** |
50 /** |
52 * Initialize from another object. Note that both objects use the same |
51 * Construct object from file stream. |
53 * references (shallow copy). Use clone() for a physical copy. |
52 * @param file Input stream |
54 */ |
53 * @throws IOException |
55 protected FieldOrMethod(final FieldOrMethod c) { |
54 * @throws ClassFormatException |
56 this(c.getAccessFlags(), c.getNameIndex(), c.getSignatureIndex(), |
55 */ |
57 c.getAttributes(), c.getConstantPool()); |
56 protected FieldOrMethod(DataInputStream file, ConstantPool constant_pool) |
58 } |
57 throws IOException, ClassFormatException |
59 |
58 { |
60 /** |
59 this(file.readUnsignedShort(), file.readUnsignedShort(), |
61 * Construct object from file stream. |
60 file.readUnsignedShort(), null, constant_pool); |
62 * |
61 |
63 * @param file Input stream |
62 attributes_count = file.readUnsignedShort(); |
64 * @throws IOException |
63 attributes = new Attribute[attributes_count]; |
65 * @throws ClassFormatException |
64 for(int i=0; i < attributes_count; i++) |
66 * @deprecated (6.0) Use |
65 attributes[i] = Attribute.readAttribute(file, constant_pool); |
67 * {@link #FieldOrMethod(java.io.DataInput, ConstantPool)} instead. |
66 } |
68 */ |
67 |
69 @java.lang.Deprecated |
68 /** |
70 protected FieldOrMethod(final DataInputStream file, |
69 * @param access_flags Access rights of method |
71 final ConstantPool constant_pool) throws IOException, |
70 * @param name_index Points to field name in constant pool |
72 ClassFormatException { |
71 * @param signature_index Points to encoded signature |
73 this((DataInput) file, constant_pool); |
72 * @param attributes Collection of attributes |
74 } |
73 * @param constant_pool Array of constants |
75 |
74 */ |
76 /** |
75 protected FieldOrMethod(int access_flags, int name_index, int signature_index, |
77 * Construct object from file stream. |
76 Attribute[] attributes, ConstantPool constant_pool) |
78 * |
77 { |
79 * @param file Input stream |
78 this.access_flags = access_flags; |
80 * @throws IOException |
79 this.name_index = name_index; |
81 * @throws ClassFormatException |
80 this.signature_index = signature_index; |
82 */ |
81 this.constant_pool = constant_pool; |
83 protected FieldOrMethod(final DataInput file, |
82 |
84 final ConstantPool constant_pool) throws IOException, ClassFormatException { |
83 setAttributes(attributes); |
85 this(file.readUnsignedShort(), file.readUnsignedShort(), file.readUnsignedShort(), null, |
84 } |
86 constant_pool); |
85 |
87 attributes_count = file.readUnsignedShort(); |
86 /** |
88 attributes = new Attribute[attributes_count]; |
87 * Dump object to file stream on binary format. |
89 for (int i = 0; i < attributes_count; i++) { |
88 * |
90 attributes[i] = Attribute.readAttribute(file, constant_pool); |
89 * @param file Output file stream |
91 } |
90 * @throws IOException |
92 } |
91 */ |
93 |
92 public final void dump(DataOutputStream file) throws IOException |
94 /** |
93 { |
95 * @param access_flags Access rights of method |
94 file.writeShort(access_flags); |
96 * @param name_index Points to field name in constant pool |
95 file.writeShort(name_index); |
97 * @param signature_index Points to encoded signature |
96 file.writeShort(signature_index); |
98 * @param attributes Collection of attributes |
97 file.writeShort(attributes_count); |
99 * @param constant_pool Array of constants |
98 |
100 */ |
99 for(int i=0; i < attributes_count; i++) |
101 protected FieldOrMethod(final int access_flags, final int name_index, final int signature_index, |
100 attributes[i].dump(file); |
102 final Attribute[] attributes, final ConstantPool constant_pool) { |
101 } |
103 super(access_flags); |
102 |
104 this.name_index = name_index; |
103 /** |
105 this.signature_index = signature_index; |
104 * @return Collection of object attributes. |
106 this.constant_pool = constant_pool; |
105 */ |
107 setAttributes(attributes); |
106 public final Attribute[] getAttributes() { return attributes; } |
108 } |
107 |
109 |
108 /** |
110 /** |
109 * @param attributes Collection of object attributes. |
111 * Dump object to file stream on binary format. |
110 */ |
112 * |
111 public final void setAttributes(Attribute[] attributes) { |
113 * @param file Output file stream |
112 this.attributes = attributes; |
114 * @throws IOException |
113 attributes_count = (attributes == null)? 0 : attributes.length; |
115 */ |
114 } |
116 public final void dump(final DataOutputStream file) throws IOException { |
115 |
117 file.writeShort(super.getAccessFlags()); |
116 /** |
118 file.writeShort(name_index); |
117 * @return Constant pool used by this object. |
119 file.writeShort(signature_index); |
118 */ |
120 file.writeShort(attributes_count); |
119 public final ConstantPool getConstantPool() { return constant_pool; } |
121 |
120 |
122 for(int i=0; i < attributes_count; i++) { |
121 /** |
123 attributes[i].dump(file); |
122 * @param constant_pool Constant pool to be used for this object. |
124 } |
123 */ |
125 } |
124 public final void setConstantPool(ConstantPool constant_pool) { |
126 |
125 this.constant_pool = constant_pool; |
127 /** |
126 } |
128 * @return Collection of object attributes. |
127 |
129 */ |
128 /** |
130 public final Attribute[] getAttributes() { |
129 * @return Index in constant pool of object's name. |
131 return attributes; |
130 */ |
132 } |
131 public final int getNameIndex() { return name_index; } |
133 |
132 |
134 /** |
133 /** |
135 * @param attributes Collection of object attributes. |
134 * @param name_index Index in constant pool of object's name. |
136 */ |
135 */ |
137 public final void setAttributes(final Attribute[] attributes) { |
136 public final void setNameIndex(int name_index) { |
138 this.attributes = attributes; |
137 this.name_index = name_index; |
139 this.attributes_count = attributes != null ? attributes.length : 0; |
138 } |
140 } |
139 |
141 |
140 /** |
142 /** |
141 * @return Index in constant pool of field signature. |
143 * @return Constant pool used by this object. |
142 */ |
144 */ |
143 public final int getSignatureIndex() { return signature_index; } |
145 public final ConstantPool getConstantPool() { |
144 |
146 return constant_pool; |
145 /** |
147 } |
146 * @param signature_index Index in constant pool of field signature. |
148 |
147 */ |
149 /** |
148 public final void setSignatureIndex(int signature_index) { |
150 * @param constant_pool Constant pool to be used for this object. |
149 this.signature_index = signature_index; |
151 */ |
150 } |
152 public final void setConstantPool(final ConstantPool constant_pool) { |
151 |
153 this.constant_pool = constant_pool; |
152 /** |
154 } |
153 * @return Name of object, i.e., method name or field name |
155 |
154 */ |
156 /** |
155 public final String getName() { |
157 * @return Index in constant pool of object's name. |
156 ConstantUtf8 c; |
158 */ |
157 c = (ConstantUtf8)constant_pool.getConstant(name_index, |
159 public final int getNameIndex() { |
158 Constants.CONSTANT_Utf8); |
160 return name_index; |
159 return c.getBytes(); |
161 } |
160 } |
162 |
161 |
163 /** |
162 /** |
164 * @param name_index Index in constant pool of object's name. |
163 * @return String representation of object's type signature (java style) |
165 */ |
164 */ |
166 public final void setNameIndex(final int name_index) { |
165 public final String getSignature() { |
167 this.name_index = name_index; |
166 ConstantUtf8 c; |
168 } |
167 c = (ConstantUtf8)constant_pool.getConstant(signature_index, |
169 |
168 Constants.CONSTANT_Utf8); |
170 /** |
169 return c.getBytes(); |
171 * @return Index in constant pool of field signature. |
170 } |
172 */ |
171 |
173 public final int getSignatureIndex() { |
172 /** |
174 return signature_index; |
173 * @return deep copy of this field |
175 } |
174 */ |
176 |
175 protected FieldOrMethod copy_(ConstantPool constant_pool) { |
177 /** |
176 FieldOrMethod c = null; |
178 * @param signature_index Index in constant pool of field signature. |
177 |
179 */ |
178 try { |
180 public final void setSignatureIndex(final int signature_index) { |
179 c = (FieldOrMethod)clone(); |
181 this.signature_index = signature_index; |
180 } catch(CloneNotSupportedException e) {} |
182 } |
181 |
183 |
182 c.constant_pool = constant_pool; |
184 /** |
183 c.attributes = new Attribute[attributes_count]; |
185 * @return Name of object, i.e., method name or field name |
184 |
186 */ |
185 for(int i=0; i < attributes_count; i++) |
187 public final String getName() { |
186 c.attributes[i] = attributes[i].copy(constant_pool); |
188 ConstantUtf8 c; |
187 |
189 c = (ConstantUtf8) constant_pool.getConstant(name_index, Const.CONSTANT_Utf8); |
188 return c; |
190 return c.getBytes(); |
189 } |
191 } |
|
192 |
|
193 /** |
|
194 * @return String representation of object's type signature (java style) |
|
195 */ |
|
196 public final String getSignature() { |
|
197 ConstantUtf8 c; |
|
198 c = (ConstantUtf8) constant_pool.getConstant(signature_index, Const.CONSTANT_Utf8); |
|
199 return c.getBytes(); |
|
200 } |
|
201 |
|
202 /** |
|
203 * @return deep copy of this field |
|
204 */ |
|
205 protected FieldOrMethod copy_(final ConstantPool _constant_pool) { |
|
206 FieldOrMethod c = null; |
|
207 |
|
208 try { |
|
209 c = (FieldOrMethod) clone(); |
|
210 } catch (final CloneNotSupportedException e) { |
|
211 // ignored, but will cause NPE ... |
|
212 } |
|
213 |
|
214 c.constant_pool = constant_pool; |
|
215 c.attributes = new Attribute[attributes_count]; |
|
216 c.attributes_count = attributes_count; |
|
217 |
|
218 for (int i = 0; i < attributes_count; i++) { |
|
219 c.attributes[i] = attributes[i].copy(constant_pool); |
|
220 } |
|
221 |
|
222 return c; |
|
223 } |
|
224 |
|
225 /** |
|
226 * @return Annotations on the field or method |
|
227 * @since 6.0 |
|
228 */ |
|
229 public AnnotationEntry[] getAnnotationEntries() { |
|
230 if (annotationEntries == null) { |
|
231 annotationEntries = AnnotationEntry.createAnnotationEntries(getAttributes()); |
|
232 } |
|
233 |
|
234 return annotationEntries; |
|
235 } |
|
236 |
|
237 /** |
|
238 * Hunts for a signature attribute on the member and returns its contents. |
|
239 * So where the 'regular' signature may be (Ljava/util/Vector;)V the |
|
240 * signature attribute may in fact say |
|
241 * 'Ljava/lang/Vector<Ljava/lang/String>;' Coded for performance - |
|
242 * searches for the attribute only when requested - only searches for it |
|
243 * once. |
|
244 * |
|
245 * @since 6.0 |
|
246 */ |
|
247 public final String getGenericSignature() { |
|
248 if (!searchedForSignatureAttribute) { |
|
249 boolean found = false; |
|
250 for (int i = 0; !found && i < attributes.length; i++) { |
|
251 if (attributes[i] instanceof Signature) { |
|
252 signatureAttributeString = ((Signature) attributes[i]) |
|
253 .getSignature(); |
|
254 found = true; |
|
255 } |
|
256 } |
|
257 searchedForSignatureAttribute = true; |
|
258 } |
|
259 return signatureAttributeString; |
|
260 } |
190 } |
261 } |