pinpoint-apm/pinpoint · error · InstrumentException

non private UtilMethod unsupported. method=${methodLongName}

Error message

non private UtilMethod unsupported. method=${methodLongName}

What it means

copyUtilMethods() copies methods annotated @ProfilerCallUtility from the advice class into the source class, but only private utility methods are supported. A non-private (public/protected/package-private) utility method cannot be safely copied, so InstrumentException is thrown naming the method.

Source

Thrown at agent-module/profiler/src/main/java/com/navercorp/pinpoint/profiler/instrument/ASMAspectWeaver.java:97

            if (methodNode.hasAnnotation(PointCut.class)) {
                methodNodes.pointCuts.add(methodNode);
                continue;
            }
            if (methodNode.hasAnnotation(JointPoint.class)) {
                methodNodes.jointPoints.add(methodNode);
                continue;
            }

            methodNodes.utils.add(methodNode);
        }

        return methodNodes;
    }

    private void copyUtilMethods(final MethodNodes methodNodes, final ASMClassNodeAdapter classNode) throws InstrumentException {
        for (ASMMethodNodeAdapter methodNode : methodNodes.utils) {
            if (!methodNode.isPrivate()) {
                throw new InstrumentException("non private UtilMethod unsupported. method=" + methodNode.getLongName());
            }

            classNode.copyMethod(methodNode);
        }
    }

    private void copyPointCutMethods(final MethodNodes methodNodes, final ASMClassNodeAdapter classNode) throws InstrumentException {
        final ASMMethodInsnNodeRemapper.Builder remapBuilder = new ASMMethodInsnNodeRemapper.Builder();
        for (ASMMethodNodeAdapter joinPointMethodNode : methodNodes.jointPoints) {
            remapBuilder.addFilter(null, joinPointMethodNode.getName(), joinPointMethodNode.getDesc());
        }

        for (ASMMethodNodeAdapter pointCutMethodNode : methodNodes.pointCuts) {
            final ASMMethodNodeAdapter sourceMethodNode = classNode.getDeclaredMethod(pointCutMethodNode.getName(), pointCutMethodNode.getDesc());
            if (sourceMethodNode == null) {
                throw new InstrumentException("not found method. " + classNode.getInternalName() + "." + pointCutMethodNode.getName());
            }

View on GitHub (pinned to 744c3d3075)

Solutions

  1. Change the utility method to private
  2. Remove the util-method annotation if the method shouldn't be copied
  3. Rename it so it doesn't collide with source class methods and keep it private
  4. Split non-private logic into the pointcut methods instead

Example fix

// before
public String helper() { return "x"; }
// after
private String helper() { return "x"; }
Defensive patterns

Strategy: validation

Validate before calling

for (ASMMethodNodeAdapter m : utilMethods) { if (!m.isPrivate()) { throw new IllegalArgumentException("util method must be private: " + m.getLongName()); } }

Try / catch

try { weaver.weaving(src, adv); } catch (InstrumentException e) { if (e.getMessage().startsWith("non private UtilMethod")) { logger.error("make util method private: {}", e.getMessage()); } }

Prevention

When it happens

Trigger: An @Aspect advice class declares a utility method annotated as a util method with an access modifier other than private, and weaving() encounters it during copyUtilMethods.

Common situations: Plugin authors writing advice utility methods and forgetting to make them private after refactoring visibility, or an upgrade of the weaver adding stricter access checks.

Understand the failure class

Background: UnsupportedOperationException and "is not supported" errors: when a library deliberately refuses a call — this error's family across 30 libraries.

Related errors


AI-assisted analysis of pinpoint-apm/pinpoint@744c3d3075 (2026-09-07). Data as JSON: /api/errors/e74c4ad0f1858e11. Report an issue: GitHub.