14
14
import com .intellij .util .lang .Resource ;
15
15
import com .intellij .util .lang .UrlClassLoader ;
16
16
import com .intellij .util .ui .EDT ;
17
- import org .jetbrains .annotations .*;
17
+ import org .jetbrains .annotations .ApiStatus ;
18
+ import org .jetbrains .annotations .NonNls ;
19
+ import org .jetbrains .annotations .NotNull ;
20
+ import org .jetbrains .annotations .Nullable ;
18
21
19
22
import java .io .*;
20
23
import java .net .URL ;
21
24
import java .nio .file .Files ;
22
25
import java .nio .file .Path ;
23
26
import java .nio .file .Paths ;
24
- import java .security .CodeSource ;
25
- import java .security .ProtectionDomain ;
26
- import java .security .cert .Certificate ;
27
27
import java .util .*;
28
28
import java .util .concurrent .atomic .AtomicInteger ;
29
29
import java .util .concurrent .atomic .AtomicLong ;
30
30
import java .util .function .BiFunction ;
31
31
import java .util .function .Function ;
32
32
33
33
/**
34
- * Fork of PluginClassLoader_Fork
34
+ * Fork of com.intellij.ide.plugins.cl.PluginClassLoader
35
35
* because its an internal IJ API and it has been changing in IJ 2020.2 causing LivePlugin to break.
36
36
* The assumption is that using fork will make LivePlugin forward-compatible with more IJ versions
37
37
* given that PluginClassLoader_Fork implementation compatibility is more stable than PluginClassLoader API.
@@ -52,9 +52,6 @@ public final class PluginClassLoader_Fork extends UrlClassLoader implements Plug
52
52
53
53
private static final Set <String > KOTLIN_STDLIB_CLASSES_USED_IN_SIGNATURES ;
54
54
55
- // avoid capturing reference to classloader in AccessControlContext
56
- private static final ProtectionDomain PROTECTION_DOMAIN = new ProtectionDomain (new CodeSource (null , (Certificate []) null ), null );
57
-
58
55
static {
59
56
@ SuppressWarnings ("SSBasedInspection" )
60
57
Set <String > kotlinStdlibClassesUsedInSignatures = new HashSet <>(Arrays .asList (
@@ -80,11 +77,17 @@ public final class PluginClassLoader_Fork extends UrlClassLoader implements Plug
80
77
"kotlin.coroutines.CoroutineContext" ,
81
78
"kotlin.coroutines.CoroutineContext$Element" ,
82
79
"kotlin.coroutines.CoroutineContext$Key" ,
80
+ "kotlin.Result" ,
81
+ "kotlin.Result$Failure" ,
82
+ "kotlin.Result$Companion" ,
83
83
// Even though it's internal class, it can leak (and it does) into API surface because it's exposed by public
84
84
// `kotlin.coroutines.intrinsics.COROUTINE_SUSPENDED` property
85
85
"kotlin.coroutines.intrinsics.CoroutineSingletons" ,
86
86
"kotlin.coroutines.AbstractCoroutineContextElement" ,
87
- "kotlin.coroutines.AbstractCoroutineContextKey"
87
+ "kotlin.coroutines.AbstractCoroutineContextKey" ,
88
+ "kotlin.coroutines.jvm.internal.ContinuationImpl" , // IDEA-295189
89
+ "kotlin.coroutines.jvm.internal.BaseContinuationImpl" , // IDEA-295189
90
+ "kotlin.coroutines.jvm.internal.CoroutineStackFrame" // IDEA-295189
88
91
));
89
92
String classes = System .getProperty ("idea.kotlin.classes.used.in.signatures" );
90
93
if (classes != null ) {
@@ -225,7 +228,7 @@ public Class<?> loadClass(@NotNull String name, boolean resolve) throws ClassNot
225
228
}
226
229
227
230
/**
228
- * See https://stackoverflow.com/a/5428795 about resolve flag.
231
+ * See <a href=" https://stackoverflow.com/a/5428795">https://stackoverflow.com/a/5428795</a> about resolve flag.
229
232
*/
230
233
@ Override
231
234
public @ Nullable Class <?> tryLoadingClass (@ NotNull String name , boolean forceLoadFromSubPluginClassloader )
@@ -382,9 +385,23 @@ private static boolean mustBeLoadedByPlatform(@NonNls String className) {
382
385
// some commonly used classes from kotlin-runtime must be loaded by the platform classloader. Otherwise, if a plugin bundles its own version
383
386
// of kotlin-runtime.jar it won't be possible to call platform's methods with these types in signatures from such a plugin.
384
387
// We assume that these classes don't change between Kotlin versions, so it's safe to always load them from platform's kotlin-runtime.
385
- return className .startsWith ("kotlin." ) && (className .startsWith ("kotlin.jvm.functions." ) ||
386
- (className .startsWith ("kotlin.reflect." ) &&
387
- className .indexOf ('.' , 15 /* "kotlin.reflect".length */ ) < 0 ) ||
388
+ return className .startsWith ("kotlin." ) &&
389
+ (className .startsWith ("kotlin.jvm.functions." ) ||
390
+ // Those are kotlin-reflect related classes but unfortunately, they are placed in kotlin-stdlib. Since we always
391
+ // want to load reflect from platform, we should force those classes with platform classloader as well
392
+ className .startsWith ("kotlin.reflect." ) ||
393
+ className .startsWith ("kotlin.jvm.internal.CallableReference" ) ||
394
+ className .startsWith ("kotlin.jvm.internal.ClassReference" ) ||
395
+ className .startsWith ("kotlin.jvm.internal.FunInterfaceConstructorReference" ) ||
396
+ className .startsWith ("kotlin.jvm.internal.FunctionReference" ) ||
397
+ className .startsWith ("kotlin.jvm.internal.MutablePropertyReference" ) ||
398
+ className .startsWith ("kotlin.jvm.internal.PropertyReference" ) ||
399
+ className .startsWith ("kotlin.jvm.internal.TypeReference" ) ||
400
+ className .equals ("kotlin.jvm.internal.Lambda" ) ||
401
+ className .startsWith ("kotlin.jvm.internal.LocalVariableReference" ) ||
402
+ className .startsWith ("kotlin.jvm.internal.MutableLocalVariableReference" ) ||
403
+ className .equals ("kotlin.jvm.internal.ReflectionFactory" ) ||
404
+ className .equals ("kotlin.jvm.internal.Reflection" ) ||
388
405
KOTLIN_STDLIB_CLASSES_USED_IN_SIGNATURES .contains (className ));
389
406
}
390
407
@@ -510,7 +527,7 @@ private void logClass(@NotNull String name, @NotNull Writer logStream, @Nullable
510
527
return doFindResource (name , f1 , f2 );
511
528
}
512
529
513
- private <T > @ Nullable T doFindResource (String name , Function <Resource , T > f1 , BiFunction <ClassLoader , String , T > f2 ) {
530
+ private <T > @ Nullable T doFindResource (String name , Function <? super Resource , ? extends T > f1 , BiFunction <? super ClassLoader , ? super String , ? extends T > f2 ) {
514
531
String canonicalPath = toCanonicalPath (name );
515
532
516
533
Resource resource = classPath .findResource (canonicalPath );
@@ -601,10 +618,10 @@ public String toString() {
601
618
}
602
619
603
620
private static final class DeepEnumeration implements Enumeration <URL > {
604
- private final @ NotNull List <Enumeration <URL >> list ;
621
+ private final @ NotNull List <? extends Enumeration <URL >> list ;
605
622
private int myIndex ;
606
623
607
- DeepEnumeration (@ NotNull List <Enumeration <URL >> enumerations ) {
624
+ private DeepEnumeration (@ NotNull List <? extends Enumeration <URL >> enumerations ) {
608
625
list = enumerations ;
609
626
}
610
627
@@ -629,10 +646,6 @@ public URL nextElement() {
629
646
}
630
647
}
631
648
632
- protected ProtectionDomain getProtectionDomain () {
633
- return PROTECTION_DOMAIN ;
634
- }
635
-
636
649
private static void flushDebugLog () {
637
650
if (logStream != null ) {
638
651
try {
0 commit comments