RuedigerMoeller / fast-serialization

FST: fast java serialization drop in-replacement
Apache License 2.0
1.58k stars 248 forks source link

FST doesn't work on Java 16 #312

Open Venorcis opened 3 years ago

Venorcis commented 3 years ago

The following exception is always thrown:

java.lang.reflect.InaccessibleObjectException: Unable to make field private final byte[] java.lang.String.value accessible: module java.base does not "opens java.lang" to unnamed module @59690aa4
    at java.base/java.lang.reflect.AccessibleObject.checkCanSetAccessible(AccessibleObject.java:357)
    at java.base/java.lang.reflect.AccessibleObject.checkCanSetAccessible(AccessibleObject.java:297)
    at java.base/java.lang.reflect.Field.checkCanSetAccessible(Field.java:177)
    at java.base/java.lang.reflect.Field.setAccessible(Field.java:171)
    at org.nustaq.serialization.FSTClazzInfo.createFieldInfo(FSTClazzInfo.java:504)
    at org.nustaq.serialization.FSTClazzInfo.createFields(FSTClazzInfo.java:367)
    at org.nustaq.serialization.FSTClazzInfo.<init>(FSTClazzInfo.java:128)
    at org.nustaq.serialization.FSTClazzInfoRegistry.getCLInfo(FSTClazzInfoRegistry.java:129)
    at org.nustaq.serialization.FSTClazzNameRegistry.addClassMapping(FSTClazzNameRegistry.java:97)
    at org.nustaq.serialization.FSTClazzNameRegistry.registerClassNoLookup(FSTClazzNameRegistry.java:84)
    at org.nustaq.serialization.FSTClazzNameRegistry.registerClass(FSTClazzNameRegistry.java:80)
    at org.nustaq.serialization.FSTConfiguration.addDefaultClazzes(FSTConfiguration.java:810)
    at org.nustaq.serialization.FSTConfiguration.initDefaultFstConfigurationInternal(FSTConfiguration.java:477)
    at org.nustaq.serialization.FSTConfiguration.createDefaultConfiguration(FSTConfiguration.java:472)
    at org.nustaq.serialization.FSTConfiguration.createDefaultConfiguration(FSTConfiguration.java:464)

This is probably related to the implementation of JEP-396...

izogfif commented 3 years ago

Temporary workaround: add --illegal-access=permit argument as a command-line argument for your java.exe. Yes, to java.exe, not to javac or compiler options. You can't tell this to compiler. You have to tell --illegal-access=permit to java executable.

d98ama commented 3 years ago

It seems like this workaround will no longer be possible with Java 17:

OpenJDK 64-Bit Server VM warning: Ignoring option --illegal-access=permit; support was removed in 17.0

mtf90 commented 3 years ago

Judging by the comments in projectlombok/lombok#2681 (especially the ones by @pron) granting (instrusive) access to internal classes and properties of JDK classes is to be explicitly white-listed by developers in the future. So issues like these probably won't magically disappear. However, the JVM seems to officially support granting these access rights via the --add-opens flags.

I managed to solve the above issue with the following maven config (we use FST during testing):

<plugin>
    <groupId>org.apache.maven.plugins</groupId>
    <artifactId>maven-surefire-plugin</artifactId>
    <configuration>
        <argLine>--add-opens=java.base/java.lang=ALL-UNNAMED
            --add-opens=java.base/java.math=ALL-UNNAMED
            --add-opens=java.base/java.util=ALL-UNNAMED
            --add-opens=java.base/java.util.concurrent=ALL-UNNAMED
            --add-opens=java.base/java.net=ALL-UNNAMED
            --add-opens=java.base/java.text=ALL-UNNAMED
            --add-opens=java.sql/java.sql=ALL-UNNAMED</argLine>
    </configuration>
</plugin>

I wasn't able to check this with Java 17, but maybe this proves useful for somebody else as well.

JJBRT commented 2 years ago

It can be solved without any JVM parameter with Burningwave Core reflection components that thanks to a special driver work on all JDKs from 8. In this case you can also simply call the method org.burningwave.core.assembler.StaticComponentContainer.Modules.exportAllToAll()

RockyMM commented 2 years ago

I would strongly advise against breaking strong encapsulation and going against what is mainstream Java orientation. --add-opens is only supported way to access Java internals. Anything else will create a maintenance burden and produce security concerns.

Birthright50 commented 2 years ago

Will there be a solution to the problem out of the box or is the project abandoned?

istinnstudio commented 2 years ago

Strong Encapsulation in the JDK Java 17 LTS

It is a funtamental change for security reasons and probably will stay for ever. This probably means that "--add-opens=...." will follow all upgraded projects to 17 LTS.

https://docs.oracle.com/en/java/javase/17/migrate/migrating-jdk-8-later-jdk-releases.html#GUID-7744EF96-5899-4FB2-B34E-86D49B2E89B6

oschina commented 2 years ago

Judging by the comments in projectlombok/lombok#2681 (especially the ones by @pron) granting (instrusive) access to internal classes and properties of JDK classes is to be explicitly white-listed by developers in the future. So issues like these probably won't magically disappear. However, the JVM seems to officially support granting these access rights via the --add-opens flags.

I managed to solve the above issue with the following maven config (we use FST during testing):

<plugin>
    <groupId>org.apache.maven.plugins</groupId>
    <artifactId>maven-surefire-plugin</artifactId>
    <configuration>
        <argLine>--add-opens=java.base/java.lang=ALL-UNNAMED
            --add-opens=java.base/java.math=ALL-UNNAMED
            --add-opens=java.base/java.util=ALL-UNNAMED
            --add-opens=java.base/java.util.concurrent=ALL-UNNAMED
            --add-opens=java.base/java.net=ALL-UNNAMED
            --add-opens=java.base/java.text=ALL-UNNAMED
            --add-opens=java.sql/java.sql=ALL-UNNAMED</argLine>
    </configuration>
</plugin>

I wasn't able to check this with Java 17, but maybe this proves useful for somebody else as well.

This solution works on Java 17 !

MatCuk commented 2 years ago

Is there any plan to fix this as part of library update instead of adding maven configuration options?

JJBRT commented 2 years ago

Is there any plan to fix this as part of library update instead of adding maven configuration options?

Take a look at how to export all modules to all modules at runtime

debraj-manna commented 1 year ago

In maven central I can see the below version.

https://mvnrepository.com/artifact/de.ruedigermoeller/fst/3.0.4-jdk17

Does 3.0.4-jdk17 support JDK 17?

istinnstudio commented 1 year ago

The name points that it does, only after using the necessary"--add-opens" settings. Changes from the old version: https://github.com/RuedigerMoeller/fast-serialization/compare/master...jdk17

pron commented 1 year ago

@JJBRT Note that any remaining loophole in strong encapsulation, including JNI, will eventually also require an explicit command-line permission similar to add-opens -- just as SecurityManager required such permission -- as strong encapsulation gradually becomes the foundation of the JDK's security.