mjiderhamn/classloader-leak-prevention

Add jdk., and com.apple. to DEFAULT_IGNORED_PACKAGES

vlsi opened this issue · 4 comments

vlsi commented

Classes like jdk.internal.loader.NativeLibraries, and jdk.proxy4.$Proxy... should not be loaded by RedefiningClassLoader

jdk.* I absolutely agree.

Can you explain why you think com.apple belongs in that list?

vlsi commented

Do you see reasons for com.apple classes to be loaded by the redefining classloader by default?
For instance, com.apple.laf. implements AWT/Swing in macOS.

% java -version
openjdk version "11.0.13" 2021-10-19 LTS
OpenJDK Runtime Environment (build 11.0.13+8-LTS)
OpenJDK 64-Bit Server VM (build 11.0.13+8-LTS, mixed mode)

Here are test results for classloader-leak-test-framework with macOS:

Loading jdk.internal.misc.Unsafe in se.jiderhamn.classloader.RedefiningClassLoader[se.jiderhamn.classloader.leak.known.JEditorPaneTest.triggerJEditorPaneLeak]@2890c451
Tests run: 1, Failures: 0, Errors: 1, Skipped: 0, Time elapsed: 0.293 sec <<< FAILURE!
triggerJEditorPaneLeak(se.jiderhamn.classloader.leak.known.JEditorPaneTest)  Time elapsed: 0.293 sec  <<< ERROR!
java.lang.UnsatisfiedLinkError: 'void jdk.internal.misc.Unsafe.registerNatives()'
	at jdk.internal.misc.Unsafe.registerNatives(Native Method)
	at jdk.internal.misc.Unsafe.<clinit>(Unsafe.java:57)
	at jdk.internal.misc.SharedSecrets.<clinit>(SharedSecrets.java:51)
	at jdk.internal.loader.ClassLoaders.<clinit>(ClassLoaders.java:50)
	at com.apple.laf.AquaUtils.shouldUseOpaqueButtons(AquaUtils.java:349)
	at com.apple.laf.AquaLookAndFeel.initComponentDefaults(AquaLookAndFeel.java:277)
	at com.apple.laf.AquaLookAndFeel.getDefaults(AquaLookAndFeel.java:235)
	at java.desktop/javax.swing.UIManager.setLookAndFeel(UIManager.java:587)
	at java.desktop/javax.swing.UIManager.setLookAndFeel(UIManager.java:633)
	at java.desktop/javax.swing.UIManager.initializeDefaultLAF(UIManager.java:1404)
	at java.desktop/javax.swing.UIManager.initialize(UIManager.java:1517)
	at java.desktop/javax.swing.UIManager.maybeInitialize(UIManager.java:1483)
	at java.desktop/javax.swing.UIManager.getUI(UIManager.java:1056)
	at java.desktop/javax.swing.text.JTextComponent.updateUI(JTextComponent.java:352)
	at java.desktop/javax.swing.text.JTextComponent.<init>(JTextComponent.java:326)
	at java.desktop/javax.swing.JEditorPane.<init>(JEditorPane.java:198)
	at java.desktop/javax.swing.JEditorPane.<init>(JEditorPane.java:290)
	at se.jiderhamn.classloader.leak.known.JEditorPaneTest.triggerJEditorPaneLeak(JEditorPaneTest.java:18)
	at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
	at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
	at java.base/jdk.internal.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
	at java.base/java.lang.reflect.Method.invoke(Method.java:566)
	at org.junit.runners.model.FrameworkMethod$1.runReflectiveCall(FrameworkMethod.java:59)
	at org.junit.internal.runners.model.ReflectiveCallable.run(ReflectiveCallable.java:12)
	at org.junit.runners.model.FrameworkMethod.invokeExplosively(FrameworkMethod.java:56)
	at se.jiderhamn.classloader.leak.JUnitClassloaderRunner$SeparateClassLoaderInvokeMethod.evaluate(JUnitClassloaderRunner.java:115)
	at org.junit.runners.ParentRunner$3.evaluate(ParentRunner.java:306)
	at org.junit.runners.BlockJUnit4ClassRunner$1.evaluate(BlockJUnit4ClassRunner.java:100)
	at org.junit.runners.ParentRunner.runLeaf(ParentRunner.java:366)
	at org.junit.runners.BlockJUnit4ClassRunner.runChild(BlockJUnit4ClassRunner.java:103)
	at org.junit.runners.BlockJUnit4ClassRunner.runChild(BlockJUnit4ClassRunner.java:63)
	at org.junit.runners.ParentRunner$4.run(ParentRunner.java:331)
	at org.junit.runners.ParentRunner$1.schedule(ParentRunner.java:79)
	at org.junit.runners.ParentRunner.runChildren(ParentRunner.java:329)
	at org.junit.runners.ParentRunner.access$100(ParentRunner.java:66)
	at org.junit.runners.ParentRunner$2.evaluate(ParentRunner.java:293)
	at org.junit.runners.ParentRunner$3.evaluate(ParentRunner.java:306)
	at org.junit.runners.ParentRunner.run(ParentRunner.java:413)
	at org.apache.maven.surefire.junit4.JUnit4Provider.execute(JUnit4Provider.java:252)
	at org.apache.maven.surefire.junit4.JUnit4Provider.executeTestSet(JUnit4Provider.java:141)
	at org.apache.maven.surefire.junit4.JUnit4Provider.invoke(JUnit4Provider.java:112)
	at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
	at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
	at java.base/jdk.internal.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
	at java.base/java.lang.reflect.Method.invoke(Method.java:566)
	at org.apache.maven.surefire.util.ReflectionUtils.invokeMethodWithArray(ReflectionUtils.java:189)
	at org.apache.maven.surefire.booter.ProviderFactory$ProviderProxy.invoke(ProviderFactory.java:165)
	at org.apache.maven.surefire.booter.ProviderFactory.invokeProvider(ProviderFactory.java:85)
	at org.apache.maven.surefire.booter.ForkedBooter.runSuitesInProcess(ForkedBooter.java:115)
	at org.apache.maven.surefire.booter.ForkedBooter.main(ForkedBooter.java:75)

Running se.jiderhamn.classloader.leak.known.CustomThreadLocalCustomValueTest
Loading se.jiderhamn.classloader.leak.known.CustomThreadLocalCustomValueTest in se.jiderhamn.classloader.RedefiningClassLoader[se.jiderhamn.classloader.leak.known.CustomThreadLocalCustomValueTest.setCustomThreadLocalValue]@7b98f307
Loading se.jiderhamn.classloader.leak.known.CustomThreadLocalCustomValueTest$1 in se.jiderhamn.classloader.RedefiningClassLoader[se.jiderhamn.classloader.leak.known.CustomThreadLocalCustomValueTest.setCustomThreadLocalValue]@7b98f307
Loading se.jiderhamn.classloader.leak.JUnitClassloaderRunner in se.jiderhamn.classloader.RedefiningClassLoader[se.jiderhamn.classloader.leak.known.CustomThreadLocalCustomValueTest.setCustomThreadLocalValue]@7b98f307
JUnit used jdk.internal.loader.ClassLoaders$AppClassLoader@277050dc

I could imagine Apple releasing lots of separate libraries packaged under com.apple.*, which should not be ignored by default. Here's one example I found quickly.

Can we compile a list of sub-packages that makes sense to ignore?

  • com.apple.eawt.*
  • com.apple.eio.*
  • com.apple.laf.*
  • more???
vlsi commented
com.apple.eawt.*
com.apple.eio.*
com.apple.laf.*

would work as well.