1 19 20 package soot.dava.toolkits.base.misc; 21 22 import soot.*; 23 import java.io.*; 24 import java.util.*; 25 import soot.util.*; 26 import soot.dava.*; 27 import java.util.jar.*; 28 29 public class PackageNamer 30 { 31 public PackageNamer( Singletons.Global g ) {} 32 public static PackageNamer v() { return G.v().soot_dava_toolkits_base_misc_PackageNamer(); } 33 34 public boolean has_FixedNames() 35 { 36 return fixed; 37 } 38 39 public boolean use_ShortName( String fixedPackageName, String fixedShortClassName) 40 { 41 if (fixed == false) 42 return false; 43 44 if (fixedPackageName.equals( Dava.v().get_CurrentPackage())) 45 return true; 46 47 IterableSet packageContext = Dava.v().get_CurrentPackageContext(); 48 if (packageContext == null) 49 return true; 50 51 packageContext = patch_PackageContext( packageContext); 52 53 int count = 0; 54 StringTokenizer st = new StringTokenizer( classPath, pathSep); 55 while (st.hasMoreTokens()) { 56 String classpathDir = st.nextToken(); 57 58 Iterator packIt = packageContext.iterator(); 59 while (packIt.hasNext()) 60 if (package_ContainsClass( classpathDir, (String ) packIt.next(), fixedShortClassName)) 61 if (++count > 1) 62 return false; 63 } 64 65 return true; 66 } 67 68 public String get_FixedClassName( String originalFullClassName) 69 { 70 if (fixed == false) 71 return originalFullClassName; 72 73 Iterator it = appRoots.iterator(); 74 while (it.hasNext()) { 75 NameHolder h = (NameHolder) it.next(); 76 if (h.contains_OriginalName( new StringTokenizer( originalFullClassName, "."), true)) 77 return h.get_FixedName( new StringTokenizer( originalFullClassName, "."), true); 78 } 79 80 return originalFullClassName.substring( originalFullClassName.lastIndexOf( ".") + 1); 81 } 82 83 public String get_FixedPackageName( String originalPackageName) 84 { 85 if (fixed == false) 86 return originalPackageName; 87 88 if (originalPackageName.equals( "")) 89 return ""; 90 91 Iterator it = appRoots.iterator(); 92 while (it.hasNext()) { 93 NameHolder h = (NameHolder) it.next(); 94 if (h.contains_OriginalName( new StringTokenizer( originalPackageName, "."), false)) 95 return h.get_FixedName( new StringTokenizer( originalPackageName, "."), false); 96 } 97 98 return originalPackageName; 99 } 100 101 102 private class NameHolder 103 { 104 private String originalName, packageName, className; 105 private ArrayList children; 106 private NameHolder parent; 107 private boolean isClass; 108 109 110 public NameHolder( String name, NameHolder parent, boolean isClass) 111 { 112 originalName = name; 113 className = name; 114 packageName = name; 115 116 this.parent = parent; 117 this.isClass = isClass; 118 119 children = new ArrayList(); 120 } 121 122 public NameHolder get_Parent() 123 { 124 return parent; 125 } 126 127 public void set_ClassAttr() 128 { 129 isClass = true; 130 } 131 132 public boolean is_Class() 133 { 134 if (children.isEmpty()) 135 return true; 136 else 137 return isClass; 138 } 139 140 public boolean is_Package() 141 { 142 return (children.isEmpty() == false); 143 } 144 145 public String get_PackageName() 146 { 147 return packageName; 148 } 149 150 public String get_ClassName() 151 { 152 return className; 153 } 154 155 public void set_PackageName( String packageName) 156 { 157 this.packageName = packageName; 158 } 159 160 public void set_ClassName( String className) 161 { 162 this.className = className; 163 } 164 165 public String get_OriginalName() 166 { 167 return originalName; 168 } 169 170 public ArrayList get_Children() 171 { 172 return children; 173 } 174 175 public String get_FixedPackageName() 176 { 177 if (parent == null) 178 return ""; 179 180 return parent.retrieve_FixedPackageName(); 181 } 182 183 public String retrieve_FixedPackageName() 184 { 185 if (parent == null) 186 return packageName; 187 188 return parent.get_FixedPackageName() + "." + packageName; 189 } 190 191 public String get_FixedName( StringTokenizer st, boolean forClass) 192 { 193 if (st.nextToken().equals( originalName) == false) 194 throw new RuntimeException ( "Unable to resolve naming."); 195 196 return retrieve_FixedName( st, forClass); 197 } 198 199 private String retrieve_FixedName( StringTokenizer st, boolean forClass) 200 { 201 if (st.hasMoreTokens() == false) { 202 if (forClass) 203 return className; 204 else 205 return packageName; 206 } 207 208 String subName = st.nextToken(); 209 Iterator cit = children.iterator(); 210 while (cit.hasNext()) { 211 NameHolder h = (NameHolder) cit.next(); 212 213 if (h.get_OriginalName().equals( subName)) { 214 if (forClass) 215 return h.retrieve_FixedName( st, forClass); 216 else 217 return packageName + "." + h.retrieve_FixedName( st, forClass); 218 } 219 } 220 221 throw new RuntimeException ( "Unable to resolve naming."); 222 } 223 224 public String get_OriginalPackageName( StringTokenizer st) 225 { 226 if (st.hasMoreTokens() == false) 227 return get_OriginalName(); 228 229 String subName = st.nextToken(); 230 231 Iterator cit = children.iterator(); 232 while (cit.hasNext()) { 233 NameHolder h = (NameHolder) cit.next(); 234 235 if (h.get_PackageName().equals( subName)) { 236 String originalSubPackageName = h.get_OriginalPackageName( st); 237 238 if (originalSubPackageName == null) 239 return null; 240 else 241 return get_OriginalName() + "." + originalSubPackageName; 242 } 243 } 244 245 return null; 246 } 247 248 public boolean contains_OriginalName( StringTokenizer st, boolean forClass) 249 { 250 if (get_OriginalName().equals( st.nextToken()) == false) 251 return false; 252 253 return finds_OriginalName( st, forClass); 254 } 255 256 private boolean finds_OriginalName( StringTokenizer st, boolean forClass) 257 { 258 if (st.hasMoreTokens() == false) 259 return (((forClass) && (is_Class())) || ((!forClass) && (is_Package()))); 260 261 String subName = st.nextToken(); 262 Iterator cit = children.iterator(); 263 while (cit.hasNext()) { 264 NameHolder h = (NameHolder) cit.next(); 265 266 if (h.get_OriginalName().equals( subName)) 267 return h.finds_OriginalName( st, forClass); 268 } 269 270 return false; 271 } 272 273 public void fix_ClassNames( String curPackName) 274 { 275 if ((is_Class()) && (keywords.contains( className))) { 276 String tClassName = className; 277 278 if (Character.isLowerCase( className.charAt( 0))) { 279 tClassName = tClassName.substring( 0, 1).toUpperCase() + tClassName.substring( 1); 280 className = tClassName; 281 } 282 283 for (int i=0; keywords.contains( className); i++) 284 className = tClassName + "_c" + i; 285 } 286 287 Iterator it = children.iterator(); 288 while (it.hasNext()) 289 ((NameHolder) it.next()).fix_ClassNames( curPackName + "." + packageName); 290 } 291 292 public void fix_PackageNames() 293 { 294 if ((is_Package()) && (verify_PackageName() == false)) { 295 String tPackageName = packageName; 296 297 if (Character.isUpperCase( packageName.charAt( 0))) { 298 tPackageName = tPackageName.substring( 0, 1).toLowerCase() + tPackageName.substring( 1); 299 packageName = tPackageName; 300 } 301 302 for (int i=0; verify_PackageName() == false; i++) 303 packageName = tPackageName + "_p" + i; 304 } 305 306 Iterator it = children.iterator(); 307 while (it.hasNext()) 308 ((NameHolder) it.next()).fix_PackageNames(); 309 } 310 311 312 public boolean verify_PackageName() 313 { 314 return ((keywords.contains( packageName) == false) && 315 (siblingClashes( packageName) == false) && 316 ((is_Class() == false) || (className.equals( packageName) == false))); 317 } 318 319 public boolean siblingClashes( String name) 320 { 321 Iterator it = null; 322 323 if (parent == null) { 324 325 if (appRoots.contains( this)) 326 it = appRoots.iterator(); 327 else 328 throw new RuntimeException ( "Unable to find package siblings."); 329 } 330 else 331 it = parent.get_Children().iterator(); 332 333 while (it.hasNext()) { 334 NameHolder sibling = (NameHolder) it.next(); 335 336 if (sibling == this) 337 continue; 338 339 if (((sibling.is_Package()) && (sibling.get_PackageName().equals( name))) || 340 ((sibling.is_Class()) && (sibling.get_ClassName().equals( name)))) 341 342 return true; 343 } 344 345 return false; 346 } 347 348 public void dump( String indentation) 349 { 350 G.v().out.print( indentation + "\"" + originalName + "\", \"" + packageName + "\", \"" + className + "\" ("); 351 if (is_Class()) 352 G.v().out.print("c"); 353 if (is_Package()) 354 G.v().out.print("p"); 355 G.v().out.println( ")"); 356 357 Iterator it = children.iterator(); 358 while (it.hasNext()) 359 ((NameHolder) it.next()).dump( indentation + " "); 360 } 361 } 362 363 private boolean fixed = false; 364 private ArrayList appRoots = new ArrayList(); 365 private ArrayList otherRoots = new ArrayList(); 366 private HashSet keywords = new HashSet(); 367 private HashMap class2package = new HashMap(); 368 private char fileSep; 369 private String classPath, pathSep; 370 371 public void fixNames() 372 { 373 if (fixed) 374 return; 375 376 String [] keywordArray = 377 { 378 "abstract", "default", "if", "private", "this", "boolean", 379 "do", "implements", "protected", "throw", "break", 380 "double", "import", "public", "throws", "byte", "else", 381 "instanceof", "return", "transient", "case", "extends", 382 "int", "short", "try", "catch", "final", "interface", 383 "static", "void", "char", "finally", "long", "strictfp", 384 "volatile", "class", "float", "native", "super", "while", 385 "const", "for", "new", "switch", "continue", "goto", 386 "package", "synchronized", "true", "false", "null" 387 }; 388 389 for (int i=0; i<keywordArray.length; i++) 390 keywords.add( keywordArray[i]); 391 392 Iterator classIt = Scene.v().getLibraryClasses().iterator(); 393 while (classIt.hasNext()) 394 add_ClassName( ((SootClass) classIt.next()).getName(), otherRoots); 395 396 classIt = Scene.v().getApplicationClasses().iterator(); 397 while (classIt.hasNext()) 398 add_ClassName( ((SootClass) classIt.next()).getName(), appRoots); 399 400 Iterator arit = appRoots.iterator(); 401 while (arit.hasNext()) 402 ((NameHolder) arit.next()).fix_ClassNames( ""); 403 404 arit = appRoots.iterator(); 405 while (arit.hasNext()) 406 ((NameHolder) arit.next()).fix_PackageNames(); 407 408 fileSep = System.getProperty( "file.separator").charAt(0); 409 pathSep = System.getProperty( "path.separator"); 410 classPath = System.getProperty( "java.class.path"); 411 412 fixed = true; 413 } 414 415 private void add_ClassName( String className, ArrayList roots) 416 { 417 ArrayList children = roots; 418 NameHolder curNode = null; 419 420 StringTokenizer st = new StringTokenizer( className, "."); 421 while (st.hasMoreTokens()) { 422 String curName = (String ) st.nextToken(); 423 424 NameHolder child = null; 425 boolean found = false; 426 Iterator lit = children.iterator(); 427 428 while (lit.hasNext()) { 429 child = (NameHolder) lit.next(); 430 431 if (child.get_OriginalName().equals( curName)) { 432 433 if (st.hasMoreTokens() == false) 434 child.set_ClassAttr(); 435 436 found = true; 437 break; 438 } 439 } 440 441 if (!found) { 442 child = new NameHolder( curName, curNode, st.hasMoreTokens() == false); 443 children.add( child); 444 } 445 446 curNode = child; 447 children = child.get_Children(); 448 } 449 } 450 451 public boolean package_ContainsClass( String classpathDir, String packageName, String className) 452 { 453 File p = new File( classpathDir); 454 455 if (p.exists() == false) 456 return false; 457 458 packageName = packageName.replace( '.', fileSep); 459 if ((packageName.length() > 0) && (packageName.charAt( packageName.length() - 1) != fileSep)) 460 packageName += fileSep; 461 462 String name = packageName + className + ".class"; 463 464 if (p.isDirectory()) { 465 if ((classpathDir.length() > 0) && (classpathDir.charAt( classpathDir.length() - 1) != fileSep)) 466 classpathDir += fileSep; 467 468 return (new File( classpathDir + name)).exists(); 469 } 470 471 else { 472 JarFile jf = null; 473 474 try { 475 jf = new JarFile( p); 476 } 477 catch (IOException ioe) { 478 return false; 479 } 480 481 return (jf.getJarEntry( name) != null); 482 } 483 } 484 485 IterableSet patch_PackageContext( IterableSet currentContext) 486 { 487 IterableSet newContext = new IterableSet(); 488 489 Iterator it = currentContext.iterator(); 490 while (it.hasNext()) { 491 String 492 currentPackage = (String ) it.next(), 493 newPackage = null; 494 495 StringTokenizer st = new StringTokenizer( currentPackage, "."); 496 497 if (st.hasMoreTokens() == false) { 498 newContext.add( currentPackage); 499 continue; 500 } 501 502 String firstToken = st.nextToken(); 503 Iterator arit = appRoots.iterator(); 504 while (arit.hasNext()) { 505 NameHolder h = (NameHolder) arit.next(); 506 507 if (h.get_PackageName().equals( firstToken)) { 508 newPackage = h.get_OriginalPackageName( st); 509 break; 510 } 511 } 512 if (newPackage != null) 513 newContext.add( newPackage); 514 else 515 newContext.add( currentPackage); 516 } 517 518 return newContext; 519 } 520 } 521 | Popular Tags |