public static void main(String[] args) throws Exception {
    List<String> pkgs = new ArrayList<>(Arrays.asList(packages));
    String osName = System.getProperty("os.name");
    if (osName.contains("OS X")) {
      pkgs.add("apple."); // add apple package for OS X
    } else if (osName.startsWith("Windows")) {
      pkgs.add("com.sun.java.accessibility.");
    }

    List<String> jspkgs = getPackages(Security.getProperty("package.access"));

    // Sort to ensure lists are comparable
    Collections.sort(pkgs);
    Collections.sort(jspkgs);

    if (!pkgs.equals(jspkgs)) {
      for (String p : pkgs)
        if (!jspkgs.contains(p)) System.out.println("In golden set, but not in j.s file: " + p);
      for (String p : jspkgs)
        if (!pkgs.contains(p)) System.out.println("In j.s file, but not in golden set: " + p);

      throw new RuntimeException(
          "restricted packages are not " + "consistent with java.security file");
    }
    System.setSecurityManager(new SecurityManager());
    SecurityManager sm = System.getSecurityManager();
    for (String pkg : packages) {
      String subpkg = pkg + "foo";
      try {
        sm.checkPackageAccess(pkg);
        throw new RuntimeException("Able to access " + pkg + " package");
      } catch (SecurityException se) {
      }
      try {
        sm.checkPackageAccess(subpkg);
        throw new RuntimeException("Able to access " + subpkg + " package");
      } catch (SecurityException se) {
      }
      try {
        sm.checkPackageDefinition(pkg);
        throw new RuntimeException("Able to define class in " + pkg + " package");
      } catch (SecurityException se) {
      }
      try {
        sm.checkPackageDefinition(subpkg);
        throw new RuntimeException("Able to define class in " + subpkg + " package");
      } catch (SecurityException se) {
      }
    }
    System.out.println("Test passed");
  }
  /** {@inheritDoc} */
  @SuppressWarnings("all")
  protected Class findClass(final String className) throws ClassNotFoundException {
    // first think check if we are allowed to define the package
    SecurityManager securityManager = System.getSecurityManager();
    if (securityManager != null) {
      String packageName;
      int packageEnd = className.lastIndexOf('.');
      if (packageEnd >= 0) {
        packageName = className.substring(0, packageEnd);
        securityManager.checkPackageDefinition(packageName);
      }
    }

    // convert the class name to a file name
    String resourceName = className.replace('.', '/') + ".class";

    // find the class file resource
    ResourceHandle resourceHandle = resourceFinder.getResource(resourceName);
    if (resourceHandle == null) {
      throw new ClassNotFoundException(className);
    }

    byte[] bytes;
    Manifest manifest;
    try {
      // get the bytes from the class file
      bytes = resourceHandle.getBytes();

      // get the manifest for defining the packages
      manifest = resourceHandle.getManifest();
    } catch (IOException e) {
      throw new ClassNotFoundException(className, e);
    }

    // get the certificates for the code source
    Certificate[] certificates = resourceHandle.getCertificates();

    // the code source url is used to define the package and as the security context for the class
    URL codeSourceUrl = resourceHandle.getCodeSourceUrl();

    // define the package (required for security)
    definePackage(className, codeSourceUrl, manifest);

    // this is the security context of the class
    CodeSource codeSource = new CodeSource(codeSourceUrl, certificates);

    // load the class into the vm
    Class clazz = defineClass(className, bytes, 0, bytes.length, codeSource);
    return clazz;
  }
Beispiel #3
0
  /**
   * L&auml;dt die per Name angegebene Klasse. sse. Im Namen kann entweder der Punkt oder der
   * Schr&auml;gstrich als Paket-Trennzeichen benutzt werden. Mit der Option <code>resolve</code>
   * kann entschieden werden, ob die Aufl&ouml;sung von Abh&auml;ngigkeiten n&ouml;tig ist. Bei
   * <code>true</code> werden auch die von dieser Klasse ben&ouml;tigten Klassen geladen.
   *
   * @param name Name der Klasse
   * @param resolve Option <code>true</code> um Abh&auml;ngigkeitem zu laden
   * @return die geladene Klasse, ist diese nicht ermittelbar, f&uuml;hrt der Aufruf zur Ausnahme
   *     <code>ClassNotFoundException</code>
   */
  protected synchronized Class loadClass(String name, boolean resolve)
      throws ClassNotFoundException {

    Class source;
    InputStream input;
    Iterator iterator;
    SecurityManager security;
    String packet;
    ZipEntry entry;
    ZipFile store;

    byte[] bytes;

    int cursor;
    int size;
    int volume;

    name = (name == null) ? "" : name.trim();

    if (name.length() == 0) return null;

    source = (Class) this.classes.get(name);

    if (source != null) return source;

    try {

      // die Berechtigung zur Definition der Klasse wird geprueft, wenn
      // ein entsprechender SecurityManager vorliegt, ohne ist Definition
      // aller Klassen zulaessig
      security = System.getSecurityManager();

      cursor = name.lastIndexOf('.');

      packet = (cursor > -1) ? name.substring(0, cursor) : "";

      // prueft die Berechtigung zum Laden der Klasse/Paket, liegt diese
      // Berechtigung nicht vor, fuehrt dies zur SecurityException
      if (security != null) security.checkPackageDefinition(packet);

      // das Package wird registriert
      if (super.getPackage(packet) == null)
        super.definePackage(packet, null, null, null, null, null, null, null);

    } catch (SecurityException exception) {

      if (this.loader == null) throw exception;

      this.loader.loadClass(name);
    }

    try {

      // die Klasse wird versucht als (System)Klasse zu laden
      source = (this.loader == null) ? null : this.loader.loadClass(name);

      if (source != null) {

        if (resolve) super.resolveClass(source);

        return source;
      }

    } catch (Exception exception) {

      source = null;
    }

    // alle Bibliotheken werden ermittelt
    iterator = this.libraries.iterator();

    for (store = null; iterator.hasNext(); ) {

      try {

        // das Zip-Archiv wird geoeffnet
        store = new ZipFile((File) iterator.next());

        // der Klassenname wird vereinheitlicht
        entry = store.getEntry(name.replace('.', '/').concat(".class"));

        if (entry != null) {

          input = store.getInputStream(entry);
          volume = (int) entry.getSize();
          bytes = new byte[volume];

          size = cursor = 0;

          // der Datenstrom wird ausgelesen
          while (volume > 0 && (size = input.read(bytes, cursor, volume)) >= 0) {

            cursor += size;
            volume -= size;
          }

          // die Klasse wird ueber den ClassLoader definiert
          source = super.defineClass(name, bytes, 0, bytes.length);

          // die Klasse wird als geladen registriert
          this.classes.put(name, source);

          // gegebenfalls werden die Abhaengigkeitem aufgeloest
          if (resolve) super.resolveClass(source);

          return source;
        }

      } catch (Throwable throwable) {

        // keine Fehlerbehandlung vorgesehen

      } finally {

        // das Zip-Archiv wird geschlossen
        try {
          store.close();
        } catch (Throwable throwable) {

          // keine Fehlerbehandlung vorgesehen
        }
      }
    }

    throw new ClassNotFoundException(name);
  }
 @Override
 public void checkPackageDefinition(final String pPkg) {
   if (finalSecurityManager != null) finalSecurityManager.checkPackageDefinition(pPkg);
 }