fix(ILO-460): reject nested fn decls with hint to use lambda or top-level helper#774
Merged
Conversation
❌ 1 Tests Failed:
View the top 1 failed test(s) by shortest run time
To view more test analytics, go to the Test Analytics Dashboard |
…evel helper A `name params>type;body` declaration written inside another function's body used to silently hoist to top-level, dropping the enclosing scope. Any reference to a local of the outer function (the `rows` case from the type-coerce-records feedback) then failed verification with a misleading "undefined" cascade. Emit ILO-P023 at the inner header instead. The hint names the two canonical rewrites: an inline lambda for one-off captures, or a top-level helper that takes the captured value as an explicit param. The diagnostic only fires when the inner decl is NOT separated from the surrounding body by an un-indented newline (`decl_boundary`), so genuinely-sibling top-level decls on separate physical lines keep parsing as before. The VM test that relied on indented-continuation silent hoisting is updated to put `f>t` on a clean top-level line. Closure-capturing nested fn decls are a separate language addition; tracked as ILO-485. Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
ILO-P023 was allocated concurrently by the ILO-473 reject-guard-in-lambda PR (#773) which merged into the open-PR set first. Renumbering this branch's diagnostic to ILO-P024 (next free) to avoid a registry collision on merge. No semantic change; same diagnostic, same tests, same hint. Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
The earlier check fired on any inline ;-separated sibling fn decl (test fixtures like `key x:n>n;mod x 2;main xs:L n>L n;uniqby key xs` were broken — aot_cov_partition, aot_cov_uniqby). Restrict to the actual scope-capture trap: enclosing body must already have a binding statement (Stmt::Let) before the would-be nested decl. Sibling top-level decls (one-line or multi-line) parse cleanly again. Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
635aa32 to
f561680
Compare
Three things in this commit: - Restore registry.rs from main (ILO-P023 entry) and append ILO-P024 cleanly. The earlier conflict-marker stripper had merged the two registry entries into one broken block. - Regenerate ai.txt to match SPEC after rebase. - Rewrite ilo468_braceless_guard_tail_wrong_type_inline_lambda to assert ILO-P023 at parse time. Post-ILO-473 the braceless-guard-in-lambda is rejected by the parser before T008 can run; the two diagnostics are complementary, not overlapping, and either closes the silent-miscompile. The named-fn variant of the same trap still pins the T008 path. Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.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
name params>type;bodydeclaration written inside another function's body used to silently hoist to top-level, losing any reference to an enclosing local (therowscase from the type-coerce-records feedback). Emit a precise parse-time diagnostic instead.ILO-P023fires at the inner header, with a hint naming both rewrites: an inline lambda for one-off captures (proc = (x:n>n; +x rows)/{x> +x rows}), or a top-level helper that takes the captured value as an explicit param.decl_boundary), so genuinely-sibling top-level decls on separate physical lines keep parsing as before.ai.txtregenerated automatically bybuild.rs.Follow-up
Closure-capturing nested fn decls (the substantive language feature alternative) tracked separately as ILO-485: https://linear.app/ilo-lang/issue/ILO-485
Closes ILO-460
Test plan
cargo test --features cranelift,http,golden --lib— 3508 pass / 0 fail / 48 ignorednested_fn_decl_in_body_rejected,top_level_fn_decls_still_parse,inline_lambda_in_body_still_parsesGenerated with Claude Code