quarkusio/quarkus · error · IllegalStateException

BUG: Don't know how to generate JVM bridge method for : has

Error message

BUG: Don't know how to generate JVM bridge method for : has primitive parameters

What it means

The Kotlin Panache bytecode generator creates JVM bridge methods that forward calls to the erased generic method. Bridging a parameter requires loading a reference (ALOAD); primitive parameters (int, long, boolean...) cannot be loaded as references, so the generator aborts with this IllegalStateException, indicating an unsupported/unhandled case in the transformation.

Source

Thrown at extensions/panache/panache-common/deployment/src/main/java/io/quarkus/panache/common/deployment/visitors/KotlinPanacheClassOperationGenerationVisitor.java:357

        }
    }

    private void generateBridge(MethodInfo method, String descriptor) {
        MethodVisitor mv = cv.visitMethod(Opcodes.ACC_PUBLIC | Opcodes.ACC_SYNTHETIC | Opcodes.ACC_BRIDGE,
                method.name(),
                descriptor,
                null,
                null);
        List<Type> parameters = method.parameterTypes();
        AsmUtil.copyParameterNames(mv, method);
        mv.visitCode();
        // this
        mv.visitIntInsn(Opcodes.ALOAD, 0);
        // each param
        for (int i = 0; i < parameters.size(); i++) {
            Type paramType = parameters.get(i);
            if (paramType.kind() == Type.Kind.PRIMITIVE)
                throw new IllegalStateException("BUG: Don't know how to generate JVM bridge method for " + method
                        + ": has primitive parameters");
            mv.visitIntInsn(getLoadOpcode(paramType), i + 1);
            if (paramType.kind() == Type.Kind.TYPE_VARIABLE) {
                String typeParamName = paramType.asTypeVariable().identifier();
                org.objectweb.asm.Type type = getType(typeArguments.get(typeParamName).descriptor());
                if (type.getSort() > org.objectweb.asm.Type.DOUBLE) {
                    mv.visitTypeInsn(Opcodes.CHECKCAST, type.getInternalName());
                } else {
                    unboxIfRequired(mv, type);
                }
            }
        }

        String targetDescriptor = method.descriptor(name -> typeArguments.get(name).get());
        mv.visitMethodInsn(Opcodes.INVOKEVIRTUAL,
                classInfo.name().toString().replace('.', '/'),
                method.name(),
                targetDescriptor, false);

View on GitHub (pinned to e1c734241f)

Solutions

  1. Change the method parameter from a primitive type to its boxed wrapper (Int -> Integer/Int?, boolean -> Boolean) so a reference load is possible.
  2. Rename the method so it no longer requires a JVM bridge against the generic supertype method.
  3. Report/fix in Quarkus: add primitive load-opcode handling (IRETURN/LLOAD etc.) to generateBridge in KotlinPanacheClassOperationGenerationVisitor.

Example fix

// before (Kotlin)
override fun findById(id: Long): Person? = ...  // triggers bridge over primitive
// after
override fun findById(id: Long?): Person? = ...  // boxed Long? avoids primitive bridge
Defensive patterns

Strategy: type-guard

Validate before calling

fun bridgeable(method: MethodInfo): Boolean =
    method.parameters().none { it.type().kind() == Type.Kind.PRIMITIVE }

Type guard

fun hasPrimitiveParams(parameters: List<Type>): Boolean =
    parameters.any { it.kind() == Type.Kind.PRIMITIVE }

Try / catch

try {
    visitor.generateBridge(method, parameters);
} catch (IllegalStateException e) {
    if (e.getMessage().contains("primitive parameters")) {
        // skip or box parameters and retry
    } else throw e;
}

Prevention

When it happens

Trigger: visitEnd -> generateBridge encounters a method whose parameters include a primitive Type.Kind.PRIMITIVE while generating bridge methods for a Kotlin Panache class with generic (type-variable) methods.

Common situations: Declaring a Kotlin Panache repository/entity method with primitive parameters that collides with a generic base-class method (same name/erasure), forcing a bridge; Kotlin methods like fun findByName(name: String, active: Boolean) overloading generic Panache methods.

Related errors


AI-assisted analysis of quarkusio/quarkus@e1c734241f (2026-09-05). Data as JSON: /api/errors/00e59ec0a3d1b453. Report an issue: GitHub.