KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > proguard > classfile > editor > AttributesEditor


1 /*
2  * ProGuard -- shrinking, optimization, obfuscation, and preverification
3  * of Java bytecode.
4  *
5  * Copyright (c) 2002-2007 Eric Lafortune (eric@graphics.cornell.edu)
6  *
7  * This program is free software; you can redistribute it and/or modify it
8  * under the terms of the GNU General Public License as published by the Free
9  * Software Foundation; either version 2 of the License, or (at your option)
10  * any later version.
11  *
12  * This program is distributed in the hope that it will be useful, but WITHOUT
13  * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
14  * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
15  * more details.
16  *
17  * You should have received a copy of the GNU General Public License along
18  * with this program; if not, write to the Free Software Foundation, Inc.,
19  * 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
20  */

21 package proguard.classfile.editor;
22
23 import proguard.classfile.*;
24 import proguard.classfile.attribute.*;
25 import proguard.classfile.attribute.visitor.*;
26 import proguard.classfile.attribute.annotation.*;
27 import proguard.classfile.instruction.*;
28 import proguard.classfile.instruction.visitor.InstructionVisitor;
29 import proguard.classfile.util.SimplifiedVisitor;
30
31 /**
32  * This class can add and delete attributes to and from classes, fields,
33  * methods, and code attributes. Attributes to be added must be filled out
34  * beforehand, including their references to the constant pool. Existing
35  * attributes of the same type are always replaced.
36  *
37  * @author Eric Lafortune
38  */

39 public class AttributesEditor
40 {
41     /**
42      * Adds the given attribute to the given class.
43      */

44     public void addAttribute(ProgramClass programClass,
45                              Attribute attribute)
46     {
47         // Try to replace an existing attribute.
48
if (!replaceAttribute(programClass,
49                               programClass.u2attributesCount,
50                               programClass.attributes,
51                               attribute))
52         {
53             // Otherwise append the attribute.
54
programClass.attributes =
55                 appendAttribute(programClass.u2attributesCount,
56                                 programClass.attributes,
57                                 attribute);
58
59             programClass.u2attributesCount++;
60         }
61     }
62
63
64     /**
65      * Adds the given attribute to the given field.
66      */

67     public void addAttribute(ProgramClass programClass,
68                              ProgramField programField,
69                              Attribute attribute)
70     {
71         // Try to replace an existing attribute.
72
if (!replaceAttribute(programClass,
73                               programField.u2attributesCount,
74                               programField.attributes,
75                               attribute))
76         {
77             // Otherwise append the attribute.
78
programField.attributes =
79                 appendAttribute(programField.u2attributesCount,
80                                 programField.attributes,
81                                 attribute);
82
83             programField.u2attributesCount++;
84         }
85     }
86
87
88     /**
89      * Adds the given attribute to the given method.
90      */

91     public void addAttribute(ProgramClass programClass,
92                              ProgramMethod programMethod,
93                              Attribute attribute)
94     {
95         // Try to replace an existing attribute.
96
if (!replaceAttribute(programClass,
97                               programMethod.u2attributesCount,
98                               programMethod.attributes,
99                               attribute))
100         {
101             // Otherwise append the attribute.
102
programMethod.attributes =
103                 appendAttribute(programMethod.u2attributesCount,
104                                 programMethod.attributes,
105                                 attribute);
106
107             programMethod.u2attributesCount++;
108         }
109     }
110
111
112     /**
113      * Adds the given attribute to the given code attribute.
114      */

115     public void addAttribute(ProgramClass programClass,
116                              ProgramMethod programMethod,
117                              CodeAttribute codeAttribute,
118                              Attribute attribute)
119     {
120         // Try to replace an existing attribute.
121
if (!replaceAttribute(programClass,
122                               codeAttribute.u2attributesCount,
123                               codeAttribute.attributes,
124                               attribute))
125         {
126             // Otherwise append the attribute.
127
codeAttribute.attributes =
128                 appendAttribute(codeAttribute.u2attributesCount,
129                                 codeAttribute.attributes,
130                                 attribute);
131
132             codeAttribute.u2attributesCount++;
133         }
134     }
135
136
137     /**
138      * Deletes the given attribute from the given class.
139      */

140     public void deleteAttribute(ProgramClass programClass,
141                                 String JavaDoc attributeName)
142     {
143         programClass.u2attributesCount =
144             deleteAttribute(programClass,
145                             programClass.u2attributesCount,
146                             programClass.attributes,
147                             attributeName);
148     }
149
150
151     /**
152      * Deletes the given attribute from the given field.
153      */

154     public void deleteAttribute(ProgramClass programClass,
155                                 ProgramField programField,
156                                 String JavaDoc attributeName)
157     {
158         programField.u2attributesCount =
159             deleteAttribute(programClass,
160                             programField.u2attributesCount,
161                             programField.attributes,
162                             attributeName);
163     }
164
165
166     /**
167      * Deletes the given attribute from the given method.
168      */

169     public void deleteAttribute(ProgramClass programClass,
170                                 ProgramMethod programMethod,
171                                 String JavaDoc attributeName)
172     {
173         programMethod.u2attributesCount =
174             deleteAttribute(programClass,
175                             programMethod.u2attributesCount,
176                             programMethod.attributes,
177                             attributeName);
178     }
179
180
181     /**
182      * Deletes the given attribute from the given code attribute.
183      */

184     public void deleteAttribute(ProgramClass programClass,
185                                 ProgramMethod programMethod,
186                                 CodeAttribute codeAttribute,
187                                 String JavaDoc attributeName)
188     {
189         codeAttribute.u2attributesCount =
190             deleteAttribute(programClass,
191                             codeAttribute.u2attributesCount,
192                             codeAttribute.attributes,
193                             attributeName);
194     }
195
196
197     // Small utility methods.
198

199     /**
200      * Tries put the given attribute in place of an existing attribute of
201      * the same type.
202      */

203     private boolean replaceAttribute(Clazz clazz,
204                                      int attributesCount,
205                                      Attribute[] attributes,
206                                      Attribute attribute)
207     {
208         String JavaDoc attributeName = attribute.getAttributeName(clazz);
209
210         for (int index = 0; index < attributesCount; index++)
211         {
212             if (attributes[index].getAttributeName(clazz).equals(attributeName))
213             {
214                 attributes[index] = attribute;
215                 return true;
216             }
217         }
218
219         return false;
220     }
221
222
223     /**
224      * Appends the given attribute to the given array of attributes, creating
225      * a new array if necessary.
226      */

227     private Attribute[] appendAttribute(int attributesCount,
228                                         Attribute[] attributes,
229                                         Attribute attribute)
230     {
231         // Is the array too small to contain the additional attribute?
232
if (attributes.length <= attributesCount)
233         {
234             // Create a new array and copy the attributes into it.
235
Attribute[] newAttributes = new Attribute[attributesCount + 1];
236             System.arraycopy(attributes, 0, newAttributes, 0, attributesCount);
237             attributes = newAttributes;
238         }
239
240         // Append the attribute.
241
attributes[attributesCount] = attribute;
242
243         return attributes;
244     }
245
246
247     /**
248      * Deletes attributes with the given name, and returns the new number of
249      * attributes.
250      */

251     private int deleteAttribute(Clazz clazz,
252                                 int attributesCount,
253                                 Attribute[] attributes,
254                                 String JavaDoc attributeName)
255     {
256         int newIndex = 0;
257
258         // Shift the other attributes in the array.
259
for (int index = 0; index < attributesCount; index++)
260         {
261             if (!attributes[index].getAttributeName(clazz).equals(attributeName))
262             {
263                 attributes[newIndex++] = attributes[index];
264             }
265         }
266
267         // Clear the remaining entries in the array.
268
for (int index = newIndex; index < attributesCount; index++)
269         {
270             attributes[index] = null;
271         }
272
273         return newIndex;
274     }
275 }
276
Popular Tags