Explorar o código

Setup vm-names of JvmPluginClassLoader's libraries classloaders

Karlatemp %!s(int64=3) %!d(string=hai) anos
pai
achega
b0711ed9ab

+ 3 - 0
mirai-console/backend/integration-test/testers/service-loader/module-service-loader-impl/src/ServiceImpl.kt

@@ -11,4 +11,7 @@ package net.mamoe.console.integrationtest.mod.serviceimpl
 import net.mamoe.console.integrationtest.mod.servicetypedef.ServiceTypedef
 
 public class ServiceImpl : ServiceTypedef {
+    override fun act() {
+        Throwable("Stacktrace").printStackTrace(System.out)
+    }
 }

+ 1 - 0
mirai-console/backend/integration-test/testers/service-loader/module-service-loader-typedef/src/ServiceTypedef.kt

@@ -10,4 +10,5 @@
 package net.mamoe.console.integrationtest.mod.servicetypedef
 
 public interface ServiceTypedef {
+    public fun act() {}
 }

+ 9 - 6
mirai-console/backend/integration-test/testers/service-loader/src/PMain.kt

@@ -11,7 +11,7 @@
 
 package net.mamoe.console.itest.serviceloader
 
-import net.mamoe.mirai.console.internal.plugin.DynLibClassLoader
+import net.mamoe.mirai.console.internal.plugin.JvmPluginClassLoaderN
 import net.mamoe.mirai.console.plugin.jvm.JvmPluginDescription
 import net.mamoe.mirai.console.plugin.jvm.KotlinPlugin
 import net.mamoe.mirai.utils.info
@@ -21,21 +21,24 @@ import kotlin.test.assertEquals
 
 internal object PMain : KotlinPlugin(JvmPluginDescription("net.mamoe.console.itest.serviceloader", "0.0.0")) {
     init {
-        val cl = PMain.javaClass.classLoader.parent as DynLibClassLoader
-        cl.addLib(File("modules/module-service-loader-typedef-0.0.0.jar"))
-        cl.addLib(File("modules/module-service-loader-impl-0.0.0.jar"))
+        val cl = PMain.javaClass.classLoader as JvmPluginClassLoaderN
+        cl.pluginSharedCL.addLib(File("modules/module-service-loader-typedef-0.0.0.jar"))
+        cl.pluginSharedCL.addLib(File("modules/module-service-loader-impl-0.0.0.jar"))
     }
 
     override fun onEnable() {
+        @Suppress("LocalVariableName")
+        val ServiceTypedef = Class.forName("net.mamoe.console.integrationtest.mod.servicetypedef.ServiceTypedef")
         val loader = ServiceLoader.load(
-            Class.forName("net.mamoe.console.integrationtest.mod.servicetypedef.ServiceTypedef"),
+            ServiceTypedef,
             javaClass.classLoader,
-        )
+        ).toList()
         val services = loader.asSequence().map { it.javaClass.name }.toMutableList()
         services.forEach { service ->
             logger.info { "Service: $service" }
         }
         assertEquals(mutableListOf("net.mamoe.console.integrationtest.mod.serviceimpl.ServiceImpl"), services)
+        ServiceTypedef.getMethod("act").invoke(loader.first())
 
         assertEquals(
             "from plugin",

+ 3 - 1
mirai-console/backend/mirai-console/src/internal/plugin/BuiltInJvmPluginLoaderImpl.kt

@@ -73,7 +73,9 @@ internal class BuiltInJvmPluginLoaderImpl(
 
 
     internal val jvmPluginLoadingCtx: JvmPluginsLoadingCtx by lazy {
-        val classLoader = DynLibClassLoader(BuiltInJvmPluginLoaderImpl::class.java.classLoader, "GlobalShared")
+        val classLoader = DynLibClassLoader.newInstance(
+            BuiltInJvmPluginLoaderImpl::class.java.classLoader, "GlobalShared", "global-shared"
+        )
         val ctx = JvmPluginsLoadingCtx(
             classLoader,
             mutableListOf(),

+ 30 - 9
mirai-console/backend/mirai-console/src/internal/plugin/JvmPluginClassLoader.kt

@@ -51,13 +51,32 @@ internal class JvmPluginsLoadingCtx(
     }
 }
 
-internal class DynLibClassLoader(
-    parent: ClassLoader?,
-    private val clName: String? = null,
-) : URLClassLoader(arrayOf(), parent) {
+internal class DynLibClassLoader : URLClassLoader {
+    private val clName: String?
+
+    private constructor(parent: ClassLoader?, clName: String?) : super(arrayOf(), parent) {
+        this.clName = clName
+    }
+
+    @Suppress("Since15")
+    private constructor(parent: ClassLoader?, clName: String?, vmName: String?) : super(vmName, arrayOf(), parent) {
+        this.clName = clName
+    }
+
+
     companion object {
+        internal val java9: Boolean
+
         init {
             ClassLoader.registerAsParallelCapable()
+            java9 = kotlin.runCatching { Class.forName("java.lang.Module") }.isSuccess
+        }
+
+        fun newInstance(parent: ClassLoader?, clName: String?, vmName: String?): DynLibClassLoader {
+            return when {
+                java9 -> DynLibClassLoader(parent, clName, vmName)
+                else -> DynLibClassLoader(parent, clName)
+            }
         }
     }
 
@@ -192,8 +211,12 @@ internal class JvmPluginClassLoaderN : URLClassLoader {
                     pluginMainPackages.add(pkg)
                 }
         }
-        pluginSharedCL = DynLibClassLoader(ctx.sharedLibrariesLoader, "SharedCL{${file.name}}")
-        pluginIndependentCL = DynLibClassLoader(pluginSharedCL, "IndependentCL{${file.name}}")
+        pluginSharedCL = DynLibClassLoader.newInstance(
+            ctx.sharedLibrariesLoader, "SharedCL{${file.name}}", "${file.name}[shared]"
+        )
+        pluginIndependentCL = DynLibClassLoader.newInstance(
+            pluginSharedCL, "IndependentCL{${file.name}}", "${file.name}[private]"
+        )
         addURL(file.toURI().toURL())
     }
 
@@ -265,16 +288,14 @@ internal class JvmPluginClassLoaderN : URLClassLoader {
     }
 
     companion object {
-        private val java9: Boolean
 
         init {
             ClassLoader.registerAsParallelCapable()
-            java9 = kotlin.runCatching { Class.forName("java.lang.Module") }.isSuccess
         }
 
         fun newLoader(file: File, ctx: JvmPluginsLoadingCtx): JvmPluginClassLoaderN {
             return when {
-                java9 -> JvmPluginClassLoaderN(file, ctx)
+                DynLibClassLoader.java9 -> JvmPluginClassLoaderN(file, ctx)
                 else -> JvmPluginClassLoaderN(file, ctx, Unit)
             }
         }