1 16 package net.sf.cglib.core; 17 18 import java.util.*; 19 import org.objectweb.asm.Type; 20 21 public class TypeUtils { 22 private static final Map transforms = new HashMap(); 23 private static final Map rtransforms = new HashMap(); 24 25 private TypeUtils() { 26 } 27 28 static { 29 transforms.put("void", "V"); 30 transforms.put("byte", "B"); 31 transforms.put("char", "C"); 32 transforms.put("double", "D"); 33 transforms.put("float", "F"); 34 transforms.put("int", "I"); 35 transforms.put("long", "J"); 36 transforms.put("short", "S"); 37 transforms.put("boolean", "Z"); 38 39 CollectionUtils.reverse(transforms, rtransforms); 40 } 41 42 public static Type getType(String className) { 43 return Type.getType("L" + className.replace('.', '/') + ";"); 44 } 45 46 public static boolean isFinal(int access) { 47 return (Constants.ACC_FINAL & access) != 0; 48 } 49 50 public static boolean isStatic(int access) { 51 return (Constants.ACC_STATIC & access) != 0; 52 } 53 54 public static boolean isProtected(int access) { 55 return (Constants.ACC_PROTECTED & access) != 0; 56 } 57 58 public static boolean isPublic(int access) { 59 return (Constants.ACC_PUBLIC & access) != 0; 60 } 61 62 public static boolean isAbstract(int access) { 63 return (Constants.ACC_ABSTRACT & access) != 0; 64 } 65 66 public static boolean isInterface(int access) { 67 return (Constants.ACC_INTERFACE & access) != 0; 68 } 69 70 public static boolean isPrivate(int access) { 71 return (Constants.ACC_PRIVATE & access) != 0; 72 } 73 74 public static boolean isSynthetic(int access) { 75 return (Constants.ACC_SYNTHETIC & access) != 0; 76 } 77 78 public static String getPackageName(Type type) { 80 return getPackageName(getClassName(type)); 81 } 82 83 public static String getPackageName(String className) { 84 int idx = className.lastIndexOf('.'); 85 return (idx < 0) ? "" : className.substring(0, idx); 86 } 87 88 public static String upperFirst(String s) { 89 if (s == null || s.length() == 0) { 90 return s; 91 } 92 return Character.toUpperCase(s.charAt(0)) + s.substring(1); 93 } 94 95 public static String getClassName(Type type) { 96 if (isPrimitive(type)) { 97 return (String )rtransforms.get(type.getDescriptor()); 98 } else if (isArray(type)) { 99 return getClassName(getComponentType(type)) + "[]"; 100 } else { 101 return type.getClassName(); 102 } 103 } 104 105 public static Type[] add(Type[] types, Type extra) { 106 if (types == null) { 107 return new Type[]{ extra }; 108 } else { 109 List list = Arrays.asList(types); 110 if (list.contains(extra)) { 111 return types; 112 } 113 Type[] copy = new Type[types.length + 1]; 114 System.arraycopy(types, 0, copy, 0, types.length); 115 copy[types.length] = extra; 116 return copy; 117 } 118 } 119 120 public static Type[] add(Type[] t1, Type[] t2) { 121 Type[] all = new Type[t1.length + t2.length]; 123 System.arraycopy(t1, 0, all, 0, t1.length); 124 System.arraycopy(t2, 0, all, t1.length, t2.length); 125 return all; 126 } 127 128 public static Type fromInternalName(String name) { 129 return Type.getType("L" + name + ";"); 131 } 132 133 public static Type[] fromInternalNames(String [] names) { 134 if (names == null) { 135 return null; 136 } 137 Type[] types = new Type[names.length]; 138 for (int i = 0; i < names.length; i++) { 139 types[i] = fromInternalName(names[i]); 140 } 141 return types; 142 } 143 144 public static int getStackSize(Type[] types) { 145 int size = 0; 146 for (int i = 0; i < types.length; i++) { 147 size += types[i].getSize(); 148 } 149 return size; 150 } 151 152 public static String [] toInternalNames(Type[] types) { 153 if (types == null) { 154 return null; 155 } 156 String [] names = new String [types.length]; 157 for (int i = 0; i < types.length; i++) { 158 names[i] = types[i].getInternalName(); 159 } 160 return names; 161 } 162 163 public static Signature parseSignature(String s) { 164 int space = s.indexOf(' '); 165 int lparen = s.indexOf('(', space); 166 int rparen = s.indexOf(')', lparen); 167 String returnType = s.substring(0, space); 168 String methodName = s.substring(space + 1, lparen); 169 StringBuffer sb = new StringBuffer (); 170 sb.append('('); 171 for (Iterator it = parseTypes(s, lparen + 1, rparen).iterator(); it.hasNext();) { 172 sb.append(it.next()); 173 } 174 sb.append(')'); 175 sb.append(map(returnType)); 176 return new Signature(methodName, sb.toString()); 177 } 178 179 public static Type parseType(String s) { 180 return Type.getType(map(s)); 181 } 182 183 public static Type[] parseTypes(String s) { 184 List names = parseTypes(s, 0, s.length()); 185 Type[] types = new Type[names.size()]; 186 for (int i = 0; i < types.length; i++) { 187 types[i] = Type.getType((String )names.get(i)); 188 } 189 return types; 190 } 191 192 public static Signature parseConstructor(Type[] types) { 193 StringBuffer sb = new StringBuffer (); 194 sb.append("("); 195 for (int i = 0; i < types.length; i++) { 196 sb.append(types[i].getDescriptor()); 197 } 198 sb.append(")"); 199 sb.append("V"); 200 return new Signature(Constants.CONSTRUCTOR_NAME, sb.toString()); 201 } 202 203 public static Signature parseConstructor(String sig) { 204 return parseSignature("void <init>(" + sig + ")"); } 206 207 private static List parseTypes(String s, int mark, int end) { 208 List types = new ArrayList(5); 209 for (;;) { 210 int next = s.indexOf(',', mark); 211 if (next < 0) { 212 break; 213 } 214 types.add(map(s.substring(mark, next).trim())); 215 mark = next + 1; 216 } 217 types.add(map(s.substring(mark, end).trim())); 218 return types; 219 } 220 221 private static String map(String type) { 222 if (type.equals("")) { 223 return type; 224 } 225 String t = (String )transforms.get(type); 226 if (t != null) { 227 return t; 228 } else if (type.indexOf('.') < 0) { 229 return map("java.lang." + type); 230 } else { 231 StringBuffer sb = new StringBuffer (); 232 int index = 0; 233 while ((index = type.indexOf("[]", index) + 1) > 0) { 234 sb.append('['); 235 } 236 type = type.substring(0, type.length() - sb.length() * 2); 237 sb.append('L').append(type.replace('.', '/')).append(';'); 238 return sb.toString(); 239 } 240 } 241 242 public static Type getBoxedType(Type type) { 243 switch (type.getSort()) { 244 case Type.CHAR: 245 return Constants.TYPE_CHARACTER; 246 case Type.BOOLEAN: 247 return Constants.TYPE_BOOLEAN; 248 case Type.DOUBLE: 249 return Constants.TYPE_DOUBLE; 250 case Type.FLOAT: 251 return Constants.TYPE_FLOAT; 252 case Type.LONG: 253 return Constants.TYPE_LONG; 254 case Type.INT: 255 return Constants.TYPE_INTEGER; 256 case Type.SHORT: 257 return Constants.TYPE_SHORT; 258 case Type.BYTE: 259 return Constants.TYPE_BYTE; 260 default: 261 return type; 262 } 263 } 264 265 public static Type getUnboxedType(Type type) { 266 if (Constants.TYPE_INTEGER.equals(type)) { 267 return Type.INT_TYPE; 268 } else if (Constants.TYPE_BOOLEAN.equals(type)) { 269 return Type.BOOLEAN_TYPE; 270 } else if (Constants.TYPE_DOUBLE.equals(type)) { 271 return Type.DOUBLE_TYPE; 272 } else if (Constants.TYPE_LONG.equals(type)) { 273 return Type.LONG_TYPE; 274 } else if (Constants.TYPE_CHARACTER.equals(type)) { 275 return Type.CHAR_TYPE; 276 } else if (Constants.TYPE_BYTE.equals(type)) { 277 return Type.BYTE_TYPE; 278 } else if (Constants.TYPE_FLOAT.equals(type)) { 279 return Type.FLOAT_TYPE; 280 } else if (Constants.TYPE_SHORT.equals(type)) { 281 return Type.SHORT_TYPE; 282 } else { 283 return type; 284 } 285 } 286 287 public static boolean isArray(Type type) { 288 return type.getSort() == Type.ARRAY; 289 } 290 291 public static Type getComponentType(Type type) { 292 if (!isArray(type)) { 293 throw new IllegalArgumentException ("Type " + type + " is not an array"); 294 } 295 return Type.getType(type.getDescriptor().substring(1)); 296 } 297 298 public static boolean isPrimitive(Type type) { 299 switch (type.getSort()) { 300 case Type.ARRAY: 301 case Type.OBJECT: 302 return false; 303 default: 304 return true; 305 } 306 } 307 308 public static String emulateClassGetName(Type type) { 309 if (isArray(type)) { 310 return type.getDescriptor().replace('/', '.'); 311 } else { 312 return getClassName(type); 313 } 314 } 315 316 public static boolean isConstructor(MethodInfo method) { 317 return method.getSignature().getName().equals(Constants.CONSTRUCTOR_NAME); 318 } 319 320 public static Type[] getTypes(Class [] classes) { 321 if (classes == null) { 322 return null; 323 } 324 Type[] types = new Type[classes.length]; 325 for (int i = 0; i < classes.length; i++) { 326 types[i] = Type.getType(classes[i]); 327 } 328 return types; 329 } 330 331 public static int ICONST(int value) { 332 switch (value) { 333 case -1: return Constants.ICONST_M1; 334 case 0: return Constants.ICONST_0; 335 case 1: return Constants.ICONST_1; 336 case 2: return Constants.ICONST_2; 337 case 3: return Constants.ICONST_3; 338 case 4: return Constants.ICONST_4; 339 case 5: return Constants.ICONST_5; 340 } 341 return -1; } 343 344 public static int LCONST(long value) { 345 if (value == 0L) { 346 return Constants.LCONST_0; 347 } else if (value == 1L) { 348 return Constants.LCONST_1; 349 } else { 350 return -1; } 352 } 353 354 public static int FCONST(float value) { 355 if (value == 0f) { 356 return Constants.FCONST_0; 357 } else if (value == 1f) { 358 return Constants.FCONST_1; 359 } else if (value == 2f) { 360 return Constants.FCONST_2; 361 } else { 362 return -1; } 364 } 365 366 public static int DCONST(double value) { 367 if (value == 0d) { 368 return Constants.DCONST_0; 369 } else if (value == 1d) { 370 return Constants.DCONST_1; 371 } else { 372 return -1; } 374 } 375 376 public static int NEWARRAY(Type type) { 377 switch (type.getSort()) { 378 case Type.BYTE: 379 return Constants.T_BYTE; 380 case Type.CHAR: 381 return Constants.T_CHAR; 382 case Type.DOUBLE: 383 return Constants.T_DOUBLE; 384 case Type.FLOAT: 385 return Constants.T_FLOAT; 386 case Type.INT: 387 return Constants.T_INT; 388 case Type.LONG: 389 return Constants.T_LONG; 390 case Type.SHORT: 391 return Constants.T_SHORT; 392 case Type.BOOLEAN: 393 return Constants.T_BOOLEAN; 394 default: 395 return -1; } 397 } 398 399 public static String escapeType(String s) { 400 StringBuffer sb = new StringBuffer (); 401 for (int i = 0, len = s.length(); i < len; i++) { 402 char c = s.charAt(i); 403 switch (c) { 404 case '$': sb.append("$24"); break; 405 case '.': sb.append("$2E"); break; 406 case '[': sb.append("$5B"); break; 407 case ';': sb.append("$3B"); break; 408 case '(': sb.append("$28"); break; 409 case ')': sb.append("$29"); break; 410 case '/': sb.append("$2F"); break; 411 default: 412 sb.append(c); 413 } 414 } 415 return sb.toString(); 416 } 417 } 418 | Popular Tags |