KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > com > tc > object > bytecode > ChangeClassNameHierarchyAdapter


1 /*
2  * All content copyright (c) 2003-2006 Terracotta, Inc., except as may otherwise be noted in a separate copyright notice. All rights reserved.
3  */

4 package com.tc.object.bytecode;
5
6 import com.tc.asm.ClassAdapter;
7 import com.tc.asm.ClassVisitor;
8 import com.tc.asm.MethodVisitor;
9 import com.tc.asm.Opcodes;
10 import com.tc.asm.Type;
11
12 import java.util.HashMap JavaDoc;
13 import java.util.Map JavaDoc;
14
15 /**
16  * This class will change the class name in methodInsn.
17  */

18 public abstract class ChangeClassNameHierarchyAdapter extends ClassAdapter implements Opcodes {
19   public final static char DOT_DELIMITER = '.';
20   public final static char SLASH_DELIMITER = '/';
21   final static String JavaDoc CLASS_DELIMITER = ";";
22   final static String JavaDoc CLASS_START_CHAR = "L";
23   final static String JavaDoc CLASS_START_DESC_CHAR = "(L";
24   final static String JavaDoc CLASS_RETURN_DESC_CHAR = ")L";
25   final static String JavaDoc CLASS_ARRAY_DESC_CHAR = "[L";
26   
27   ChangeContext addNewContextIfNotExist(String JavaDoc fullClassNameSlashes, String JavaDoc convertedFullClassNameSlashes, Map JavaDoc instrumentedContext) {
28     ChangeContext changeContext = (ChangeContext)instrumentedContext.get(fullClassNameSlashes);
29     if (changeContext == null) {
30       changeContext = new ChangeContext(fullClassNameSlashes, convertedFullClassNameSlashes);
31       instrumentedContext.put(fullClassNameSlashes, changeContext);
32     } else if (!convertedFullClassNameSlashes.equals(fullClassNameSlashes) &&
33                !convertedFullClassNameSlashes.equals(changeContext.convertedClassNameSlashes)) {
34       changeContext.convertedClassNameSlashes = convertedFullClassNameSlashes;
35     }
36     return changeContext;
37   }
38   
39   ChangeContext addNewContext(String JavaDoc fullClassNameSlashes, String JavaDoc convertedFullClassNameSlashes, Map JavaDoc instrumentedContext) {
40     ChangeContext changeContext = new ChangeContext(fullClassNameSlashes, convertedFullClassNameSlashes);
41     instrumentedContext.put(fullClassNameSlashes, changeContext);
42
43     return changeContext;
44   }
45   
46   ModifiedMethodInfo getModifiedMethodInfo(ChangeContext changeContext, String JavaDoc methodName, String JavaDoc desc) {
47     if (changeContext == null) { return null; }
48     
49     ModifiedMethodInfo methodInfo = (ModifiedMethodInfo)changeContext.modifiedMethodInfo.get(methodName+desc);
50     if (methodInfo != null && methodName.equals(methodInfo.methodName) && desc.equals(methodInfo.originalMethodDesc)) { return methodInfo; }
51     return null;
52   }
53   
54   String JavaDoc getConvertedMethodDesc(Map JavaDoc instrumentedContext, String JavaDoc fullClassNameSlashes, String JavaDoc methodName, String JavaDoc methodDesc) {
55     ChangeContext context = (ChangeContext)instrumentedContext.get(fullClassNameSlashes);
56     while (context != null) {
57       ModifiedMethodInfo methodInfo = getModifiedMethodInfo(context, methodName, methodDesc);
58       if (methodInfo != null) {
59         return methodInfo.convertedMethodDesc;
60       }
61       String JavaDoc superClassName = context.originalSuperClassNameSlashes;
62       if (superClassName != null) {
63         context = (ChangeContext)instrumentedContext.get(superClassName);
64       } else {
65         context = null;
66       }
67     }
68     return null;
69   }
70
71   static class ChangeContext {
72     final String JavaDoc originalClassNameSlashes;
73     String JavaDoc convertedClassNameSlashes;
74     String JavaDoc originalSuperClassNameSlashes;
75
76     final Map JavaDoc modifiedMethodInfo = new HashMap JavaDoc();
77     final Map JavaDoc modifiedFieldInfo = new HashMap JavaDoc();
78
79     public ChangeContext(String JavaDoc originalClassNameSlashes, String JavaDoc convertedClassNameSlashes) {
80       this.originalClassNameSlashes = originalClassNameSlashes;
81       this.convertedClassNameSlashes = convertedClassNameSlashes;
82     }
83     
84     public void setOriginalSuperClass(String JavaDoc superClassNameSlashes) {
85       this.originalSuperClassNameSlashes = superClassNameSlashes;
86     }
87
88     void addModifiedMethodInfo(String JavaDoc name, String JavaDoc originalDesc, String JavaDoc convertedDesc, String JavaDoc signature,
89                                String JavaDoc convertedSignature) {
90       ModifiedMethodInfo methodInfo = (ModifiedMethodInfo)modifiedMethodInfo.get(name+originalDesc);
91       if (methodInfo == null) {
92         modifiedMethodInfo.put(name+originalDesc, new ModifiedMethodInfo(name, originalDesc, convertedDesc, signature, convertedSignature));
93       } else {
94         if (!convertedDesc.equals(methodInfo.convertedMethodDesc)) {
95           methodInfo.convertedMethodDesc = convertedDesc;
96         }
97         if (signature != null && !signature.equals(methodInfo.originalSignature)) {
98           methodInfo.originalSignature = signature;
99         }
100         if (convertedSignature != null && !convertedSignature.equals(methodInfo.convertedSignature)) {
101           methodInfo.convertedSignature = signature;
102         }
103       }
104     }
105
106     void addModifiedFieldInfo(String JavaDoc name, String JavaDoc originalDesc, String JavaDoc convertedDesc, String JavaDoc signature,
107                               String JavaDoc convertedSignature) {
108       modifiedFieldInfo.put(name+originalDesc, new ModifiedFieldInfo(name, originalDesc, convertedDesc, signature, convertedSignature));
109     }
110
111     public String JavaDoc toString() {
112       StringBuffer JavaDoc buf = new StringBuffer JavaDoc();
113       buf.append(super.toString());
114       buf.append(" ChangeContext :- ");
115       buf.append("originalClassNameSlashes: ");
116       buf.append(originalClassNameSlashes);
117       buf.append(", convertedClassNameSlashes: ");
118       buf.append(convertedClassNameSlashes);
119       buf.append(", modifiedMethodInfo size: ");
120       buf.append(modifiedMethodInfo.size());
121       buf.append(modifiedMethodInfo);
122       return buf.toString();
123     }
124   }
125
126   static class ModifiedFieldInfo {
127     final String JavaDoc fieldName;
128     final String JavaDoc originalFieldDesc;
129     String JavaDoc convertedFieldDesc;
130     String JavaDoc originalSignature;
131     String JavaDoc convertedSignature;
132
133     ModifiedFieldInfo(String JavaDoc name, String JavaDoc originalDesc, String JavaDoc convertedDesc, String JavaDoc signature,
134                       String JavaDoc convertedSignature) {
135       this.fieldName = name;
136       this.originalFieldDesc = originalDesc;
137       this.convertedFieldDesc = convertedDesc;
138       this.originalSignature = signature;
139       this.convertedSignature = convertedSignature;
140     }
141
142     public boolean equals(Object JavaDoc obj) {
143       ModifiedFieldInfo fieldInfo = (ModifiedFieldInfo) obj;
144       boolean match = this.fieldName != null && this.fieldName.equals(fieldInfo.fieldName);
145       match = match && this.originalFieldDesc != null && this.originalFieldDesc.equals(fieldInfo.originalFieldDesc);
146       match = match && this.convertedFieldDesc != null && this.convertedFieldDesc.equals(fieldInfo.convertedFieldDesc);
147       match = match
148               && ((this.originalSignature == null && fieldInfo.originalSignature == null) || (this.originalSignature != null && this.originalSignature
149                   .equals(fieldInfo.originalSignature)));
150       match = match
151               && ((this.convertedSignature == null && fieldInfo.convertedSignature == null) || (this.convertedSignature != null && this.convertedSignature
152                   .equals(fieldInfo.convertedSignature)));
153       return match;
154     }
155     
156     public String JavaDoc toString() {
157       return super.toString() + ", name: " +fieldName + ", desc: " + originalFieldDesc + ", convertedDesc: " + convertedFieldDesc;
158     }
159   }
160
161   static class ModifiedMethodInfo {
162     final String JavaDoc methodName;
163     final String JavaDoc originalMethodDesc;
164     String JavaDoc convertedMethodDesc;
165     String JavaDoc originalSignature;
166     String JavaDoc convertedSignature;
167
168     ModifiedMethodInfo(String JavaDoc name, String JavaDoc originalDesc, String JavaDoc convertedDesc, String JavaDoc signature,
169                        String JavaDoc convertedSignature) {
170       this.methodName = name;
171       this.originalMethodDesc = originalDesc;
172       this.convertedMethodDesc = convertedDesc;
173       this.originalSignature = signature;
174       this.convertedSignature = convertedSignature;
175     }
176
177     public boolean equals(Object JavaDoc obj) {
178       ModifiedMethodInfo methodInfo = (ModifiedMethodInfo) obj;
179       boolean match = this.methodName != null && this.methodName.equals(methodInfo.methodName);
180       match = match && this.originalMethodDesc != null && this.originalMethodDesc.equals(methodInfo.originalMethodDesc);
181       match = match && this.convertedMethodDesc != null
182               && this.convertedMethodDesc.equals(methodInfo.convertedMethodDesc);
183       match = match
184               && ((this.originalSignature == null && methodInfo.originalSignature == null) || (this.originalSignature != null && this.originalSignature
185                   .equals(methodInfo.originalSignature)));
186       match = match
187               && ((this.convertedSignature == null && methodInfo.convertedSignature == null) || (this.convertedSignature != null && this.convertedSignature
188                   .equals(methodInfo.convertedSignature)));
189       return match;
190     }
191     
192     public String JavaDoc toString() {
193       return super.toString() + ", name: " + methodName + ", desc: " + originalMethodDesc + ", convertedDesc: " + convertedMethodDesc;
194     }
195   }
196
197   public ChangeClassNameHierarchyAdapter(ClassVisitor cv) {
198     super(cv);
199   }
200   
201   public MethodVisitor invokeSuperVisitMethod(int access, String JavaDoc name, String JavaDoc desc, String JavaDoc signature, String JavaDoc[] exceptions,
202                                               Map JavaDoc instrumentedContext, String JavaDoc fullClassSlashes) {
203     ChangeContext context = (ChangeContext)instrumentedContext.get(fullClassSlashes);
204     String JavaDoc origSuperClassName = context.originalSuperClassNameSlashes;
205     // -- need this when superClassNameAdapter and RootAdapter are merged context = (ChangeContext)instrumentedContext.get(origSuperClassName);
206
String JavaDoc convertedSuperClassName = context.convertedClassNameSlashes;
207     
208     Type returnType = Type.getReturnType(desc);
209     MethodVisitor mv = cv.visitMethod(access, name, desc, signature, exceptions);
210     mv.visitCode();
211     mv.visitVarInsn(ALOAD, 0);
212     ByteCodeUtil.pushMethodArguments(access, desc, mv);
213     mv.visitMethodInsn(INVOKESPECIAL, origSuperClassName, name, desc);
214     mv.visitInsn(returnType.getOpcode(IRETURN));
215     mv.visitMaxs(0, 0);
216     mv.visitEnd();
217     return mv;
218   }
219
220 }
221
Popular Tags