src/java.base/share/classes/jdk/internal/loader/BootLoader.java
author redestad
Wed, 17 Jul 2019 12:35:46 +0200
changeset 55693 9a97b1393e72
parent 52427 3c6aa484536c
permissions -rw-r--r--
8227587: Add internal privileged System.loadLibrary Reviewed-by: rriggs, mchung, chegar
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
36511
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
     1
/*
49285
4d2e3f5abb48 8194746: (fs) Add equivalents of Paths.get to Path interface
bpb
parents: 48995
diff changeset
     2
 * Copyright (c) 2015, 2018, Oracle and/or its affiliates. All rights reserved.
36511
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
     3
 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
     4
 *
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
     5
 * This code is free software; you can redistribute it and/or modify it
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
     6
 * under the terms of the GNU General Public License version 2 only, as
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
     7
 * published by the Free Software Foundation.  Oracle designates this
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
     8
 * particular file as subject to the "Classpath" exception as provided
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
     9
 * by Oracle in the LICENSE file that accompanied this code.
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
    10
 *
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
    11
 * This code is distributed in the hope that it will be useful, but WITHOUT
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
    12
 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
    13
 * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
    14
 * version 2 for more details (a copy is included in the LICENSE file that
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
    15
 * accompanied this code).
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
    16
 *
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
    17
 * You should have received a copy of the GNU General Public License version
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
    18
 * 2 along with this work; if not, write to the Free Software Foundation,
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
    19
 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
    20
 *
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
    21
 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
    22
 * or visit www.oracle.com if you need additional information or have any
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
    23
 * questions.
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
    24
 */
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
    25
package jdk.internal.loader;
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
    26
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
    27
import java.io.IOException;
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
    28
import java.io.InputStream;
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
    29
import java.lang.module.ModuleReference;
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
    30
import java.net.MalformedURLException;
37605
6f6cd967ec11 8154837: Class::getPackage with exploded modules when classes in modules defined to the boot loader
mchung
parents: 36972
diff changeset
    31
import java.net.URI;
36511
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
    32
import java.net.URL;
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
    33
import java.nio.file.Files;
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
    34
import java.nio.file.Path;
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
    35
import java.security.AccessController;
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
    36
import java.security.PrivilegedAction;
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
    37
import java.util.Arrays;
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
    38
import java.util.Enumeration;
36972
27147cde3256 8152115: (proxy) Examine performance of dynamic proxy creation
plevart
parents: 36511
diff changeset
    39
import java.util.concurrent.ConcurrentHashMap;
36511
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
    40
import java.util.jar.JarInputStream;
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
    41
import java.util.jar.Manifest;
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
    42
import java.util.stream.Stream;
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
    43
52427
3c6aa484536c 8211122: Reduce the number of internal classes made accessible to jdk.unsupported
mchung
parents: 50817
diff changeset
    44
import jdk.internal.access.JavaLangAccess;
3c6aa484536c 8211122: Reduce the number of internal classes made accessible to jdk.unsupported
mchung
parents: 50817
diff changeset
    45
import jdk.internal.access.SharedSecrets;
50744
6c306d54366d 8205533: Class.getPackage() fails with InternalError if class is defined to the bootstrap class loader but module is not in the boot layer
alanb
parents: 49528
diff changeset
    46
import jdk.internal.module.Modules;
36511
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
    47
import jdk.internal.module.ServicesCatalog;
50817
fa1e04811ff6 8066709: Make some JDK system properties read only
rriggs
parents: 50744
diff changeset
    48
import jdk.internal.util.StaticProperty;
36511
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
    49
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
    50
/**
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
    51
 * Find resources and packages in modules defined to the boot class loader or
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
    52
 * resources and packages on the "boot class path" specified via -Xbootclasspath/a.
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
    53
 */
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
    54
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
    55
public class BootLoader {
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
    56
    private BootLoader() { }
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
    57
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
    58
    // The unnamed module for the boot loader
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
    59
    private static final Module UNNAMED_MODULE;
50817
fa1e04811ff6 8066709: Make some JDK system properties read only
rriggs
parents: 50744
diff changeset
    60
    private static final String JAVA_HOME = StaticProperty.javaHome();
36511
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
    61
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
    62
    static {
44545
83b611b88ac8 8177530: Module system implementation refresh (4/2017)
alanb
parents: 44359
diff changeset
    63
        UNNAMED_MODULE = SharedSecrets.getJavaLangAccess().defineUnnamedModule(null);
36511
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
    64
        setBootLoaderUnnamedModule0(UNNAMED_MODULE);
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
    65
    }
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
    66
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
    67
    // ServiceCatalog for the boot class loader
37779
7c84df693837 8154956: Module system implementation refresh (4/2016)
alanb
parents: 37605
diff changeset
    68
    private static final ServicesCatalog SERVICES_CATALOG = ServicesCatalog.create();
36511
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
    69
48995
58bec53828ba 8198481: Coding style cleanups for src/java.base/share/classes/jdk/internal/loader
martin
parents: 47216
diff changeset
    70
    // ClassLoaderValue map for the boot class loader
42338
a60f280f803c 8169069: Module system implementation refresh (11/2016)
alanb
parents: 37779
diff changeset
    71
    private static final ConcurrentHashMap<?, ?> CLASS_LOADER_VALUE_MAP
a60f280f803c 8169069: Module system implementation refresh (11/2016)
alanb
parents: 37779
diff changeset
    72
        = new ConcurrentHashMap<>();
36972
27147cde3256 8152115: (proxy) Examine performance of dynamic proxy creation
plevart
parents: 36511
diff changeset
    73
36511
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
    74
    /**
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
    75
     * Returns the unnamed module for the boot loader.
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
    76
     */
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
    77
    public static Module getUnnamedModule() {
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
    78
        return UNNAMED_MODULE;
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
    79
    }
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
    80
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
    81
    /**
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
    82
     * Returns the ServiceCatalog for modules defined to the boot class loader.
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
    83
     */
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
    84
    public static ServicesCatalog getServicesCatalog() {
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
    85
        return SERVICES_CATALOG;
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
    86
    }
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
    87
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
    88
    /**
36972
27147cde3256 8152115: (proxy) Examine performance of dynamic proxy creation
plevart
parents: 36511
diff changeset
    89
     * Returns the ClassLoaderValue map for the boot class loader.
27147cde3256 8152115: (proxy) Examine performance of dynamic proxy creation
plevart
parents: 36511
diff changeset
    90
     */
27147cde3256 8152115: (proxy) Examine performance of dynamic proxy creation
plevart
parents: 36511
diff changeset
    91
    public static ConcurrentHashMap<?, ?> getClassLoaderValueMap() {
27147cde3256 8152115: (proxy) Examine performance of dynamic proxy creation
plevart
parents: 36511
diff changeset
    92
        return CLASS_LOADER_VALUE_MAP;
27147cde3256 8152115: (proxy) Examine performance of dynamic proxy creation
plevart
parents: 36511
diff changeset
    93
    }
27147cde3256 8152115: (proxy) Examine performance of dynamic proxy creation
plevart
parents: 36511
diff changeset
    94
27147cde3256 8152115: (proxy) Examine performance of dynamic proxy creation
plevart
parents: 36511
diff changeset
    95
    /**
44359
c6761862ca0b 8174823: Module system implementation refresh (3/2017)
alanb
parents: 44003
diff changeset
    96
     * Returns {@code true} if there is a class path associated with the
c6761862ca0b 8174823: Module system implementation refresh (3/2017)
alanb
parents: 44003
diff changeset
    97
     * BootLoader.
c6761862ca0b 8174823: Module system implementation refresh (3/2017)
alanb
parents: 44003
diff changeset
    98
     */
c6761862ca0b 8174823: Module system implementation refresh (3/2017)
alanb
parents: 44003
diff changeset
    99
    public static boolean hasClassPath() {
c6761862ca0b 8174823: Module system implementation refresh (3/2017)
alanb
parents: 44003
diff changeset
   100
        return ClassLoaders.bootLoader().hasClassPath();
c6761862ca0b 8174823: Module system implementation refresh (3/2017)
alanb
parents: 44003
diff changeset
   101
    }
c6761862ca0b 8174823: Module system implementation refresh (3/2017)
alanb
parents: 44003
diff changeset
   102
c6761862ca0b 8174823: Module system implementation refresh (3/2017)
alanb
parents: 44003
diff changeset
   103
    /**
49528
c1eb35eb5f38 8200125: Fix some classloader/module typos
martin
parents: 49285
diff changeset
   104
     * Registers a module with this class loader so that its classes
c1eb35eb5f38 8200125: Fix some classloader/module typos
martin
parents: 49285
diff changeset
   105
     * (and resources) become visible via this class loader.
36511
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   106
     */
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   107
    public static void loadModule(ModuleReference mref) {
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   108
        ClassLoaders.bootLoader().loadModule(mref);
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   109
    }
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   110
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   111
    /**
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   112
     * Loads the Class object with the given name defined to the boot loader.
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   113
     */
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   114
    public static Class<?> loadClassOrNull(String name) {
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   115
        return ClassLoaders.bootLoader().loadClassOrNull(name);
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   116
    }
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   117
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   118
    /**
42338
a60f280f803c 8169069: Module system implementation refresh (11/2016)
alanb
parents: 37779
diff changeset
   119
     * Loads the Class object with the given name in the given module
a60f280f803c 8169069: Module system implementation refresh (11/2016)
alanb
parents: 37779
diff changeset
   120
     * defined to the boot loader. Returns {@code null} if not found.
a60f280f803c 8169069: Module system implementation refresh (11/2016)
alanb
parents: 37779
diff changeset
   121
     */
a60f280f803c 8169069: Module system implementation refresh (11/2016)
alanb
parents: 37779
diff changeset
   122
    public static Class<?> loadClass(Module module, String name) {
a60f280f803c 8169069: Module system implementation refresh (11/2016)
alanb
parents: 37779
diff changeset
   123
        Class<?> c = loadClassOrNull(name);
a60f280f803c 8169069: Module system implementation refresh (11/2016)
alanb
parents: 37779
diff changeset
   124
        if (c != null && c.getModule() == module) {
a60f280f803c 8169069: Module system implementation refresh (11/2016)
alanb
parents: 37779
diff changeset
   125
            return c;
a60f280f803c 8169069: Module system implementation refresh (11/2016)
alanb
parents: 37779
diff changeset
   126
        } else {
a60f280f803c 8169069: Module system implementation refresh (11/2016)
alanb
parents: 37779
diff changeset
   127
            return null;
a60f280f803c 8169069: Module system implementation refresh (11/2016)
alanb
parents: 37779
diff changeset
   128
        }
a60f280f803c 8169069: Module system implementation refresh (11/2016)
alanb
parents: 37779
diff changeset
   129
    }
a60f280f803c 8169069: Module system implementation refresh (11/2016)
alanb
parents: 37779
diff changeset
   130
a60f280f803c 8169069: Module system implementation refresh (11/2016)
alanb
parents: 37779
diff changeset
   131
    /**
55693
9a97b1393e72 8227587: Add internal privileged System.loadLibrary
redestad
parents: 52427
diff changeset
   132
     * Loads a library from the system path.
9a97b1393e72 8227587: Add internal privileged System.loadLibrary
redestad
parents: 52427
diff changeset
   133
     */
9a97b1393e72 8227587: Add internal privileged System.loadLibrary
redestad
parents: 52427
diff changeset
   134
    public static void loadLibrary(String library) {
9a97b1393e72 8227587: Add internal privileged System.loadLibrary
redestad
parents: 52427
diff changeset
   135
        if (System.getSecurityManager() == null) {
9a97b1393e72 8227587: Add internal privileged System.loadLibrary
redestad
parents: 52427
diff changeset
   136
            SharedSecrets.getJavaLangAccess().loadLibrary(BootLoader.class, library);
9a97b1393e72 8227587: Add internal privileged System.loadLibrary
redestad
parents: 52427
diff changeset
   137
        } else {
9a97b1393e72 8227587: Add internal privileged System.loadLibrary
redestad
parents: 52427
diff changeset
   138
            AccessController.doPrivileged(
9a97b1393e72 8227587: Add internal privileged System.loadLibrary
redestad
parents: 52427
diff changeset
   139
                new java.security.PrivilegedAction<>() {
9a97b1393e72 8227587: Add internal privileged System.loadLibrary
redestad
parents: 52427
diff changeset
   140
                    public Void run() {
9a97b1393e72 8227587: Add internal privileged System.loadLibrary
redestad
parents: 52427
diff changeset
   141
                        SharedSecrets.getJavaLangAccess().loadLibrary(BootLoader.class, library);
9a97b1393e72 8227587: Add internal privileged System.loadLibrary
redestad
parents: 52427
diff changeset
   142
                        return null;
9a97b1393e72 8227587: Add internal privileged System.loadLibrary
redestad
parents: 52427
diff changeset
   143
                    }
9a97b1393e72 8227587: Add internal privileged System.loadLibrary
redestad
parents: 52427
diff changeset
   144
                });
9a97b1393e72 8227587: Add internal privileged System.loadLibrary
redestad
parents: 52427
diff changeset
   145
        }
9a97b1393e72 8227587: Add internal privileged System.loadLibrary
redestad
parents: 52427
diff changeset
   146
    }
9a97b1393e72 8227587: Add internal privileged System.loadLibrary
redestad
parents: 52427
diff changeset
   147
9a97b1393e72 8227587: Add internal privileged System.loadLibrary
redestad
parents: 52427
diff changeset
   148
    /**
42338
a60f280f803c 8169069: Module system implementation refresh (11/2016)
alanb
parents: 37779
diff changeset
   149
     * Returns a URL to a resource in a module defined to the boot loader.
36511
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   150
     */
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   151
    public static URL findResource(String mn, String name) throws IOException {
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   152
        return ClassLoaders.bootLoader().findResource(mn, name);
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   153
    }
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   154
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   155
    /**
42338
a60f280f803c 8169069: Module system implementation refresh (11/2016)
alanb
parents: 37779
diff changeset
   156
     * Returns an input stream to a resource in a module defined to the
36511
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   157
     * boot loader.
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   158
     */
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   159
    public static InputStream findResourceAsStream(String mn, String name)
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   160
        throws IOException
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   161
    {
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   162
        return ClassLoaders.bootLoader().findResourceAsStream(mn, name);
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   163
    }
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   164
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   165
    /**
42338
a60f280f803c 8169069: Module system implementation refresh (11/2016)
alanb
parents: 37779
diff changeset
   166
     * Returns the URL to the given resource in any of the modules
a60f280f803c 8169069: Module system implementation refresh (11/2016)
alanb
parents: 37779
diff changeset
   167
     * defined to the boot loader and the boot class path.
36511
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   168
     */
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   169
    public static URL findResource(String name) {
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   170
        return ClassLoaders.bootLoader().findResource(name);
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   171
    }
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   172
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   173
    /**
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   174
     * Returns an Iterator to iterate over the resources of the given name
42338
a60f280f803c 8169069: Module system implementation refresh (11/2016)
alanb
parents: 37779
diff changeset
   175
     * in any of the modules defined to the boot loader.
36511
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   176
     */
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   177
    public static Enumeration<URL> findResources(String name) throws IOException {
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   178
        return ClassLoaders.bootLoader().findResources(name);
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   179
    }
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   180
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   181
    /**
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   182
     * Define a package for the given class to the boot loader, if not already
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   183
     * defined.
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   184
     */
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   185
    public static Package definePackage(Class<?> c) {
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   186
        return getDefinedPackage(c.getPackageName());
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   187
    }
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   188
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   189
    /**
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   190
     * Returns the Package of the given name defined to the boot loader or null
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   191
     * if the package has not been defined.
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   192
     */
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   193
    public static Package getDefinedPackage(String pn) {
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   194
        Package pkg = ClassLoaders.bootLoader().getDefinedPackage(pn);
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   195
        if (pkg == null) {
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   196
            String location = getSystemPackageLocation(pn.replace('.', '/'));
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   197
            if (location != null) {
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   198
                pkg = PackageHelper.definePackage(pn.intern(), location);
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   199
            }
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   200
        }
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   201
        return pkg;
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   202
    }
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   203
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   204
    /**
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   205
     * Returns a stream of the packages defined to the boot loader.
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   206
     */
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   207
    public static Stream<Package> packages() {
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   208
        return Arrays.stream(getSystemPackageNames())
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   209
                     .map(name -> getDefinedPackage(name.replace('/', '.')));
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   210
    }
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   211
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   212
    /**
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   213
     * Helper class to define {@code Package} objects for packages in modules
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   214
     * defined to the boot loader.
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   215
     */
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   216
    static class PackageHelper {
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   217
        private static final JavaLangAccess JLA = SharedSecrets.getJavaLangAccess();
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   218
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   219
        /**
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   220
         * Define the {@code Package} with the given name. The specified
37605
6f6cd967ec11 8154837: Class::getPackage with exploded modules when classes in modules defined to the boot loader
mchung
parents: 36972
diff changeset
   221
         * location is a jrt URL to a named module in the run-time image,
6f6cd967ec11 8154837: Class::getPackage with exploded modules when classes in modules defined to the boot loader
mchung
parents: 36972
diff changeset
   222
         * a file URL to a module in an exploded run-time image, or a file
6f6cd967ec11 8154837: Class::getPackage with exploded modules when classes in modules defined to the boot loader
mchung
parents: 36972
diff changeset
   223
         * path to an entry on the boot class path (java agent Boot-Class-Path
36511
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   224
         * or -Xbootclasspath/a.
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   225
         *
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   226
         * <p> If the given location is a JAR file containing a manifest,
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   227
         * the defined Package contains the versioning information from
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   228
         * the manifest, if present.
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   229
         *
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   230
         * @param name     package name
37605
6f6cd967ec11 8154837: Class::getPackage with exploded modules when classes in modules defined to the boot loader
mchung
parents: 36972
diff changeset
   231
         * @param location location where the package is (jrt URL or file URL
6f6cd967ec11 8154837: Class::getPackage with exploded modules when classes in modules defined to the boot loader
mchung
parents: 36972
diff changeset
   232
         *                 for a named module in the run-time or exploded image;
6f6cd967ec11 8154837: Class::getPackage with exploded modules when classes in modules defined to the boot loader
mchung
parents: 36972
diff changeset
   233
         *                 a file path for a package from -Xbootclasspath/a)
36511
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   234
         */
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   235
        static Package definePackage(String name, String location) {
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   236
            Module module = findModule(location);
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   237
            if (module != null) {
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   238
                // named module from runtime image or exploded module
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   239
                if (name.isEmpty())
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   240
                    throw new InternalError("empty package in " + location);
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   241
                return JLA.definePackage(ClassLoaders.bootLoader(), name, module);
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   242
            }
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   243
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   244
            // package in unnamed module (-Xbootclasspath/a)
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   245
            URL url = toFileURL(location);
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   246
            Manifest man = url != null ? getManifest(location) : null;
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   247
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   248
            return ClassLoaders.bootLoader().defineOrCheckPackage(name, man, url);
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   249
        }
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   250
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   251
        /**
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   252
         * Finds the module at the given location defined to the boot loader.
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   253
         * The module is either in runtime image or exploded image.
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   254
         * Otherwise this method returns null.
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   255
         */
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   256
        private static Module findModule(String location) {
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   257
            String mn = null;
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   258
            if (location.startsWith("jrt:/")) {
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   259
                // named module in runtime image ("jrt:/".length() == 5)
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   260
                mn = location.substring(5, location.length());
37605
6f6cd967ec11 8154837: Class::getPackage with exploded modules when classes in modules defined to the boot loader
mchung
parents: 36972
diff changeset
   261
            } else if (location.startsWith("file:/")) {
36511
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   262
                // named module in exploded image
49285
4d2e3f5abb48 8194746: (fs) Add equivalents of Paths.get to Path interface
bpb
parents: 48995
diff changeset
   263
                Path path = Path.of(URI.create(location));
4d2e3f5abb48 8194746: (fs) Add equivalents of Paths.get to Path interface
bpb
parents: 48995
diff changeset
   264
                Path modulesDir = Path.of(JAVA_HOME, "modules");
36511
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   265
                if (path.startsWith(modulesDir)) {
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   266
                    mn = path.getFileName().toString();
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   267
                }
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   268
            }
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   269
50744
6c306d54366d 8205533: Class.getPackage() fails with InternalError if class is defined to the bootstrap class loader but module is not in the boot layer
alanb
parents: 49528
diff changeset
   270
            // return the Module object for the module name. The Module may
6c306d54366d 8205533: Class.getPackage() fails with InternalError if class is defined to the bootstrap class loader but module is not in the boot layer
alanb
parents: 49528
diff changeset
   271
            // in the boot layer or a child layer for the case that the module
6c306d54366d 8205533: Class.getPackage() fails with InternalError if class is defined to the bootstrap class loader but module is not in the boot layer
alanb
parents: 49528
diff changeset
   272
            // is loaded into a running VM
36511
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   273
            if (mn != null) {
50744
6c306d54366d 8205533: Class.getPackage() fails with InternalError if class is defined to the bootstrap class loader but module is not in the boot layer
alanb
parents: 49528
diff changeset
   274
                String name = mn;
6c306d54366d 8205533: Class.getPackage() fails with InternalError if class is defined to the bootstrap class loader but module is not in the boot layer
alanb
parents: 49528
diff changeset
   275
                return Modules.findLoadedModule(mn)
6c306d54366d 8205533: Class.getPackage() fails with InternalError if class is defined to the bootstrap class loader but module is not in the boot layer
alanb
parents: 49528
diff changeset
   276
                    .orElseThrow(() -> new InternalError(name + " not loaded"));
6c306d54366d 8205533: Class.getPackage() fails with InternalError if class is defined to the bootstrap class loader but module is not in the boot layer
alanb
parents: 49528
diff changeset
   277
            } else {
6c306d54366d 8205533: Class.getPackage() fails with InternalError if class is defined to the bootstrap class loader but module is not in the boot layer
alanb
parents: 49528
diff changeset
   278
                return null;
36511
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   279
            }
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   280
        }
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   281
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   282
        /**
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   283
         * Returns URL if the given location is a regular file path.
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   284
         */
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   285
        private static URL toFileURL(String location) {
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   286
            return AccessController.doPrivileged(new PrivilegedAction<>() {
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   287
                public URL run() {
49285
4d2e3f5abb48 8194746: (fs) Add equivalents of Paths.get to Path interface
bpb
parents: 48995
diff changeset
   288
                    Path path = Path.of(location);
36511
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   289
                    if (Files.isRegularFile(path)) {
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   290
                        try {
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   291
                            return path.toUri().toURL();
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   292
                        } catch (MalformedURLException e) {}
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   293
                    }
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   294
                    return null;
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   295
                }
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   296
            });
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   297
        }
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   298
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   299
        /**
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   300
         * Returns the Manifest if the given location is a JAR file
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   301
         * containing a manifest.
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   302
         */
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   303
        private static Manifest getManifest(String location) {
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   304
            return AccessController.doPrivileged(new PrivilegedAction<>() {
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   305
                public Manifest run() {
49285
4d2e3f5abb48 8194746: (fs) Add equivalents of Paths.get to Path interface
bpb
parents: 48995
diff changeset
   306
                    Path jar = Path.of(location);
36511
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   307
                    try (InputStream in = Files.newInputStream(jar);
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   308
                         JarInputStream jis = new JarInputStream(in, false)) {
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   309
                        return jis.getManifest();
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   310
                    } catch (IOException e) {
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   311
                        return null;
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   312
                    }
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   313
                }
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   314
            });
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   315
        }
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   316
    }
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   317
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   318
    /**
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   319
     * Returns an array of the binary name of the packages defined by
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   320
     * the boot loader, in VM internal form (forward slashes instead of dot).
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   321
     */
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   322
    private static native String[] getSystemPackageNames();
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   323
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   324
    /**
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   325
     * Returns the location of the package of the given name, if
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   326
     * defined by the boot loader; otherwise {@code null} is returned.
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   327
     *
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   328
     * The location may be a module from the runtime image or exploded image,
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   329
     * or from the boot class append path (i.e. -Xbootclasspath/a or
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   330
     * BOOT-CLASS-PATH attribute specified in java agent).
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   331
     */
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   332
    private static native String getSystemPackageLocation(String name);
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   333
    private static native void setBootLoaderUnnamedModule0(Module module);
9d0388c6b336 8142968: Module System implementation
alanb
parents:
diff changeset
   334
}