50 import java.util.Map; |
50 import java.util.Map; |
51 import java.util.Optional; |
51 import java.util.Optional; |
52 import java.util.ServiceLoader; |
52 import java.util.ServiceLoader; |
53 import java.util.Set; |
53 import java.util.Set; |
54 import java.util.stream.Collectors; |
54 import java.util.stream.Collectors; |
|
55 |
55 import jdk.test.lib.compiler.CompilerUtils; |
56 import jdk.test.lib.compiler.CompilerUtils; |
56 |
57 |
57 import org.testng.annotations.BeforeTest; |
58 import org.testng.annotations.BeforeTest; |
58 import org.testng.annotations.Test; |
59 import org.testng.annotations.Test; |
59 import static org.testng.Assert.*; |
60 import static org.testng.Assert.*; |
134 /** |
135 /** |
135 * Basic test of ModuleLayer.defineModulesWithOneLoader where one of the |
136 * Basic test of ModuleLayer.defineModulesWithOneLoader where one of the |
136 * modules is a service provider module. |
137 * modules is a service provider module. |
137 * |
138 * |
138 * Test scenario: |
139 * Test scenario: |
139 * m1 requires m2 and m3 |
140 * m1 requires m2 and m3 |
140 * m1 uses S |
141 * m1 uses S |
141 * m4 provides S with ... |
142 * m4 provides S with ... |
142 */ |
143 */ |
143 public void testServicesWithOneLoader() throws Exception { |
144 public void testServicesWithOneLoader() throws Exception { |
144 Configuration cf = resolveAndBind("m1"); |
145 Configuration cf = resolveAndBind("m1"); |
145 |
146 |
146 ClassLoader scl = ClassLoader.getSystemClassLoader(); |
147 ClassLoader scl = ClassLoader.getSystemClassLoader(); |
173 /** |
174 /** |
174 * Basic test of ModuleLayer.defineModulesWithManyLoaders where one of the |
175 * Basic test of ModuleLayer.defineModulesWithManyLoaders where one of the |
175 * modules is a service provider module. |
176 * modules is a service provider module. |
176 * |
177 * |
177 * Test scenario: |
178 * Test scenario: |
178 * m1 requires m2 and m3 |
179 * m1 requires m2 and m3 |
179 * m1 uses S |
180 * m1 uses S |
180 * m4 provides S with ... |
181 * m4 provides S with ... |
181 */ |
182 */ |
182 public void testServicesWithManyLoaders() throws Exception { |
183 public void testServicesWithManyLoaders() throws Exception { |
183 Configuration cf = resolveAndBind("m1"); |
184 Configuration cf = resolveAndBind("m1"); |
184 |
185 |
185 ClassLoader scl = ClassLoader.getSystemClassLoader(); |
186 ClassLoader scl = ClassLoader.getSystemClassLoader(); |
232 |
233 |
233 // one loader |
234 // one loader |
234 ModuleLayer layer = ModuleLayer.boot().defineModulesWithOneLoader(cf, parent); |
235 ModuleLayer layer = ModuleLayer.boot().defineModulesWithOneLoader(cf, parent); |
235 testLoad(layer, cn); |
236 testLoad(layer, cn); |
236 |
237 |
237 // one loader with boot loader as parent |
238 // one loader with boot loader as parent |
238 layer = ModuleLayer.boot().defineModulesWithOneLoader(cf, null); |
239 layer = ModuleLayer.boot().defineModulesWithOneLoader(cf, null); |
239 testLoadFail(layer, cn); |
240 testLoadFail(layer, cn); |
240 |
241 |
241 // many loaders |
242 // many loaders |
242 layer = ModuleLayer.boot().defineModulesWithManyLoaders(cf, parent); |
243 layer = ModuleLayer.boot().defineModulesWithManyLoaders(cf, parent); |
250 |
251 |
251 /** |
252 /** |
252 * Test defineModulesWithXXX when modules that have overlapping packages. |
253 * Test defineModulesWithXXX when modules that have overlapping packages. |
253 * |
254 * |
254 * Test scenario: |
255 * Test scenario: |
255 * m1 exports p |
256 * m1 exports p |
256 * m2 exports p |
257 * m2 exports p |
257 */ |
258 */ |
258 public void testOverlappingPackages() { |
259 public void testOverlappingPackages() { |
259 ModuleDescriptor descriptor1 |
260 ModuleDescriptor descriptor1 |
260 = ModuleDescriptor.newModule("m1").exports("p").build(); |
261 = ModuleDescriptor.newModule("m1").exports("p").build(); |
261 |
262 |
262 ModuleDescriptor descriptor2 |
263 ModuleDescriptor descriptor2 |
263 = ModuleDescriptor.newModule("m2").exports("p").build(); |
264 = ModuleDescriptor.newModule("m2").exports("p").build(); |
264 |
265 |
265 ModuleFinder finder = ModuleUtils.finderOf(descriptor1, descriptor2); |
266 ModuleFinder finder = ModuleUtils.finderOf(descriptor1, descriptor2); |
266 |
267 |
267 Configuration cf = ModuleLayer.boot() |
268 Configuration cf = ModuleLayer.boot() |
268 .configuration() |
269 .configuration() |
269 .resolve(finder, ModuleFinder.of(), Set.of("m1", "m2")); |
270 .resolve(finder, ModuleFinder.of(), Set.of("m1", "m2")); |
270 |
271 |
271 // cannot define both module m1 and m2 to the same class loader |
272 // cannot define both module m1 and m2 to the same class loader |
272 try { |
273 try { |
273 ModuleLayer.boot().defineModulesWithOneLoader(cf, null); |
274 ModuleLayer.boot().defineModulesWithOneLoader(cf, null); |
274 assertTrue(false); |
275 assertTrue(false); |
282 |
283 |
283 /** |
284 /** |
284 * Test ModuleLayer.defineModulesWithXXX with split delegation. |
285 * Test ModuleLayer.defineModulesWithXXX with split delegation. |
285 * |
286 * |
286 * Test scenario: |
287 * Test scenario: |
287 * layer1: m1 exports p, m2 exports p |
288 * layer1: m1 exports p, m2 exports p |
288 * layer2: m3 reads m1, m4 reads m2 |
289 * layer2: m3 reads m1, m4 reads m2 |
289 */ |
290 */ |
290 public void testSplitDelegation() { |
291 public void testSplitDelegation() { |
291 ModuleDescriptor descriptor1 |
292 ModuleDescriptor descriptor1 |
292 = ModuleDescriptor.newModule("m1").exports("p").build(); |
293 = ModuleDescriptor.newModule("m1").exports("p").build(); |
293 |
294 |
294 ModuleDescriptor descriptor2 |
295 ModuleDescriptor descriptor2 |
295 = ModuleDescriptor.newModule("m2").exports("p").build(); |
296 = ModuleDescriptor.newModule("m2").exports("p").build(); |
296 |
297 |
297 ModuleFinder finder1 = ModuleUtils.finderOf(descriptor1, descriptor2); |
298 ModuleFinder finder1 = ModuleUtils.finderOf(descriptor1, descriptor2); |
298 |
299 |
299 Configuration cf1 = ModuleLayer.boot() |
300 Configuration cf1 = ModuleLayer.boot() |
300 .configuration() |
301 .configuration() |
301 .resolve(finder1, ModuleFinder.of(), Set.of("m1", "m2")); |
302 .resolve(finder1, ModuleFinder.of(), Set.of("m1", "m2")); |
302 |
303 |
303 ModuleLayer layer1 = ModuleLayer.boot().defineModulesWithManyLoaders(cf1, null); |
304 ModuleLayer layer1 = ModuleLayer.boot().defineModulesWithManyLoaders(cf1, null); |
304 checkLayer(layer1, "m1", "m2"); |
305 checkLayer(layer1, "m1", "m2"); |
305 |
306 |
306 ModuleDescriptor descriptor3 |
307 ModuleDescriptor descriptor3 |
307 = ModuleDescriptor.newModule("m3").requires("m1").build(); |
308 = ModuleDescriptor.newModule("m3").requires("m1").build(); |
308 |
309 |
309 ModuleDescriptor descriptor4 |
310 ModuleDescriptor descriptor4 |
310 = ModuleDescriptor.newModule("m4").requires("m2").build(); |
311 = ModuleDescriptor.newModule("m4").requires("m2").build(); |
311 |
312 |
312 ModuleFinder finder2 = ModuleUtils.finderOf(descriptor3, descriptor4); |
313 ModuleFinder finder2 = ModuleUtils.finderOf(descriptor3, descriptor4); |
313 |
314 |
314 Configuration cf2 = cf1.resolve(finder2, ModuleFinder.of(), |
315 Configuration cf2 = cf1.resolve(finder2, ModuleFinder.of(), |
315 Set.of("m3", "m4")); |
316 Set.of("m3", "m4")); |
316 |
317 |
317 // package p cannot be supplied by two class loaders |
318 // package p cannot be supplied by two class loaders |
318 try { |
319 try { |
319 layer1.defineModulesWithOneLoader(cf2, null); |
320 layer1.defineModulesWithOneLoader(cf2, null); |
320 assertTrue(false); |
321 assertTrue(false); |
329 /** |
330 /** |
330 * Test ModuleLayer.defineModulesWithXXX when the modules that override same |
331 * Test ModuleLayer.defineModulesWithXXX when the modules that override same |
331 * named modules in the parent layer. |
332 * named modules in the parent layer. |
332 * |
333 * |
333 * Test scenario: |
334 * Test scenario: |
334 * layer1: m1, m2, m3 => same loader |
335 * layer1: m1, m2, m3 => same loader |
335 * layer2: m1, m2, m4 => same loader |
336 * layer2: m1, m2, m4 => same loader |
336 */ |
337 */ |
337 public void testOverriding1() throws Exception { |
338 public void testOverriding1() throws Exception { |
338 Configuration cf1 = resolve("m1"); |
339 Configuration cf1 = resolve("m1"); |
339 |
340 |
340 ModuleLayer layer1 = ModuleLayer.boot().defineModulesWithOneLoader(cf1, null); |
341 ModuleLayer layer1 = ModuleLayer.boot().defineModulesWithOneLoader(cf1, null); |
341 checkLayer(layer1, "m1", "m2", "m3"); |
342 checkLayer(layer1, "m1", "m2", "m3"); |
342 |
343 |
343 ModuleFinder finder = ModuleFinder.of(MODS_DIR); |
344 ModuleFinder finder = ModuleFinder.of(MODS_DIR); |
344 Configuration cf2 = cf1.resolve(finder, ModuleFinder.of(), |
345 Configuration cf2 = cf1.resolve(finder, ModuleFinder.of(), |
345 Set.of("m1")); |
346 Set.of("m1")); |
346 |
347 |
347 ModuleLayer layer2 = layer1.defineModulesWithOneLoader(cf2, null); |
348 ModuleLayer layer2 = layer1.defineModulesWithOneLoader(cf2, null); |
348 checkLayer(layer2, "m1", "m2", "m3"); |
349 checkLayer(layer2, "m1", "m2", "m3"); |
349 invoke(layer1, "m1", "p.Main"); |
350 invoke(layer1, "m1", "p.Main"); |
350 |
351 |
376 /** |
377 /** |
377 * Test Layer defineModulesWithXXX when the modules that override same |
378 * Test Layer defineModulesWithXXX when the modules that override same |
378 * named modules in the parent layer. |
379 * named modules in the parent layer. |
379 * |
380 * |
380 * Test scenario: |
381 * Test scenario: |
381 * layer1: m1, m2, m3 => loader pool |
382 * layer1: m1, m2, m3 => loader pool |
382 * layer2: m1, m2, m3 => loader pool |
383 * layer2: m1, m2, m3 => loader pool |
383 */ |
384 */ |
384 public void testOverriding2() throws Exception { |
385 public void testOverriding2() throws Exception { |
385 Configuration cf1 = resolve("m1"); |
386 Configuration cf1 = resolve("m1"); |
386 |
387 |
387 ModuleLayer layer1 = ModuleLayer.boot().defineModulesWithManyLoaders(cf1, null); |
388 ModuleLayer layer1 = ModuleLayer.boot().defineModulesWithManyLoaders(cf1, null); |
388 checkLayer(layer1, "m1", "m2", "m3"); |
389 checkLayer(layer1, "m1", "m2", "m3"); |
389 |
390 |
390 ModuleFinder finder = ModuleFinder.of(MODS_DIR); |
391 ModuleFinder finder = ModuleFinder.of(MODS_DIR); |
391 Configuration cf2 = cf1.resolve(finder, ModuleFinder.of(), |
392 Configuration cf2 = cf1.resolve(finder, ModuleFinder.of(), |
392 Set.of("m1")); |
393 Set.of("m1")); |
393 |
394 |
394 ModuleLayer layer2 = layer1.defineModulesWithManyLoaders(cf2, null); |
395 ModuleLayer layer2 = layer1.defineModulesWithManyLoaders(cf2, null); |
395 checkLayer(layer2, "m1", "m2", "m3"); |
396 checkLayer(layer2, "m1", "m2", "m3"); |
396 invoke(layer1, "m1", "p.Main"); |
397 invoke(layer1, "m1", "p.Main"); |
397 |
398 |
480 checkLayer(layer1, "m1", "m2", "m3"); |
481 checkLayer(layer1, "m1", "m2", "m3"); |
481 |
482 |
482 ModuleFinder finder = finderFor("m1", "m3"); |
483 ModuleFinder finder = finderFor("m1", "m3"); |
483 |
484 |
484 Configuration cf2 = cf1.resolve(finder, ModuleFinder.of(), |
485 Configuration cf2 = cf1.resolve(finder, ModuleFinder.of(), |
485 Set.of("m1")); |
486 Set.of("m1")); |
486 |
487 |
487 ModuleLayer layer2 = layer1.defineModulesWithOneLoader(cf2, null); |
488 ModuleLayer layer2 = layer1.defineModulesWithOneLoader(cf2, null); |
488 checkLayer(layer2, "m1", "m3"); |
489 checkLayer(layer2, "m1", "m3"); |
489 invoke(layer1, "m1", "p.Main"); |
490 invoke(layer1, "m1", "p.Main"); |
490 |
491 |
515 checkLayer(layer1, "m1", "m2", "m3"); |
516 checkLayer(layer1, "m1", "m2", "m3"); |
516 |
517 |
517 ModuleFinder finder = finderFor("m1", "m3"); |
518 ModuleFinder finder = finderFor("m1", "m3"); |
518 |
519 |
519 Configuration cf2 = cf1.resolve(finder, ModuleFinder.of(), |
520 Configuration cf2 = cf1.resolve(finder, ModuleFinder.of(), |
520 Set.of("m1")); |
521 Set.of("m1")); |
521 |
522 |
522 ModuleLayer layer2 = layer1.defineModulesWithManyLoaders(cf2, null); |
523 ModuleLayer layer2 = layer1.defineModulesWithManyLoaders(cf2, null); |
523 checkLayer(layer2, "m1", "m3"); |
524 checkLayer(layer2, "m1", "m3"); |
524 invoke(layer1, "m1", "p.Main"); |
525 invoke(layer1, "m1", "p.Main"); |
525 |
526 |
548 assertTrue(loader4.loadClass("w.Hello").getClassLoader() == loader6); |
549 assertTrue(loader4.loadClass("w.Hello").getClassLoader() == loader6); |
549 |
550 |
550 assertTrue(loader6.loadClass("w.Hello").getClassLoader() == loader6); |
551 assertTrue(loader6.loadClass("w.Hello").getClassLoader() == loader6); |
551 } |
552 } |
552 |
553 |
553 |
|
554 /** |
554 /** |
555 * Basic test for locating resources with a class loader created by |
555 * Basic test for locating resources with a class loader created by |
556 * defineModulesWithOneLoader. |
556 * defineModulesWithOneLoader. |
557 */ |
557 */ |
558 public void testResourcesWithOneLoader() throws Exception { |
558 public void testResourcesWithOneLoader() throws Exception { |
|
559 testResourcesWithOneLoader(ClassLoader.getSystemClassLoader()); |
|
560 testResourcesWithOneLoader(null); |
|
561 } |
|
562 |
|
563 /** |
|
564 * Test locating resources with the class loader created by |
|
565 * defineModulesWithOneLoader. The class loader has the given class |
|
566 * loader as its parent. |
|
567 */ |
|
568 void testResourcesWithOneLoader(ClassLoader parent) throws Exception { |
559 Configuration cf = resolve("m1"); |
569 Configuration cf = resolve("m1"); |
560 ClassLoader scl = ClassLoader.getSystemClassLoader(); |
570 ModuleLayer layer = ModuleLayer.boot().defineModulesWithOneLoader(cf, parent); |
561 ModuleLayer layer = ModuleLayer.boot().defineModulesWithOneLoader(cf, scl); |
|
562 |
571 |
563 ClassLoader loader = layer.findLoader("m1"); |
572 ClassLoader loader = layer.findLoader("m1"); |
564 assertNotNull(loader); |
573 assertNotNull(loader); |
|
574 assertTrue(loader.getParent() == parent); |
565 |
575 |
566 // check that getResource and getResources are consistent |
576 // check that getResource and getResources are consistent |
567 URL url1 = loader.getResource("module-info.class"); |
577 URL url1 = loader.getResource("module-info.class"); |
568 URL url2 = loader.getResources("module-info.class").nextElement(); |
578 URL url2 = loader.getResources("module-info.class").nextElement(); |
569 assertEquals(url1.toURI(), url2.toURI()); |
579 assertEquals(url1.toURI(), url2.toURI()); |
605 /** |
615 /** |
606 * Basic test for locating resources with class loaders created by |
616 * Basic test for locating resources with class loaders created by |
607 * defineModulesWithManyLoaders. |
617 * defineModulesWithManyLoaders. |
608 */ |
618 */ |
609 public void testResourcesWithManyLoaders() throws Exception { |
619 public void testResourcesWithManyLoaders() throws Exception { |
|
620 testResourcesWithManyLoaders(ClassLoader.getSystemClassLoader()); |
|
621 testResourcesWithManyLoaders(null); |
|
622 } |
|
623 |
|
624 /** |
|
625 * Test locating resources with class loaders created by |
|
626 * defineModulesWithManyLoaders. The class loaders have the given class |
|
627 * loader as their parent. |
|
628 */ |
|
629 void testResourcesWithManyLoaders(ClassLoader parent) throws Exception { |
610 Configuration cf = resolve("m1"); |
630 Configuration cf = resolve("m1"); |
611 ClassLoader scl = ClassLoader.getSystemClassLoader(); |
631 ModuleLayer layer = ModuleLayer.boot().defineModulesWithManyLoaders(cf, parent); |
612 ModuleLayer layer = ModuleLayer.boot().defineModulesWithManyLoaders(cf, scl); |
|
613 |
632 |
614 for (Module m : layer.modules()) { |
633 for (Module m : layer.modules()) { |
615 String name = m.getName(); |
634 String name = m.getName(); |
616 ClassLoader loader = m.getClassLoader(); |
635 ClassLoader loader = m.getClassLoader(); |
617 assertNotNull(loader); |
636 assertNotNull(loader); |
|
637 assertTrue(loader.getParent() == parent); |
618 |
638 |
619 // getResource should find the module-info.class for the module |
639 // getResource should find the module-info.class for the module |
620 URL url = loader.getResource("module-info.class"); |
640 URL url = loader.getResource("module-info.class"); |
621 assertEquals(readModuleName(url), name); |
641 assertEquals(readModuleName(url), name); |
622 |
642 |