You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

UtilClassLoader.java 4.3KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140
  1. /* *******************************************************************
  2. * Copyright (c) 2003 Contributors.
  3. * All rights reserved.
  4. * This program and the accompanying materials are made available
  5. * under the terms of the Eclipse Public License v1.0
  6. * which accompanies this distribution and is available at
  7. * http://www.eclipse.org/legal/epl-v10.html
  8. *
  9. * Contributors:
  10. * Isberg initial implementation
  11. * ******************************************************************/
  12. package org.aspectj.util;
  13. import java.io.ByteArrayOutputStream;
  14. import java.io.File;
  15. import java.io.FileInputStream;
  16. import java.io.IOException;
  17. import java.io.InputStream;
  18. import java.net.URL;
  19. import java.net.URLClassLoader;
  20. import java.util.ArrayList;
  21. import java.util.Arrays;
  22. import java.util.Collections;
  23. import java.util.Iterator;
  24. import java.util.List;
  25. /**
  26. * Load classes as File from File[] dirs or URL[] jars.
  27. */
  28. public class UtilClassLoader extends URLClassLoader {
  29. /** seek classes in dirs first */
  30. List<File> dirs;
  31. /** save URL[] only for toString */
  32. private URL[] urlsForDebugString;
  33. public UtilClassLoader(URL[] urls, File[] dirs) {
  34. super(urls);
  35. LangUtil.throwIaxIfNotAssignable(dirs, File.class, "dirs");
  36. this.urlsForDebugString = urls;
  37. ArrayList<File> dcopy = new ArrayList<File>();
  38. if (!LangUtil.isEmpty(dirs)) {
  39. dcopy.addAll(Arrays.asList(dirs));
  40. }
  41. this.dirs = Collections.unmodifiableList(dcopy);
  42. }
  43. public URL getResource(String name) {
  44. return ClassLoader.getSystemResource(name);
  45. }
  46. public InputStream getResourceAsStream(String name) {
  47. return ClassLoader.getSystemResourceAsStream(name);
  48. }
  49. public synchronized Class<?> loadClass(String name, boolean resolve)
  50. throws ClassNotFoundException {
  51. // search the cache, our dirs (if maybe test),
  52. // the system, the superclass (URL[]),
  53. // and our dirs again (if not maybe test)
  54. ClassNotFoundException thrown = null;
  55. Class<?> result = findLoadedClass(name);
  56. if (null != result) {
  57. resolve = false;
  58. } else {
  59. try {
  60. result = findSystemClass(name);
  61. } catch (ClassNotFoundException e) {
  62. thrown = e;
  63. }
  64. }
  65. if (null == result) {
  66. try {
  67. result = super.loadClass(name, resolve);
  68. } catch (ClassNotFoundException e) {
  69. thrown = e;
  70. }
  71. if (null != result) { // resolved by superclass
  72. return result;
  73. }
  74. }
  75. if (null == result) {
  76. byte[] data = readClass(name);
  77. if (data != null) {
  78. result = defineClass(name, data, 0, data.length);
  79. } // handle ClassFormatError?
  80. }
  81. if (null == result) {
  82. throw (null != thrown ? thrown : new ClassNotFoundException(name));
  83. }
  84. if (resolve) {
  85. resolveClass(result);
  86. }
  87. return result;
  88. }
  89. /** @return null if class not found or byte[] of class otherwise */
  90. private byte[] readClass(String className) throws ClassNotFoundException {
  91. final String fileName = className.replace('.', '/')+".class";
  92. for (Iterator<File> iter = dirs.iterator(); iter.hasNext();) {
  93. File file = new File(iter.next(), fileName);
  94. if (file.canRead()) {
  95. return getClassData(file);
  96. }
  97. }
  98. return null;
  99. }
  100. private byte[] getClassData(File f) {
  101. try {
  102. FileInputStream stream= new FileInputStream(f);
  103. ByteArrayOutputStream out= new ByteArrayOutputStream(1000);
  104. byte[] b= new byte[4096];
  105. int n;
  106. while ((n= stream.read(b)) != -1) {
  107. out.write(b, 0, n);
  108. }
  109. stream.close();
  110. out.close();
  111. return out.toByteArray();
  112. } catch (IOException e) {
  113. }
  114. return null;
  115. }
  116. /** @return String with debug info: urls and classes used */
  117. public String toString() {
  118. return "UtilClassLoader(urls="
  119. + Arrays.asList(urlsForDebugString)
  120. + ", dirs="
  121. + dirs
  122. + ")";
  123. }
  124. }