Files
hakorune/docs/development/current/main/phases/phase-137/README.md
nyash-codex 962d1803c9 docs: Phase 136/137 - return literal and add expression documentation
Phase 136 Documentation:
- Created docs/development/current/main/phases/phase-136/README.md
- Goal: loop(true) break-once with return literal (Integer)
- Supported: return 7, loop + post + return literal
- Implementation: lower_return_value_to_vid() method
- Tests: 2 fixtures + 4 smokes
- VM/LLVM EXE parity verification commands

Phase 137 Documentation:
- Created docs/development/current/main/phases/phase-137/README.md
- Goal: loop(true) break-once with return add expression
- Supported: return x+2, return 5+3, loop+post+return add
- Implementation: Extended lower_return_value_to_vid() for BinaryOp Add
- Return Value Lowering SSOT documented (lines 29-46)
- Boxification trigger: when 2+ files need identical logic
- Tests: 3 fixtures + 6 smokes
- VM/LLVM EXE parity verification commands

10-Now.md Updates:
- Added Phase 136 entry (return literal)
- Added Phase 137 entry (return add expression)
- Implementation details and test coverage
- Links to phase READMEs

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude Sonnet 4.5 <noreply@anthropic.com>
2025-12-19 00:16:06 +09:00

7.2 KiB

Phase 137: loop(true) break-once with return add expression

Date: 2025-12-18 Status: DONE Scope: return add expression (x + 2) support in Normalized shadow (dev-only)


Goal

Extend Phase 136 return literal to support minimal add expressions:

  • Enable return x + 2 (variable + integer literal)
  • Enable return 5 + 3 (integer literal + integer literal)
  • Keep PHI禁止: merge via env + continuations only
  • Keep dev-only and 既定挙動不変: unmatched shapes fall back

Supported Forms

Supported (Phase 137 P0)

// Form 1: return variable + integer literal
local x
x = 1
loop(true) {
    break
}
return x + 2  // Expected: 3 (1 + 2)
// Form 2: return integer literal + integer literal
loop(true) {
    break
}
return 5 + 3  // Expected: 8
// Form 3: loop + post assigns + return add
local x
x = 0
loop(true) {
    x = 1
    break
}
x = x + 10
return x + 2  // Expected: 13 (0 → 1 → 11 → 13)

Not Supported (Out of Scope)

// Variable + variable (Phase 138+)
return x + y

// Other operators (Phase 138+)
return x - 2
return x * 2

// Nested expressions
return (x + 2) + 3

// Function calls
return f()

Implementation

Core Changes

File: src/mir/control_tree/normalized_shadow/loop_true_break_once.rs

Method: lower_return_value_to_vid() (行 638-743, BinaryOp Add at 行 673)

Added Pattern: BinaryOp Add

ASTNode::BinaryOp { operator, left, right, .. } => {
    // Phase 137 contract: Add only
    if !matches!(operator, BinaryOperator::Add) {
        return Ok(None); // out of scope
    }

    // Lower LHS (Variable or Integer literal)
    let lhs_vid = match left.0.as_ref() {
        ASTNode::Variable { name, .. } => {
            match env.get(name).copied() {
                Some(vid) => vid,
                None => return Ok(None), // out of scope
            }
        }
        ASTNode::Literal { value: LiteralValue::Integer(i), .. } => {
            // Generate Const for LHS
            let vid = ValueId(*next_value_id);
            *next_value_id += 1;
            body.push(JoinInst::Compute(MirLikeInst::Const {
                dst: vid,
                value: ConstValue::Integer(*i),
            }));
            vid
        }
        _ => return Ok(None),
    };

    // Lower RHS (Integer literal only)
    let rhs_vid = match right.0.as_ref() {
        ASTNode::Literal { value: LiteralValue::Integer(i), .. } => {
            let vid = ValueId(*next_value_id);
            *next_value_id += 1;
            body.push(JoinInst::Compute(MirLikeInst::Const {
                dst: vid,
                value: ConstValue::Integer(*i),
            }));
            vid
        }
        _ => return Ok(None), // e.g., return x + y
    };

    // Generate BinOp Add
    let result_vid = ValueId(*next_value_id);
    *next_value_id += 1;
    body.push(JoinInst::Compute(MirLikeInst::BinOp {
        dst: result_vid,
        op: BinOpKind::Add,
        lhs: lhs_vid,
        rhs: rhs_vid,
    }));

    Ok(Some(result_vid))
}

Return Value Lowering SSOT

Location: src/mir/control_tree/normalized_shadow/loop_true_break_once.rs (行 29-43)

SSOT Documentation:

//! ## Return Value Lowering SSOT (Phase 137+)
//!
//! - Function: `lower_return_value_to_vid()`
//! - Responsibility: Lower return values (variable, literal, expr) to ValueId
//! - Supported patterns:
//!   - Variable: env lookup
//!   - Integer literal: Const generation
//!   - Add expr (Phase 137): x + 2 → BinOp(Add, env[x], Const(2))
//! - Fallback: Out-of-scope patterns return `Ok(None)` for legacy routing
//!
//! ### Boxification Trigger
//!
//! If 2+ files need identical return lowering logic, promote to:
//! - `normalized_shadow/common/return_value_lowerer_box.rs`
//! - Single responsibility: return value → ValueId conversion

Fixtures

  1. phase137_loop_true_break_once_return_add_min.hako

    • Pattern: x=1; loop(true){break}; return x+2
    • Expected: exit code 3
  2. phase137_loop_true_break_once_return_add_const_min.hako

    • Pattern: loop(true){break}; return 5+3
    • Expected: exit code 8
  3. phase137_loop_true_break_once_post_return_add_min.hako

    • Pattern: x=0; loop(true){x=1;break}; x=x+10; return x+2
    • Expected: exit code 13

Smoke Tests

VM:

  • tools/smokes/v2/profiles/integration/apps/phase137_loop_true_break_once_return_add_vm.sh
  • tools/smokes/v2/profiles/integration/apps/phase137_loop_true_break_once_return_add_const_vm.sh
  • tools/smokes/v2/profiles/integration/apps/phase137_loop_true_break_once_post_return_add_vm.sh

LLVM EXE:

  • tools/smokes/v2/profiles/integration/apps/phase137_loop_true_break_once_return_add_llvm_exe.sh
  • tools/smokes/v2/profiles/integration/apps/phase137_loop_true_break_once_return_add_const_llvm_exe.sh
  • tools/smokes/v2/profiles/integration/apps/phase137_loop_true_break_once_post_return_add_llvm_exe.sh

Verification

# Build
cargo build --release -p nyash-rust --features llvm

# Phase 137 smokes (6 tests)
bash tools/smokes/v2/profiles/integration/apps/phase137_loop_true_break_once_return_add_vm.sh
bash tools/smokes/v2/profiles/integration/apps/phase137_loop_true_break_once_return_add_const_vm.sh
bash tools/smokes/v2/profiles/integration/apps/phase137_loop_true_break_once_post_return_add_vm.sh
bash tools/smokes/v2/profiles/integration/apps/phase137_loop_true_break_once_return_add_llvm_exe.sh
bash tools/smokes/v2/profiles/integration/apps/phase137_loop_true_break_once_return_add_const_llvm_exe.sh
bash tools/smokes/v2/profiles/integration/apps/phase137_loop_true_break_once_post_return_add_llvm_exe.sh

# Regressions
bash tools/smokes/v2/profiles/integration/apps/phase97_next_non_ws_llvm_exe.sh
bash tools/smokes/v2/profiles/integration/apps/phase97_json_loader_escape_llvm_exe.sh
bash tools/smokes/v2/profiles/integration/apps/phase131_loop_true_break_once_vm.sh
bash tools/smokes/v2/profiles/integration/apps/phase135_loop_true_break_once_post_empty_return_vm.sh
bash tools/smokes/v2/profiles/integration/apps/phase136_loop_true_break_once_return_literal_vm.sh

Acceptance Criteria

  • Phase 137 VM: 3/3 PASS
  • Phase 137 LLVM EXE: 3/3 PASS
  • Phase 97 regression: 2/2 PASS
  • Phase 131/135/136 regression: 3/3 PASS
  • Dev toggle OFF → no impact (Ok(None) fallback)

Key Design Points

Ok(None) for Fallback

  • Unsupported patterns (e.g., return x + y, return x - 2) return Ok(None)
  • Fallback to existing JoinIR routing
  • No hard errors for out-of-scope patterns

BinOp Generation Pattern

  • LHS: Variable (env lookup) or Integer literal (Const generation)
  • RHS: Integer literal only (Const generation)
  • Result: BinOp(Add, lhs_vid, rhs_vid)

Phase 137 P0 Scope Decision

  • Approach A (adopted): Direct extension in loop_true_break_once.rs
  • Reasoning: Small change scope, no boxification needed yet
  • Boxification Trigger: When 2+ files need identical return lowering logic

post_if_post_k.rs Not Modified

  • Different responsibility (if-with-post normalization)
  • Unification planned for Phase 138-139 when needed

Current Status

Phase 137 - DONE (2025-12-18)

VM/LLVM EXE parity achieved (exit codes 3, 8, 13).

Return Value Lowering SSOT documented in loop_true_break_once.rs.