Remove Unsafe class injection from Java agent - #21542
Conversation
The Java agent previously used ClassInjector.UsingUnsafe at premain time to inject AgentPolicy, SubjectInterceptor, and the two stack caller chain extractors into the boot classloader. This relied on sun.misc.Unsafe, which is deprecated for removal on recent JDKs and emits JVM warnings. This change relocates StackCallerClassChainExtractor, StackCallerProtectionDomainChainExtractor, and SubjectInterceptor from :libs:agent-sm:agent into :libs:agent-sm:bootstrap, under a new org.opensearch.javaagent.bootstrap.internal subpackage to distinguish them from AgentPolicy, which is the shared API between the server and the agent. The bootstrap jar is listed on the agent jar's Boot-Class-Path manifest attribute, so the JVM loads these classes into the boot classloader natively with no runtime injection needed. Also set -Dnet.bytebuddy.safe=true on test JVMs to disable the Unsafe-based dispatchers inside ByteBuddy's ClassInjector. ByteBuddy falls back to MethodHandles.Lookup / reflection injection, which works on JDK 9+. Signed-off-by: Andrew Ross <andrross@amazon.com>
PR Reviewer Guide 🔍Here are some key observations to aid the review process:
|
PR Code Suggestions ✨Explore these optional code suggestions:
|
|
❌ Gradle check result for ed7cc24: FAILURE Please examine the workflow log, locate, and copy-paste the failure(s) below, then iterate to green. Is the failure a flaky test unrelated to your change? |
|
❌ Gradle check result for ed7cc24: FAILURE Please examine the workflow log, locate, and copy-paste the failure(s) below, then iterate to green. Is the failure a flaky test unrelated to your change? |
|
❌ Gradle check result for ed7cc24: null Please examine the workflow log, locate, and copy-paste the failure(s) below, then iterate to green. Is the failure a flaky test unrelated to your change? |
|
@reta About 3000 fewer warnings in the build log! For now anyway... |
Codecov Report✅ All modified and coverable lines are covered by tests. Additional details and impacted files@@ Coverage Diff @@
## main #21542 +/- ##
============================================
+ Coverage 73.42% 73.45% +0.02%
- Complexity 74547 74548 +1
============================================
Files 5978 5975 -3
Lines 338743 338720 -23
Branches 48843 48843
============================================
+ Hits 248707 248790 +83
+ Misses 70229 70067 -162
- Partials 19807 19863 +56 ☔ View full report in Codecov by Sentry. 🚀 New features to boost your workflow:
|
The Java agent previously used ClassInjector.UsingUnsafe at premain time to inject AgentPolicy, SubjectInterceptor, and the two stack caller chain extractors into the boot classloader. This relied on sun.misc.Unsafe, which is deprecated for removal on recent JDKs and emits JVM warnings. This change relocates StackCallerClassChainExtractor, StackCallerProtectionDomainChainExtractor, and SubjectInterceptor from :libs:agent-sm:agent into :libs:agent-sm:bootstrap, under a new org.opensearch.javaagent.bootstrap.internal subpackage to distinguish them from AgentPolicy, which is the shared API between the server and the agent. The bootstrap jar is listed on the agent jar's Boot-Class-Path manifest attribute, so the JVM loads these classes into the boot classloader natively with no runtime injection needed. Also set -Dnet.bytebuddy.safe=true on test JVMs to disable the Unsafe-based dispatchers inside ByteBuddy's ClassInjector. ByteBuddy falls back to MethodHandles.Lookup / reflection injection, which works on JDK 9+. Signed-off-by: Andrew Ross <andrross@amazon.com>
The Java agent previously used ClassInjector.UsingUnsafe at premain time to inject AgentPolicy, SubjectInterceptor, and the two stack caller chain extractors into the boot classloader. This relied on sun.misc.Unsafe, which is deprecated for removal on recent JDKs and emits JVM warnings. This change relocates StackCallerClassChainExtractor, StackCallerProtectionDomainChainExtractor, and SubjectInterceptor from :libs:agent-sm:agent into :libs:agent-sm:bootstrap, under a new org.opensearch.javaagent.bootstrap.internal subpackage to distinguish them from AgentPolicy, which is the shared API between the server and the agent. The bootstrap jar is listed on the agent jar's Boot-Class-Path manifest attribute, so the JVM loads these classes into the boot classloader natively with no runtime injection needed. Also set -Dnet.bytebuddy.safe=true on test JVMs to disable the Unsafe-based dispatchers inside ByteBuddy's ClassInjector. ByteBuddy falls back to MethodHandles.Lookup / reflection injection, which works on JDK 9+. Signed-off-by: Andrew Ross <andrross@amazon.com>
The Java agent previously used ClassInjector.UsingUnsafe at premain time to inject AgentPolicy, SubjectInterceptor, and the two stack caller chain extractors into the boot classloader. This relied on sun.misc.Unsafe, which is deprecated for removal on recent JDKs and emits JVM warnings.
This change relocates StackCallerClassChainExtractor, StackCallerProtectionDomainChainExtractor, and SubjectInterceptor from :libs:agent-sm:agent into :libs:agent-sm:bootstrap, under a new org.opensearch.javaagent.bootstrap.internal subpackage to distinguish them from AgentPolicy, which is the shared API between the server and the agent. The bootstrap jar is listed on the agent jar's Boot-Class-Path manifest attribute, so the JVM loads these classes into the boot classloader natively with no runtime injection needed.
Also set -Dnet.bytebuddy.safe=true on test JVMs to disable the Unsafe-based dispatchers inside ByteBuddy's ClassInjector. ByteBuddy falls back to MethodHandles.Lookup / reflection injection, which works on JDK 9+.
Check List
By submitting this pull request, I confirm that my contribution is made under the terms of the Apache 2.0 license.
For more information on following Developer Certificate of Origin and signing off your commits, please check here.