22
33import com .google .common .base .Preconditions ;
44import com .google .common .io .ByteStreams ;
5+ import io .izzel .tools .product .Product2 ;
56import java .io .File ;
67import java .io .IOException ;
78import java .io .InputStream ;
1011import java .net .MalformedURLException ;
1112import java .net .URL ;
1213import java .net .URLClassLoader ;
13- import java .security . CodeSigner ;
14+ import java .net . URLConnection ;
1415import java .security .CodeSource ;
1516import java .util .Collection ;
1617import java .util .Collections ;
1718import java .util .Enumeration ;
1819import java .util .Map ;
1920import java .util .Set ;
21+ import java .util .concurrent .Callable ;
2022import java .util .concurrent .ConcurrentHashMap ;
21- import java .util .jar .JarEntry ;
2223import java .util .jar .JarFile ;
2324import java .util .jar .Manifest ;
2425import java .util .logging .Level ;
26+ import org .bukkit .Bukkit ;
2527import org .bukkit .plugin .InvalidPluginException ;
2628import org .bukkit .plugin .PluginDescriptionFile ;
2729import org .bukkit .plugin .SimplePluginManager ;
2830import org .jetbrains .annotations .NotNull ;
2931import org .jetbrains .annotations .Nullable ;
32+ import org .magmafoundation .magma .asm .SwitchTableFixer ;
33+ import org .magmafoundation .magma .remapping .ClassLoaderRemapper ;
34+ import org .magmafoundation .magma .remapping .MagmaRemapper ;
35+ import org .magmafoundation .magma .remapping .loaders .RemappingClassLoader ;
3036
3137/**
3238 * A ClassLoader for plugins, to allow shared classes across multiple plugins
3339 */
34- final class PluginClassLoader extends URLClassLoader {
40+ final class PluginClassLoader extends URLClassLoader implements RemappingClassLoader {
3541 private final JavaPluginLoader loader ;
3642 private final Map <String , Class <?>> classes = new ConcurrentHashMap <String , Class <?>>();
3743 private final PluginDescriptionFile description ;
@@ -50,6 +56,18 @@ final class PluginClassLoader extends URLClassLoader {
5056 ClassLoader .registerAsParallelCapable ();
5157 }
5258
59+ // Magma start
60+ private ClassLoaderRemapper remapper ;
61+
62+ @ Override
63+ public ClassLoaderRemapper getRemapper () {
64+ if (remapper == null ) {
65+ remapper = MagmaRemapper .createClassLoaderRemapper (this );
66+ }
67+ return remapper ;
68+ }
69+ // Magma end
70+
5371 PluginClassLoader (@ NotNull final JavaPluginLoader loader , @ Nullable final ClassLoader parent , @ NotNull final PluginDescriptionFile description , @ NotNull final File dataFolder , @ NotNull final File file , @ Nullable ClassLoader libraryLoader ) throws IOException , InvalidPluginException , MalformedURLException {
5472 super (new URL [] { file .toURI ().toURL () }, parent );
5573 Preconditions .checkArgument (loader != null , "Loader cannot be null" );
@@ -167,26 +185,36 @@ protected Class<?> findClass(String name) throws ClassNotFoundException {
167185
168186 if (result == null ) {
169187 String path = name .replace ('.' , '/' ).concat (".class" );
170- JarEntry entry = jar .getJarEntry (path );
171-
172- if (entry != null ) {
173- byte [] classBytes ;
174-
175- try (InputStream is = jar .getInputStream (entry )) {
176- classBytes = ByteStreams .toByteArray (is );
177- } catch (IOException ex ) {
178- throw new ClassNotFoundException (name , ex );
188+ URL url = this .findResource (path );
189+
190+ if (url != null ) {
191+
192+ URLConnection connection ;
193+ Callable <byte []> byteSource ;
194+ try {
195+ connection = url .openConnection ();
196+ connection .connect ();
197+ byteSource = () -> {
198+ try (InputStream is = connection .getInputStream ()) {
199+ byte [] classBytes = ByteStreams .toByteArray (is );
200+ classBytes = SwitchTableFixer .INSTANCE .apply (classBytes );
201+ classBytes = Bukkit .getUnsafe ().processClass (description , path , classBytes );
202+ return classBytes ;
203+ }
204+ };
205+ } catch (IOException e ) {
206+ throw new ClassNotFoundException (name , e );
179207 }
180208
181- classBytes = loader . server . getUnsafe ().processClass ( description , path , classBytes );
209+ Product2 < byte [], CodeSource > classBytes = this . getRemapper ().remapClass ( name , byteSource , connection );
182210
183211 int dot = name .lastIndexOf ('.' );
184212 if (dot != -1 ) {
185213 String pkgName = name .substring (0 , dot );
186214 if (getPackage (pkgName ) == null ) {
187215 try {
188216 if (manifest != null ) {
189- definePackage (pkgName , manifest , url );
217+ definePackage (pkgName , manifest , this . url );
190218 } else {
191219 definePackage (pkgName , null , null , null , null , null , null , null );
192220 }
@@ -198,10 +226,7 @@ protected Class<?> findClass(String name) throws ClassNotFoundException {
198226 }
199227 }
200228
201- CodeSigner [] signers = entry .getCodeSigners ();
202- CodeSource source = new CodeSource (url , signers );
203-
204- result = defineClass (name , classBytes , 0 , classBytes .length , source );
229+ result = defineClass (name , classBytes ._1 , 0 , classBytes ._1 .length , classBytes ._2 );
205230 }
206231
207232 if (result == null ) {
0 commit comments