diff --git a/JAVA_MIGRATION.md b/JAVA_MIGRATION.md index f17c0f3..6c86b0f 100644 --- a/JAVA_MIGRATION.md +++ b/JAVA_MIGRATION.md @@ -29,8 +29,9 @@ hollow and occlusion microblock traits retain Scala inheritance/state/super decl including client bounds/mask updates. `StackAnalyser` initialization and constant-type classification delegate to Java; retain its coordinated Scala class/companion/models. `FieldMixin.accessName` also delegates to Java while retaining its case class. `MixinInfo.linearise` and `ScalaSignature.Bytes.section` delegate traversal and array-copy -behavior to Java. `TypeRef.jName` delegates normalization while preserving its virtual Scala name read. The next -bounded candidate is `ScalaSignature.TypeRef.jDesc`, with characterization before extraction. +behavior to Java. `TypeRef.jName` and `TypeRef.jDesc` delegate normalization and descriptor conversion while +preserving virtual lookup. The next bounded candidate is `ScalaSignature.TMethodType.jDesc`, with characterization +before extraction. Java-trait rewriting and compiler startup also delegate to Java helpers. Abstract Java mixins and Java-path side-only filtering are complete; multiple Scala-trait inheritance still needs its metadata. Retain trait state/accessor/super bridges and the compiler/signature/analyser model shells. diff --git a/JAVA_MIGRATION_HANDOFF.md b/JAVA_MIGRATION_HANDOFF.md index 325c494..04704c8 100644 --- a/JAVA_MIGRATION_HANDOFF.md +++ b/JAVA_MIGRATION_HANDOFF.md @@ -16,24 +16,23 @@ migration checkout; `codex/tile-compatibility-fixes` was deleted after its fixes ## Current state and next target -**442 plain-JVM tests and 237 Java 8 Forge tests pass, with zero failures/errors/skips.** Sources total **224 Java -files and 9 Scala files / 762 nonblank Scala lines**. The packaged inventory has 443 classes. +**449 plain-JVM tests and 237 Java 8 Forge tests pass, with zero failures/errors/skips.** Sources total **224 Java +files and 9 Scala files / 751 nonblank Scala lines**. The packaged inventory has 443 classes. Review follow-up: restored packet-scheduler callback mutation behavior with the original Scala hash-map traversal, virtual tile accessor dispatch throughout `TMultiPart`, and null-safe equality for scheduled-tick deduplication. Six JVM and two Forge regression cases cover the fixes. Callable signatures remain unchanged; the packet traversal callback adds one anonymous class. See the latest history entries for the individual fixes and validation. -Latest bounded target: `ScalaSignature.TypeRef.jName` delegates normalization to `ScalaSignatureParser.typeName`. -Seven characterization tests were committed first as `ac1182e`. They pin dot-to-slash conversion, exact Any/AnyRef -aliases, string identity, virtual name/symbol reads, nulls and failures, the static trait helper and SingleType's -super dispatch. Scala reads `name` once and passes only a String to Java; the path-dependent trait/models and -serialization shapes remain intact. All 442 frozen JVM consumers pass; checks preserve 442 retained class/member -APIs, all 17 ScalaSignature payloads, 3,733 unrelated method bodies and all 116 generated dumps. -Evidence: `run/migration-type-name-reference/`. +Latest bounded target: `ScalaSignature.TypeRef.jDesc` delegates to `ScalaSignatureParser.typeDescriptor`. +Seven characterization tests were committed first as `b3b3f10`. They pin primitive/array matches, unmatched names +(including the legacy Char descriptor), virtual name/jName lookup, repeated symbol reads, nulls, failures and the +static trait helper. TypeRefType's array override and SingleType's super shell remain Scala. All 449 frozen JVM +consumers pass; checks preserve 442 retained class/member APIs, all 17 ScalaSignature payloads, 3,734 unrelated +method bodies and all 116 generated dumps. Evidence: `run/migration-type-descriptor-reference/`. -**Next bounded candidate: `ScalaSignature.TypeRef.jDesc`.** Characterize primitive/array cases, unmatched names, -virtual `jName` fallback and null/failure order. Keep TypeRefType's array override and SingleType's super shell. +**Next bounded candidate: `ScalaSignature.TMethodType.jDesc`.** Characterize ordered parameter info/return-type +reads, descriptor concatenation, nulls, failures and the static trait helper before extracting method assembly. Keep case-class/product/serialization shapes and simple model accessors. Broader shell replacement and opcode algorithm fixes remain separate work. The external ProjectRed Scala-trait fixture and ScalaSignature model bridges remain required. Actual client diff --git a/docs/migration/HISTORY.md b/docs/migration/HISTORY.md index ec44061..6246bd5 100644 --- a/docs/migration/HISTORY.md +++ b/docs/migration/HISTORY.md @@ -1457,3 +1457,21 @@ differences belong in the [divergence ledger](../../JAVA_MIGRATION_DIVERGENCES.m final builds use the committed Git version. Source totals are 224 Java files and nine Scala files / 762 nonblank lines. Next candidate: `ScalaSignature.TypeRef.jDesc`, preserving primitive/array cases, virtual fallback and failure order while retaining the model overrides and trait bridges. + +### 2026-09-04 — ScalaSignature type descriptors + +- Committed seven JVM characterization cases first as `b3b3f10` against the untouched `TypeRef.jDesc`. They pin + exact primitive/array matching, legacy reference descriptors (including Char), virtual fallback and repeated + symbol reads, null/failure order, SingleType/NoType behavior, TypeRefType's first array argument and the static + trait helper with an independent proxy consumer. +- Extracted conversion into `ScalaSignatureParser.typeDescriptor(Object)`, keeping path-dependent types inside + Java method bodies. Literal equality retains the null-name fallback, and `jName()` remains virtual and lazy. + Scala declarations, array override, super dispatch and serialization shapes remain unchanged. +- Normal and clean validation pass 449 JVM tests, 449 frozen consumers and 237 Java 8 Forge tests with zero + failures/errors/skips. Both jars contain 443 Java 8 classes and matching packaged sources. Comparison preserves + 442 retained class/member APIs, all 17 ScalaSignature payloads, 3,734 unrelated method bodies and all 116 generated + dumps. Only one package-private helper method is added; there is no class inventory change or new divergence. +- Evidence is under ignored `run/migration-type-descriptor-reference/`, including the reference jar, compiled tests, + resources, reports and comparison tools. Frozen runs use its `version.txt`; final builds use the committed version. + Source totals are 224 Java files and nine Scala files / 751 nonblank lines. Next: `TMethodType.jDesc` assembly, + preserving parameter/return lookup order, nulls, failures and the retained trait/models. diff --git a/src/main/scala/codechicken/multipart/asm/ScalaSignature.scala b/src/main/scala/codechicken/multipart/asm/ScalaSignature.scala index 5bf4cac..e31784b 100644 --- a/src/main/scala/codechicken/multipart/asm/ScalaSignature.scala +++ b/src/main/scala/codechicken/multipart/asm/ScalaSignature.scala @@ -126,18 +126,7 @@ class ScalaSignature(val bytes: Bytes) { def jName = ScalaSignatureParser.typeName(name) - def jDesc = name match { - case "scala.Array" => null - case "scala.Long" => "J" - case "scala.Int" => "I" - case "scala.Short" => "S" - case "scala.Byte" => "B" - case "scala.Double" => "D" - case "scala.Float" => "F" - case "scala.Boolean" => "Z" - case "scala.Unit" => "V" - case _ => "L" + jName + ";" - } + def jDesc = ScalaSignatureParser.typeDescriptor(this) } case class TypeRefType(owner: TypeRef, sym: SymbolRef, typArgs: List[TypeRef]) diff --git a/src/main/scala/codechicken/multipart/asm/ScalaSignatureParser.java b/src/main/scala/codechicken/multipart/asm/ScalaSignatureParser.java index 1f0329e..01c1fe4 100644 --- a/src/main/scala/codechicken/multipart/asm/ScalaSignatureParser.java +++ b/src/main/scala/codechicken/multipart/asm/ScalaSignatureParser.java @@ -26,6 +26,21 @@ final class ScalaSignatureParser { return internalName; } + static String typeDescriptor(Object value) { + ScalaSignature.TypeRef ref = (ScalaSignature.TypeRef) value; + String name = ref.name(); + if ("scala.Array".equals(name)) return null; + if ("scala.Long".equals(name)) return "J"; + if ("scala.Int".equals(name)) return "I"; + if ("scala.Short".equals(name)) return "S"; + if ("scala.Byte".equals(name)) return "B"; + if ("scala.Double".equals(name)) return "D"; + if ("scala.Float".equals(name)) return "F"; + if ("scala.Boolean".equals(name)) return "Z"; + if ("scala.Unit".equals(name)) return "V"; + return "L" + ref.jName() + ";"; + } + static byte[] section(Bytes bytes) { byte[] array = bytes.arr(); int start = bytes.pos();