44 import java.util.function.Supplier; |
44 import java.util.function.Supplier; |
45 import java.lang.System.LoggerFinder; |
45 import java.lang.System.LoggerFinder; |
46 import java.lang.System.Logger; |
46 import java.lang.System.Logger; |
47 import java.lang.System.Logger.Level; |
47 import java.lang.System.Logger.Level; |
48 import java.util.stream.Stream; |
48 import java.util.stream.Stream; |
|
49 import java.lang.reflect.Module; |
|
50 import java.security.AllPermission; |
49 |
51 |
50 /** |
52 /** |
51 * @test |
53 * @test |
52 * @bug 8140364 |
54 * @bug 8140364 |
53 * @summary Tests loggers returned by System.getLogger with a naive implementation |
55 * @summary Tests loggers returned by System.getLogger with a naive implementation |
63 public class CustomLoggerTest { |
65 public class CustomLoggerTest { |
64 |
66 |
65 final static AtomicLong sequencer = new AtomicLong(); |
67 final static AtomicLong sequencer = new AtomicLong(); |
66 final static boolean VERBOSE = false; |
68 final static boolean VERBOSE = false; |
67 static final ThreadLocal<AtomicBoolean> allowControl = new ThreadLocal<AtomicBoolean>() { |
69 static final ThreadLocal<AtomicBoolean> allowControl = new ThreadLocal<AtomicBoolean>() { |
|
70 @Override |
|
71 protected AtomicBoolean initialValue() { |
|
72 return new AtomicBoolean(false); |
|
73 } |
|
74 }; |
|
75 static final ThreadLocal<AtomicBoolean> allowAll = new ThreadLocal<AtomicBoolean>() { |
68 @Override |
76 @Override |
69 protected AtomicBoolean initialValue() { |
77 protected AtomicBoolean initialValue() { |
70 return new AtomicBoolean(false); |
78 return new AtomicBoolean(false); |
71 } |
79 } |
72 }; |
80 }; |
239 eventQueue.add(event); |
247 eventQueue.add(event); |
240 } |
248 } |
241 } |
249 } |
242 |
250 |
243 @Override |
251 @Override |
244 public Logger getLogger(String name, Class<?> caller) { |
252 public Logger getLogger(String name, Module caller) { |
245 // We should check the permission to obey the API contract, but |
253 // We should check the permission to obey the API contract, but |
246 // what happens if we don't? |
254 // what happens if we don't? |
247 // This is the main difference compared with what we test in |
255 // This is the main difference compared with what we test in |
248 // java/lang/System/LoggerFinder/BaseLoggerFinderTest |
256 // java/lang/System/LoggerFinder/BaseLoggerFinderTest |
249 SecurityManager sm = System.getSecurityManager(); |
257 SecurityManager sm = System.getSecurityManager(); |
250 if (sm != null && doChecks) { |
258 if (sm != null && doChecks) { |
251 sm.checkPermission(SimplePolicy.LOGGERFINDER_PERMISSION); |
259 sm.checkPermission(SimplePolicy.LOGGERFINDER_PERMISSION); |
252 } |
260 } |
253 |
261 |
254 PrivilegedAction<ClassLoader> pa = () -> caller.getClassLoader(); |
262 final boolean before = allowAll.get().getAndSet(true); |
255 ClassLoader callerLoader = AccessController.doPrivileged(pa); |
263 final ClassLoader callerLoader; |
|
264 try { |
|
265 callerLoader = caller.getClassLoader(); |
|
266 } finally { |
|
267 allowAll.get().set(before); |
|
268 } |
256 if (callerLoader == null) { |
269 if (callerLoader == null) { |
257 return system.computeIfAbsent(name, (n) -> new LoggerImpl(n)); |
270 return system.computeIfAbsent(name, (n) -> new LoggerImpl(n)); |
258 } else { |
271 } else { |
259 return user.computeIfAbsent(name, (n) -> new LoggerImpl(n)); |
272 return user.computeIfAbsent(name, (n) -> new LoggerImpl(n)); |
260 } |
273 } |
265 |
278 |
266 static enum TestCases {NOSECURITY, NOPERMISSIONS, WITHPERMISSIONS}; |
279 static enum TestCases {NOSECURITY, NOPERMISSIONS, WITHPERMISSIONS}; |
267 |
280 |
268 static void setSecurityManager() { |
281 static void setSecurityManager() { |
269 if (System.getSecurityManager() == null) { |
282 if (System.getSecurityManager() == null) { |
270 Policy.setPolicy(new SimplePolicy(allowControl)); |
283 Policy.setPolicy(new SimplePolicy(allowControl, allowAll)); |
271 System.setSecurityManager(new SecurityManager()); |
284 System.setSecurityManager(new SecurityManager()); |
272 } |
285 } |
273 } |
286 } |
274 public static void main(String[] args) { |
287 public static void main(String[] args) { |
275 if (args.length == 0) |
288 if (args.length == 0) |
282 // 1. Obtain destination loggers directly from the LoggerFinder |
295 // 1. Obtain destination loggers directly from the LoggerFinder |
283 // - LoggerFinder.getLogger("foo", type) |
296 // - LoggerFinder.getLogger("foo", type) |
284 BaseLoggerFinder provider = |
297 BaseLoggerFinder provider = |
285 BaseLoggerFinder.class.cast(LoggerFinder.getLoggerFinder()); |
298 BaseLoggerFinder.class.cast(LoggerFinder.getLoggerFinder()); |
286 BaseLoggerFinder.LoggerImpl appSink = |
299 BaseLoggerFinder.LoggerImpl appSink = |
287 BaseLoggerFinder.LoggerImpl.class.cast(provider.getLogger("foo", CustomLoggerTest.class)); |
300 BaseLoggerFinder.LoggerImpl.class.cast(provider.getLogger("foo", CustomLoggerTest.class.getModule())); |
288 BaseLoggerFinder.LoggerImpl sysSink = |
301 BaseLoggerFinder.LoggerImpl sysSink = |
289 BaseLoggerFinder.LoggerImpl.class.cast(provider.getLogger("foo", Thread.class)); |
302 BaseLoggerFinder.LoggerImpl.class.cast(provider.getLogger("foo", Thread.class.getModule())); |
290 |
303 |
291 |
304 |
292 Stream.of(args).map(TestCases::valueOf).forEach((testCase) -> { |
305 Stream.of(args).map(TestCases::valueOf).forEach((testCase) -> { |
293 switch (testCase) { |
306 switch (testCase) { |
294 case NOSECURITY: |
307 case NOSECURITY: |
693 public static class SimplePolicy extends Policy { |
706 public static class SimplePolicy extends Policy { |
694 |
707 |
695 static final RuntimePermission LOGGERFINDER_PERMISSION = |
708 static final RuntimePermission LOGGERFINDER_PERMISSION = |
696 new RuntimePermission("loggerFinder"); |
709 new RuntimePermission("loggerFinder"); |
697 final Permissions permissions; |
710 final Permissions permissions; |
|
711 final Permissions controlPermissions; |
698 final Permissions allPermissions; |
712 final Permissions allPermissions; |
699 final ThreadLocal<AtomicBoolean> allowControl; |
713 final ThreadLocal<AtomicBoolean> allowControl; |
700 public SimplePolicy(ThreadLocal<AtomicBoolean> allowControl) { |
714 final ThreadLocal<AtomicBoolean> allowAll; |
|
715 public SimplePolicy(ThreadLocal<AtomicBoolean> allowControl, ThreadLocal<AtomicBoolean> allowAll) { |
701 this.allowControl = allowControl; |
716 this.allowControl = allowControl; |
|
717 this.allowAll = allowAll; |
702 permissions = new Permissions(); |
718 permissions = new Permissions(); |
703 |
719 |
704 // these are used for configuring the test itself... |
720 // these are used for configuring the test itself... |
|
721 controlPermissions = new Permissions(); |
|
722 controlPermissions.add(LOGGERFINDER_PERMISSION); |
|
723 |
|
724 // these are used for simulating a doPrivileged call from |
|
725 // a class in the BCL |
705 allPermissions = new Permissions(); |
726 allPermissions = new Permissions(); |
706 allPermissions.add(LOGGERFINDER_PERMISSION); |
727 allPermissions.add(new AllPermission()); |
|
728 |
|
729 } |
|
730 |
|
731 Permissions permissions() { |
|
732 if (allowAll.get().get()) return allPermissions; |
|
733 if (allowControl.get().get()) return controlPermissions; |
|
734 return permissions; |
707 |
735 |
708 } |
736 } |
709 |
737 |
710 @Override |
738 @Override |
711 public boolean implies(ProtectionDomain domain, Permission permission) { |
739 public boolean implies(ProtectionDomain domain, Permission permission) { |
712 if (allowControl.get().get()) return allPermissions.implies(permission); |
740 return permissions().implies(permission); |
713 return permissions.implies(permission); |
|
714 } |
741 } |
715 |
742 |
716 @Override |
743 @Override |
717 public PermissionCollection getPermissions(CodeSource codesource) { |
744 public PermissionCollection getPermissions(CodeSource codesource) { |
718 return new PermissionsBuilder().addAll(allowControl.get().get() |
745 return new PermissionsBuilder().addAll(permissions()).toPermissions(); |
719 ? allPermissions : permissions).toPermissions(); |
|
720 } |
746 } |
721 |
747 |
722 @Override |
748 @Override |
723 public PermissionCollection getPermissions(ProtectionDomain domain) { |
749 public PermissionCollection getPermissions(ProtectionDomain domain) { |
724 return new PermissionsBuilder().addAll(allowControl.get().get() |
750 return new PermissionsBuilder().addAll(permissions()).toPermissions(); |
725 ? allPermissions : permissions).toPermissions(); |
|
726 } |
751 } |
727 } |
752 } |
728 } |
753 } |