feat: Type::Tiny support — investigation and fixes#475
Open
feat: Type::Tiny support — investigation and fixes#475
Conversation
Add dev/modules/type_tiny.md documenting the investigation of jcpan Type::Tiny test failures, categorizing 14 distinct issues by root cause and priority. Key findings: - looks_like_number() only checks internal type, not string content - my declarations in for statement modifier dont leak to outer scope - Prototype ;$ functions followed by | infix cause syntax errors - Type::Params v2 wrap_subs cant find functions in callers stash Generated with [Devin](https://cli.devin.ai/docs) Co-Authored-By: Devin <158243242+devin-ai-integration[bot]@users.noreply.github.com>
'for (my ($s, @A) = @_)' with outer parentheses caused the modifier expression to be wrapped in a ListNode, which prevented the existing my-hoisting logic from matching the BinaryOperatorNode pattern. Now unwraps single-element ListNode before checking for the assignment pattern, so both 'for my @w = LIST' and 'for (my @w = LIST)' correctly hoist variable declarations to the enclosing scope. This fixes the dominant Type::Tiny failure (~40+ tests) caused by Type::Tiny.pm line 610: 'for (my ($s, @A) = @_)' where $s was not visible on the next line. Part of Type::Tiny support (Phase 2). Generated with [Devin](https://cli.devin.ai/docs) Co-Authored-By: Devin <158243242+devin-ai-integration[bot]@users.noreply.github.com>
Functions with ;$ prototype (e.g. ArrayRef, HashRef from Types::Standard) now correctly parse binary-only infix operators as argument terminators. For example, ArrayRef | HashRef is now parsed as (ArrayRef()) | (HashRef()) instead of trying to parse | HashRef as an argument to ArrayRef. Added |, ^, |., ^., &., ==, !=, >, >=, .., ..., =~, !~, and ? to isArgumentTerminator in PrototypeArgs.java. This matches Perl behavior where these operators cannot start a primary expression. Generated with [Devin](https://cli.devin.ai/docs) Co-Authored-By: Devin <158243242+devin-ai-integration[bot]@users.noreply.github.com>
When a subroutine contains goto $variable, PerlOnJava falls back to the interpreter backend for that sub. Previously, caller() in such subs returned the wrong package because ExceptionFormatter consumed CallerStack entries from compile-time contexts (BEGIN/use) for interpreter frames. Fix: Remove CallerStack usage from interpreter frame processing entirely. Interpreter frames now always use tokenIndex/PC-based lookup via ByteCodeSourceMapper, avoiding contamination from compile-time CallerStack entries. Also remove unused pre-scan code and all DEBUG_CALLER instrumentation. This fixes Type::Params::signature_for which uses goto $compiled and needs correct caller() to find functions in the caller stash. Tests now passing: v2-defaults.t (2/2), v2-positional.t (13/13), v2-named.t (15/15), v2-allowdash.t (20/20), v2-listtonamed.t (17/17) Generated with [Devin](https://cli.devin.ai/docs) Co-Authored-By: Devin <158243242+devin-ai-integration[bot]@users.noreply.github.com>
Add instruction in AGENTS.md to write commit messages to a temp file and use `git commit -F` instead of `-m`. This avoids problems with apostrophes, backticks, and other special characters in commit messages. Generated with [Devin](https://cli.devin.ai/docs) Co-Authored-By: Devin <158243242+devin-ai-integration[bot]@users.noreply.github.com>
Perl allows ${^_TYPE_PARAMS_MULTISIG} and similar variables where the
first character after ^ is underscore. The parser only accepted
uppercase letters (A-Z), causing compilation failures for code using
this syntax.
This fixes Type::Params multisig support which uses ${^_TYPE_PARAMS_MULTISIG}
internally to track which signature alternative matched.
Generated with [Devin](https://cli.devin.ai/docs)
Co-Authored-By: Devin <158243242+devin-ai-integration[bot]@users.noreply.github.com>
Compiler infrastructure frames (e.g., anonymous sub wrappers from runSpecialBlock for use/BEGIN argument evaluation) can have JVM line number -1, producing stack frames with empty package and line -1. Skip these invalid frames so caller() returns the correct package in compile-time contexts like use constant FBB => enum(...). This fixes Type::Tiny::Enum and other modules that call caller() through wrapper functions during compile-time evaluation. Generated with [Devin](https://cli.devin.ai/docs) Co-Authored-By: Devin <158243242+devin-ai-integration[bot]@users.noreply.github.com>
…sing - BitwiseOperators: check for overloaded '(~' on blessed objects in bitwiseNot() and integerBitwiseNot() before performing bitwise NOT - PrototypeArgs: treat ;$ and ;_ prototypes as named unary operators so that expressions like ArrayRef[Int] | HashRef[Int] parse correctly (| terminates the first argument instead of being consumed by it) Generated with [Devin](https://cli.devin.ai/docs) Co-Authored-By: Devin <158243242+devin-ai-integration[bot]@users.noreply.github.com>
Two fixes: 1. PrototypeArgs: recognize comma as "no argument" for named-unary operators with ;$ or ;_ prototypes. Previously, `Foo, bar` with sub Foo (;$) caused a syntax error because the comma wasn't treated as an argument terminator. This fixes Type::Params::Parameter loading (syntax error at line 445) and unblocks many Type::Tiny tests. 2. BytecodeInterpreter: EQ_STR and NE_STR opcodes now call CompareOperators.eq()/ne() instead of CompareOperators.cmp(). The old code only checked the (cmp overload, missing the (eq/(ne overloads. This fixes matchfor.t where objects with overloaded eq were compared as plain strings. Generated with [Devin](https://cli.devin.ai/docs) Co-Authored-By: Devin <158243242+devin-ai-integration[bot]@users.noreply.github.com>
0fb24a8 to
a379cb5
Compare
…umber
Two fixes:
1. Bytecode compiler (eval context) now compiles the right operand of
grep/map/sort/all/any in LIST context, matching the JVM backend.
Previously, the outer scalar context propagated to the list operand,
causing `scalar(grep { ... } @array)` to only see the array count
(a single number) instead of the actual array elements.
Also simplified the ARRAY_SIZE opcode to use operand.scalar()
uniformly, since RuntimeArray.scalar() already returns the count.
2. looks_like_number now recognizes signed Inf/NaN strings (-Inf, +Inf,
-NaN, +NaN) and case-insensitive variants (inf, nan, etc.).
Generated with [Devin](https://cli.devin.ai/docs)
Co-Authored-By: Devin <158243242+devin-ai-integration[bot]@users.noreply.github.com>
Updated dev/modules/type_tiny.md with: - Phase 5a/5b completed phases and fixes - Results history table (baseline → 99.0%) - Remaining 10 failing tests analysis - Next steps Generated with [Devin](https://cli.devin.ai/docs) Co-Authored-By: Devin <158243242+devin-ai-integration[bot]@users.noreply.github.com>
Three fixes that improve Type::Tiny pass rate from 99.1% to 99.3%: 1. Numify overload: Overload.numify() can return a STRING (e.g., "3.1" from a 0+ handler). getNumberLarge() now converts string results to proper numeric types. Fixes 0+$obj returning truncated integer. 2. AUTOLOAD $AUTOLOAD persistence: autoloadVariableName was permanently set on RuntimeCode objects after first AUTOLOAD fallback. This caused $self->SUPER::AUTOLOAD(@_) to overwrite $AUTOLOAD with garbage. Fixed by skipping $AUTOLOAD assignment when method name IS "AUTOLOAD". 3. Interpreter grep/map outer @_: executeGrep/executeMap didn't pass the enclosing sub's @_ to grep/map blocks (register 1), unlike the JVM backend. Dict+Slurpy inline checks use $_[0] inside grep blocks. Tests fixed: structured.t (110→115/115), Bitfield/basic.t (80→81/81), ConstrainedObject/basic.t (24→27/27), multisig-custom-message.t (→21/21) Generated with [Devin](https://cli.devin.ai/docs) Co-Authored-By: Devin <158243242+devin-ai-integration[bot]@users.noreply.github.com>
When compiling `local @_ = @_`, the RHS @_ evaluated to register 1. PUSH_LOCAL_VARIABLE then cleared register 1 before ARRAY_SET_FROM_LIST could read from it, resulting in @_ always being empty after localizing. Fix: when valueReg == regIdx, copy RHS to a temporary register via NEW_ARRAY + ARRAY_SET_FROM_LIST before calling PUSH_LOCAL_VARIABLE. The JVM backend is not affected (already clones the RHS list before localizing). This fix unlocks 246 more Type::Tiny tests that were previously dying in Type::Params::Alternatives multisig dispatch. v2-returns.t now passes all 5/5 subtests. Type::Tiny results: 345/375 files, 3130/3166 subtests (98.9%) Generated with [Devin](https://cli.devin.ai/docs) Co-Authored-By: Devin <158243242+devin-ai-integration[bot]@users.noreply.github.com>
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Summary
Investigate and fix
./jcpan --jobs 8 -t Type::Tinytest failures for Type::Tiny 2.010001.dev/modules/type_tiny.mdinvestigation plan with 14 categorized issueslooks_like_number()to parse string values (Phase 1)myscoping inforstatement modifier (Phase 2);$with|infix operator parsing (Phase 3)Test plan
makepasses (no regressions)./jcpan --jobs 8 -t Type::Tinyshows improved pass ratelooks_like_number('1.1')returns truefor (my ($s, @a) = @_)scopes variables to enclosing blockArrayRef | HashRefparses correctly with;$prototypeGenerated with Devin