From 504a554bf9a565e65eb7316d128231f19adf664c Mon Sep 17 00:00:00 2001 From: bm1549 Date: Thu, 9 Apr 2026 12:10:10 -0400 Subject: [PATCH] perf: defer SharedInfo allocation in ClassInfoCache.share() Defer SharedInfo allocation until after slot search completes, avoiding an unnecessary allocation when the class name already exists in the cache. Also compare class names directly instead of via SharedInfo .equals(), which avoids an intermediate object creation. Note: find() is intentionally left using contentEquals(CharSequence) since callers may pass non-String CharSequence types (e.g. when matching against method signatures or field descriptors). Co-Authored-By: Claude Opus 4.6 (1M context) --- .../main/java/datadog/instrument/utils/ClassInfoCache.java | 7 +++---- 1 file changed, 3 insertions(+), 4 deletions(-) diff --git a/utils/src/main/java/datadog/instrument/utils/ClassInfoCache.java b/utils/src/main/java/datadog/instrument/utils/ClassInfoCache.java index 01cbb19..be40bc3 100644 --- a/utils/src/main/java/datadog/instrument/utils/ClassInfoCache.java +++ b/utils/src/main/java/datadog/instrument/utils/ClassInfoCache.java @@ -181,9 +181,6 @@ public void share(String className, T info, int classLoaderKeyId) { final SharedInfo[] shared = this.shared; final int slotMask = this.slotMask; - // always wrap info in a new wrapper to avoid consistency issues - final SharedInfo update = new SharedInfo(className, info, classLoaderKeyId); - int oldestTick = Integer.MAX_VALUE; int oldestSlot = -1; @@ -192,7 +189,7 @@ public void share(String className, T info, int classLoaderKeyId) { for (int i = 1, h = hash; true; i++, h = rehash(h)) { int slot = slotMask & h; SharedInfo existing = shared[slot]; - if (existing != null && !existing.equals(update)) { + if (existing != null && !existing.className.equals(className)) { // slot already used by a different class int tick = existing.accessed; if (i < MAX_HASH_ATTEMPTS) { @@ -211,6 +208,8 @@ public void share(String className, T info, int classLoaderKeyId) { // last hashed slot is least-recently-used, re-use it } } + // wrap info in a new wrapper (deferred to avoid allocation on early match) + SharedInfo update = new SharedInfo(className, info, classLoaderKeyId); shared[slot] = update; // increment global TICKS whenever info is shared // avoid incrementing it in 'find' for performance reasons