Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Illegal reflective access operation warning for toString() on CGLIB proxies [SPR-17500] #22032

Closed
spring-issuemaster opened this Issue Nov 15, 2018 · 3 comments

Comments

Projects
None yet
2 participants
@spring-issuemaster
Copy link
Collaborator

spring-issuemaster commented Nov 15, 2018

Matej Spiller-Muys opened SPR-17500 and commented

There are still some cases left that should be looked at. This WARNING is displayed when running application for a while.

WARNING: Illegal reflective access using Lookup on org.springframework.cglib.core.ReflectUtils (file:/Users/X/.m2/repository/org/springframework/spring-core/5.1.2.RELEASE/spring-core-5.1.2.RELEASE.jar) to class java.lang.Object
	at org.springframework.cglib.core.ReflectUtils.defineClass(ReflectUtils.java:497)
	at org.springframework.cglib.core.AbstractClassGenerator.generate(AbstractClassGenerator.java:359)
	at org.springframework.cglib.core.AbstractClassGenerator$ClassLoaderData$3.apply(AbstractClassGenerator.java:106)
	at org.springframework.cglib.core.AbstractClassGenerator$ClassLoaderData$3.apply(AbstractClassGenerator.java:104)
	at org.springframework.cglib.core.internal.LoadingCache$2.call(LoadingCache.java:54)
	at java.base/java.util.concurrent.FutureTask.run$$$capture(FutureTask.java:264)
	at java.base/java.util.concurrent.FutureTask.run(FutureTask.java)
	at org.springframework.cglib.core.internal.LoadingCache.createEntry(LoadingCache.java:61)
	at org.springframework.cglib.core.internal.LoadingCache.get(LoadingCache.java:34)
	at org.springframework.cglib.core.AbstractClassGenerator$ClassLoaderData.get(AbstractClassGenerator.java:130)
	at org.springframework.cglib.core.AbstractClassGenerator.create(AbstractClassGenerator.java:315)
	at org.springframework.cglib.reflect.FastClass$Generator.create(FastClass.java:65)
	at org.springframework.cglib.proxy.MethodProxy.helper(MethodProxy.java:135)
	at org.springframework.cglib.proxy.MethodProxy.init(MethodProxy.java:76)
	at org.springframework.cglib.proxy.MethodProxy.invoke(MethodProxy.java:216)
	at org.springframework.aop.framework.CglibAopProxy$DynamicAdvisedInterceptor.intercept(CglibAopProxy.java:684)
	at net.xxx.service.impl.ServiceImpl$$EnhancerBySpringCGLIB$$49f6ec4b.toString(<generated>)
	at net.xxx.MessageConsumer.onMessageHandler(MessageConsumer.java:216)
	at net.xxx.Consumer.onMessage(Consumer.java:144)
	at org.springframework.amqp.rabbit.listener.AbstractMessageListenerContainer.doInvokeListener(AbstractMessageListenerContainer.java:1520)
	at org.springframework.amqp.rabbit.listener.AbstractMessageListenerContainer.actualInvokeListener(AbstractMessageListenerContainer.java:1411)
	at org.springframework.amqp.rabbit.listener.AbstractMessageListenerContainer.invokeListener(AbstractMessageListenerContainer.java:1387)
	at org.springframework.amqp.rabbit.listener.AbstractMessageListenerContainer.executeListener(AbstractMessageListenerContainer.java:1366)
	at org.springframework.amqp.rabbit.listener.SimpleMessageListenerContainer.doReceiveAndExecute(SimpleMessageListenerContainer.java:848)
	at org.springframework.amqp.rabbit.listener.SimpleMessageListenerContainer.receiveAndExecute(SimpleMessageListenerContainer.java:832)
	at org.springframework.amqp.rabbit.listener.SimpleMessageListenerContainer.access$700(SimpleMessageListenerContainer.java:78)
	at org.springframework.amqp.rabbit.listener.SimpleMessageListenerContainer$AsyncMessageProcessingConsumer.run(SimpleMessageListenerContainer.java:1073)
	at java.base/java.lang.Thread.run(Thread.java:834)
WARNING: Illegal reflective access by org.springframework.cglib.core.ReflectUtils (file:/Users/X/.m2/repository/org/springframework/spring-core/5.1.2.RELEASE/spring-core-5.1.2.RELEASE.jar) to method java.lang.ClassLoader.defineClass(java.lang.String,byte[],int,int,java.security.ProtectionDomain)
	at org.springframework.cglib.core.ReflectUtils.defineClass(ReflectUtils.java:521)
	at org.springframework.cglib.core.AbstractClassGenerator.generate(AbstractClassGenerator.java:359)
	at org.springframework.cglib.core.AbstractClassGenerator$ClassLoaderData$3.apply(AbstractClassGenerator.java:106)
	at org.springframework.cglib.core.AbstractClassGenerator$ClassLoaderData$3.apply(AbstractClassGenerator.java:104)
	at org.springframework.cglib.core.internal.LoadingCache$2.call(LoadingCache.java:54)
	at java.base/java.util.concurrent.FutureTask.run$$$capture(FutureTask.java:264)
	at java.base/java.util.concurrent.FutureTask.run(FutureTask.java)
	at org.springframework.cglib.core.internal.LoadingCache.createEntry(LoadingCache.java:61)
	at org.springframework.cglib.core.internal.LoadingCache.get(LoadingCache.java:34)
	at org.springframework.cglib.core.AbstractClassGenerator$ClassLoaderData.get(AbstractClassGenerator.java:130)
	at org.springframework.cglib.core.AbstractClassGenerator.create(AbstractClassGenerator.java:315)
	at org.springframework.cglib.reflect.FastClass$Generator.create(FastClass.java:65)
	at org.springframework.cglib.proxy.MethodProxy.helper(MethodProxy.java:135)
	at org.springframework.cglib.proxy.MethodProxy.init(MethodProxy.java:76)
	at org.springframework.cglib.proxy.MethodProxy.invoke(MethodProxy.java:216)
	at org.springframework.aop.framework.CglibAopProxy$DynamicAdvisedInterceptor.intercept(CglibAopProxy.java:684)
	at net.xxx.service.impl.ServiceImpl$$EnhancerBySpringCGLIB$$49f6ec4b.toString(<generated>)
	at net.xxx.MessageConsumer.onMessageHandler(MessageConsumer.java:216)
	at net.xxx.consumer.Consumer.onMessage(Consumer.java:144)
	at org.springframework.amqp.rabbit.listener.AbstractMessageListenerContainer.doInvokeListener(AbstractMessageListenerContainer.java:1520)
	at org.springframework.amqp.rabbit.listener.AbstractMessageListenerContainer.actualInvokeListener(AbstractMessageListenerContainer.java:1411)
	at org.springframework.amqp.rabbit.listener.AbstractMessageListenerContainer.invokeListener(AbstractMessageListenerContainer.java:1387)
	at org.springframework.amqp.rabbit.listener.AbstractMessageListenerContainer.executeListener(AbstractMessageListenerContainer.java:1366)
	at org.springframework.amqp.rabbit.listener.SimpleMessageListenerContainer.doReceiveAndExecute(SimpleMessageListenerContainer.java:848)
	at org.springframework.amqp.rabbit.listener.SimpleMessageListenerContainer.receiveAndExecute(SimpleMessageListenerContainer.java:832)
	at org.springframework.amqp.rabbit.listener.SimpleMessageListenerContainer.access$700(SimpleMessageListenerContainer.java:78)
	at org.springframework.amqp.rabbit.listener.SimpleMessageListenerContainer$AsyncMessageProcessingConsumer.run(SimpleMessageListenerContainer.java:1073)
	at java.base/java.lang.Thread.run(Thread.java:834)

I am using Java 11.0.1 with Spring Boot 2.1.0.


Affects: 5.1.2

Issue Links:

  • #16241 CglibAopProxy needs to detect package-visible methods when defined in a different ClassLoader
  • #20414 MethodHandles.Lookup.defineClass for CGLIB class definition purposes

Referenced from: commits 2a5d769

@spring-issuemaster

This comment has been minimized.

Copy link
Collaborator Author

spring-issuemaster commented Nov 15, 2018

Juergen Hoeller commented

Interestingly, both of those cases are triggered by toString() invocations, with CGLIB trying to create its fast-class adapter for java.lang.Object. We might have to explicitly bypass such attempts, using a regular reflective dispatch instead.

@spring-issuemaster

This comment has been minimized.

Copy link
Collaborator Author

spring-issuemaster commented Nov 20, 2018

Juergen Hoeller commented

It turns out that this is not easy to reproduce. Are there any specific constraints in your scenario, such as restricted visibility of your classes?

In general, we're bypassing straight invocations of java.lang.Object methods already. It might make a difference if you cast your instance to Object before calling toString() on it? Of course this is not a long-term solution, we need to make this work with subclass overrides as well...

@spring-issuemaster

This comment has been minimized.

Copy link
Collaborator Author

spring-issuemaster commented Nov 20, 2018

Juergen Hoeller commented

We're bypassing overridden equals / hashCode / toString methods now, performing straight reflective invocations to them (without CGLIB trying to create a fast class for them).

I couldn't actually reproduce the warning on JDK 11 but hopefully this defensive check makes it disappear in your scenario as well now.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
You can’t perform that action at this time.