KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > javassist > bytecode > InnerClassesAttribute


1 /*
2  * Javassist, a Java-bytecode translator toolkit.
3  * Copyright (C) 1999-2005 Shigeru Chiba. All Rights Reserved.
4  *
5  * The contents of this file are subject to the Mozilla Public License Version
6  * 1.1 (the "License"); you may not use this file except in compliance with
7  * the License. Alternatively, the contents of this file may be used under
8  * the terms of the GNU Lesser General Public License Version 2.1 or later.
9  *
10  * Software distributed under the License is distributed on an "AS IS" basis,
11  * WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
12  * for the specific language governing rights and limitations under the
13  * License.
14  */

15
16 package javassist.bytecode;
17
18 import java.io.DataInputStream JavaDoc;
19 import java.util.Map JavaDoc;
20 import java.io.IOException JavaDoc;
21
22 /**
23  * <code>InnerClasses_attribute</code>.
24  */

25 public class InnerClassesAttribute extends AttributeInfo {
26     /**
27      * The name of this attribute <code>"InnerClasses"</code>.
28      */

29     public static final String JavaDoc tag = "InnerClasses";
30
31     InnerClassesAttribute(ConstPool cp, int n, DataInputStream JavaDoc in)
32         throws IOException JavaDoc
33     {
34         super(cp, n, in);
35     }
36
37     private InnerClassesAttribute(ConstPool cp, byte[] info) {
38         super(cp, tag, info);
39     }
40
41     /**
42      * Constructs an empty InnerClasses attribute.
43      *
44      * @see #append(String, String, String, int)
45      */

46     public InnerClassesAttribute(ConstPool cp) {
47         super(cp, tag, new byte[2]);
48         ByteArray.write16bit(0, get(), 0);
49     }
50
51     /**
52      * Returns <code>number_of_classes</code>.
53      */

54     public int tableLength() { return ByteArray.readU16bit(get(), 0); }
55
56     /**
57      * Returns <code>classes[nth].inner_class_info_index</code>.
58      */

59     public int innerClassIndex(int nth) {
60         return ByteArray.readU16bit(get(), nth * 8 + 2);
61     }
62
63     /**
64      * Returns the class name indicated
65      * by <code>classes[nth].inner_class_info_index</code>.
66      *
67      * @return null or the class name.
68      */

69     public String JavaDoc innerClass(int nth) {
70         int i = innerClassIndex(nth);
71         if (i == 0)
72             return null;
73         else
74             return constPool.getClassInfo(i);
75     }
76
77     /**
78      * Sets <code>classes[nth].inner_class_info_index</code> to
79      * the given index.
80      */

81     public void setInnerClassIndex(int nth, int index) {
82         ByteArray.write16bit(index, get(), nth * 8 + 2);
83     }
84
85     /**
86      * Returns <code>classes[nth].outer_class_info_index</code>.
87      */

88     public int outerClassIndex(int nth) {
89         return ByteArray.readU16bit(get(), nth * 8 + 4);
90     }
91
92     /**
93      * Returns the class name indicated
94      * by <code>classes[nth].outer_class_info_index</code>.
95      *
96      * @return null or the class name.
97      */

98     public String JavaDoc outerClass(int nth) {
99         int i = outerClassIndex(nth);
100         if (i == 0)
101             return null;
102         else
103             return constPool.getClassInfo(i);
104     }
105
106     /**
107      * Sets <code>classes[nth].outer_class_info_index</code> to
108      * the given index.
109      */

110     public void setOuterClassIndex(int nth, int index) {
111         ByteArray.write16bit(index, get(), nth * 8 + 4);
112     }
113
114     /**
115      * Returns <code>classes[nth].inner_name_index</code>.
116      */

117     public int innerNameIndex(int nth) {
118         return ByteArray.readU16bit(get(), nth * 8 + 6);
119     }
120
121     /**
122      * Returns the simple class name indicated
123      * by <code>classes[nth].inner_name_index</code>.
124      *
125      * @return null or the class name.
126      */

127     public String JavaDoc innerName(int nth) {
128         int i = innerNameIndex(nth);
129         if (i == 0)
130             return null;
131         else
132             return constPool.getUtf8Info(i);
133     }
134
135     /**
136      * Sets <code>classes[nth].inner_name_index</code> to
137      * the given index.
138      */

139     public void setInnerNameIndex(int nth, int index) {
140         ByteArray.write16bit(index, get(), nth * 8 + 6);
141     }
142
143     /**
144      * Returns <code>classes[nth].inner_class_access_flags</code>.
145      */

146     public int accessFlags(int nth) {
147         return ByteArray.readU16bit(get(), nth * 8 + 8);
148     }
149
150     /**
151      * Sets <code>classes[nth].inner_class_access_flags</code> to
152      * the given index.
153      */

154     public void setAccessFlags(int nth, int flags) {
155         ByteArray.write16bit(flags, get(), nth * 8 + 8);
156     }
157
158     /**
159      * Appends a new entry.
160      *
161      * @param inner <code>inner_class_info_index</code>
162      * @param outer <code>outer_class_info_index</code>
163      * @param name <code>inner_name_index</code>
164      * @param flags <code>inner_class_access_flags</code>
165      */

166     public void append(String JavaDoc inner, String JavaDoc outer, String JavaDoc name, int flags) {
167         int i = constPool.addClassInfo(inner);
168         int o = constPool.addClassInfo(outer);
169         int n = constPool.addUtf8Info(name);
170         append(i, o, n, flags);
171     }
172
173     /**
174      * Appends a new entry.
175      *
176      * @param inner <code>inner_class_info_index</code>
177      * @param outer <code>outer_class_info_index</code>
178      * @param name <code>inner_name_index</code>
179      * @param flags <code>inner_class_access_flags</code>
180      */

181     public void append(int inner, int outer, int name, int flags) {
182         byte[] data = get();
183         int len = data.length;
184         byte[] newData = new byte[len + 8];
185         for (int i = 2; i < len; ++i)
186             newData[i] = data[i];
187
188         int n = ByteArray.readU16bit(data, 0);
189         ByteArray.write16bit(n + 1, newData, 0);
190
191         ByteArray.write16bit(inner, newData, len);
192         ByteArray.write16bit(outer, newData, len + 2);
193         ByteArray.write16bit(name, newData, len + 4);
194         ByteArray.write16bit(flags, newData, len + 6);
195
196         set(newData);
197     }
198
199     /**
200      * Makes a copy. Class names are replaced according to the
201      * given <code>Map</code> object.
202      *
203      * @param newCp the constant pool table used by the new copy.
204      * @param classnames pairs of replaced and substituted
205      * class names.
206      */

207     public AttributeInfo copy(ConstPool newCp, Map JavaDoc classnames) {
208         byte[] src = get();
209         byte[] dest = new byte[src.length];
210         ConstPool cp = getConstPool();
211         InnerClassesAttribute attr = new InnerClassesAttribute(newCp, dest);
212         int n = ByteArray.readU16bit(src, 0);
213         ByteArray.write16bit(n, dest, 0);
214         int j = 2;
215         for (int i = 0; i < n; ++i) {
216             int innerClass = ByteArray.readU16bit(src, j);
217             int outerClass = ByteArray.readU16bit(src, j + 2);
218             int innerName = ByteArray.readU16bit(src, j + 4);
219             int innerAccess = ByteArray.readU16bit(src, j + 6);
220
221             if (innerClass != 0)
222                 innerClass = cp.copy(innerClass, newCp, classnames);
223
224             ByteArray.write16bit(innerClass, dest, j);
225
226             if (outerClass != 0)
227                 outerClass = cp.copy(outerClass, newCp, classnames);
228
229             ByteArray.write16bit(outerClass, dest, j + 2);
230
231             if (innerName != 0)
232                 innerName = cp.copy(innerName, newCp, classnames);
233
234             ByteArray.write16bit(innerName, dest, j + 4);
235             ByteArray.write16bit(innerAccess, dest, j + 6);
236             j += 8;
237         }
238
239         return attr;
240     }
241 }
242
Popular Tags