Skip to main content
FORGEJO ERA / ISSUE #608

JAR entry names are passed to javap as command-line arguments

closedOpened by MelanX on

Original description​

By MelanX · October 23, 2026

Crate: tools/minecraft-options

Commit: 2b2af1e4f8166d02e4732d19e040a53745d97a51

Behavior

Class names come straight from JAR entry names to javap as a bare argument, with no -- and no name validation. Any entry whose bytes contain options.txt becomes a root. An entry named -version.class or -J-XX:....class is parsed by javap as an option, and -J<vm-option> is forwarded to the JVM. This contradicts the module docstring ("inputs are treated strictly as ZIP/class-file data").

Expected behavior

Names that do not match [A-Za-z0-9_$./]+ or that start with - are rejected, and -- precedes the class names.

Impact

Official JARs are SHA-1 verified by update.py, but discover() and --root accept arbitrary JARs, so a crafted JAR can run javap with chosen options and JVM flags.

Locations

  • tools/minecraft-options/analyze_options.py Disassembler.verbose/get (171-229), roots_and_constants (~1797-1823)

Validation and limitations

Built a scratch JAR with entries -version.class and -J-Dsome.prop=1.class: both were returned as roots, and Disassembler.get('-version') returned the JDK version string with no error.