Skip to content

Fix goto LABEL resolution in loop bodies under subtest#177

Closed
fglock wants to merge 3 commits intomasterfrom
fix-goto-labels-subtests
Closed

Fix goto LABEL resolution in loop bodies under subtest#177
fglock wants to merge 3 commits intomasterfrom
fix-goto-labels-subtests

Conversation

@fglock
Copy link
Copy Markdown
Owner

@fglock fglock commented Feb 7, 2026

Summary

Enabling the upstream/original Test::More (from Test-Simple) caused src/test/resources/unit/control_flow.t to fail inside subtest with:

  • Can't find label NEXT at ... control_flow.t line 201

This PR fixes local label resolution for goto LABEL inside loop-body blocks by ensuring loop body labels are registered in gotoLabelStack while emitting the loop body.

Problem Details

Reproducer

./jperl src/test/resources/unit/control_flow.t

Root cause

EmitControlFlow.handleGotoLabel() determines whether goto LABEL is local via:

  • ctx.javaClassInfo.findGotoLabelsByName(labelName)

The failing construct parses such that the label is scoped to the loop body block:

  • For1Node.Body.BlockNode.labels: NEXT
  • and an explicit LabelNode: NEXT:

However, EmitForeach.emitFor1() emitted the loop body statements directly without registering any goto labels for that body BlockNode. As a result, goto NEXT was treated as non-local and eventually raised an uncaught marker error.

Why upstream Test::More exposes this

Upstream Test::More runs subtest bodies via Test::Builder->subtest, wraps the callback in an eval, and then dies if it failed. This makes label-resolution failures inside subtests fatal and aborts the test file before done_testing().

Changes

1) Register loop-body goto labels in EmitForeach

File: src/main/java/org/perlonjava/codegen/EmitForeach.java

  • Added helper methods to push/pop goto labels for a BlockNode.
  • When For1Node.body is a BlockNode, push labels before emitting statements and pop them after.

This makes forward and backward goto LABEL work correctly inside loop bodies.

2) Pre-register statement labels in EmitBlock

File: src/main/java/org/perlonjava/codegen/EmitBlock.java

  • Pre-register LabelNode statement labels for blocks emitted via EmitBlock.

3) Enable upstream Test::More import

Files:

  • dev/import-perl5/config.yaml
  • src/main/perl/lib/Test/More.pm

This switches Test::More to the upstream/original code path that surfaced the issue.

Tests

  • make passes
  • ./jperl src/test/resources/unit/control_flow.t passes

Notes

  • This PR addresses local goto LABEL resolution during compilation.
  • It does not implement goto EXPR (computed labels), which remains skipped in control_flow.t.

@fglock fglock force-pushed the fix-goto-labels-subtests branch from 543523e to 5a1dbd7 Compare February 7, 2026 14:46
@fglock fglock closed this Feb 7, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant