feat(joinir): Phase 188.3 - Pattern6 (NestedLoopMinimal) 選択ロジック実装
## Phase 188.3 進捗: Phase 2 完了 (6/13 tasks) ### 実装完了 ✅ **Phase 1: Fixture作成** - apps/tests/phase1883_nested_minimal.hako 追加 - Add/Compare のみ(乗算なし) - 期待 exit code: 9 (3×3 nested loops) - 既存 lowering で fallback 動作確認 **Phase 2: 選択ロジック (SSOT)** - LoopPatternContext に step_tree_max_loop_depth フィールド追加 - choose_pattern_kind() に Pattern6 選択ロジック実装: 1. Cheap check (has_inner_loop) 2. StepTree 構築 (max_loop_depth 取得) 3. AST validation (is_pattern6_lowerable) - pattern6_nested_minimal.rs モジュール作成 (stub) - LOOP_PATTERNS に Pattern6 entry 追加 - **検証**: Pattern6 が正しく選択される ✅ ### 設計原則 (確認済み) 1. **Fail-Fast**: Pattern6 選択後は Ok(None) で逃げない 2. **outer 変数 write-back 検出 → validation false** (Phase 188.4+) 3. **最小実装**: inner local だけ、Pattern1 モデル二重化 4. **cfg! 依存なし**: production で動作 ### 検証結果 ``` [choose_pattern_kind] has_inner_loop=true [choose_pattern_kind] max_loop_depth=2 [choose_pattern_kind] is_pattern6_lowerable=true ✅ Pattern6 SELECTED! ``` Stub からの期待エラー: ``` [ERROR] ❌ [Pattern6] Nested loop lowering not yet implemented ``` ### 次: Phase 3 (Lowering 実装 - 推定4時間) 残りタスク: - Phase 3-1: AST 抽出ヘルパー - Phase 3-2: Validation ヘルパー - Phase 3-3: Continuation 生成 (outer_step, inner_step, k_inner_exit) - Phase 3-4: fixture が exit=9 を返すことを検証 ### 変更ファイル **新規**: - apps/tests/phase1883_nested_minimal.hako - src/mir/builder/control_flow/joinir/patterns/pattern6_nested_minimal.rs - docs/development/current/main/phases/phase-188.{1,2,3}/README.md **変更**: - src/mir/builder/control_flow/joinir/routing.rs (Pattern6 選択) - src/mir/builder/control_flow/joinir/patterns/router.rs (Context 拡張) - src/mir/builder/control_flow/joinir/patterns/mod.rs (module 宣言) 🎯 Generated with [Claude Code](https://claude.com/claude-code) Co-Authored-By: Claude Sonnet 4.5 <noreply@anthropic.com>
This commit is contained in:
104
docs/development/current/main/phases/phase-188.3/README.md
Normal file
104
docs/development/current/main/phases/phase-188.3/README.md
Normal file
@ -0,0 +1,104 @@
|
||||
# Phase 188.3: Nested loop lowering (1-level) — make Pattern 6 real
|
||||
|
||||
**Date**: TBD
|
||||
**Status**: Planning (docs-first)
|
||||
**Prereq**: Phase 188.2 Option A is complete (StepTree depth SSOT + strict Fail-Fast)
|
||||
|
||||
---
|
||||
|
||||
## Goal
|
||||
|
||||
`max_loop_depth == 2`(1-level nested loop)を **JoinIR lowering で実際に通す**。
|
||||
|
||||
- 既知の事実: `LoopForm (=LoopShape)` にはネスト情報が無いので、**LoopFormベースの Pattern6 検出/ルーティングでは実装できない**
|
||||
- 実装は **StepTree(AST側)**を SSOT として扱う(Phase 188.2 Option A を継続)
|
||||
|
||||
---
|
||||
|
||||
## Scope (minimal)
|
||||
|
||||
対応するのは “NestedLoop Minimal” の 1形だけに限定する。
|
||||
|
||||
- depth: `max_loop_depth == 2` のみ
|
||||
- inner loop: Pattern1相当(break/continue 無し)
|
||||
- outer loop: Pattern1相当(break/continue 無し)を優先
|
||||
- それ以外:
|
||||
- strict mode: 明示エラー(Phase 188.2 の depth check とは別タグで良い)
|
||||
- non-strict mode: 既存の fallback 経路に任せる(ただし silent fallback を増やさない)
|
||||
|
||||
---
|
||||
|
||||
## SSOT (what to rely on)
|
||||
|
||||
- nesting depth SSOT: `StepTreeFeatures.max_loop_depth`
|
||||
- depth > 2: strict mode で `control_tree/nested_loop/depth_exceeded`(Phase 188.2)
|
||||
|
||||
---
|
||||
|
||||
## Scope & Variable Model (SSOT)
|
||||
|
||||
Nyash の変数スコープ方針に合わせて、nested loop lowering でも以下を SSOT として固定する。
|
||||
|
||||
### Visibility (read)
|
||||
|
||||
- inner loop から outer の binding は参照できる(lexical scope: “1つ上は見える”)
|
||||
- ただし JoinIR lowering では「見える」を **明示的な引数/継続で表現**する(暗黙キャプチャを増やさない)
|
||||
|
||||
### Mutation (write-back)
|
||||
|
||||
Phase 188.3 では段階的に進める:
|
||||
|
||||
- **P188.3 (minimal)**: outer 変数の **read-only capture** を許す(inner から outer を読む)
|
||||
- **P188.4+ (generalize)**: outer 変数の **write-back** を対応する(inner で outer に代入した値を `k_inner_exit(...)` で戻す)
|
||||
|
||||
この分離により、PHI/exit binding の複雑さを Phase 188.3 に持ち込まずに済む。
|
||||
|
||||
---
|
||||
|
||||
## Lowering sketch (how it should look)
|
||||
|
||||
Nested loop は JoinIR の「tail recursion + continuation」を再帰的に合成して表現する。
|
||||
|
||||
- outer: `outer_step(state..., k_outer_exit)`
|
||||
- inner: `inner_step(state..., k_inner_exit)`
|
||||
- inner が終わったら `k_inner_exit(...)` で outer の“残り”へ戻る
|
||||
|
||||
この `k_inner_exit` がスコープ境界として働くので、将来の write-back もここに集約できる。
|
||||
|
||||
---
|
||||
|
||||
## Deliverables
|
||||
|
||||
1. **Fixture + integration smoke(exit code SSOT)**
|
||||
- 1-level nested loop を最小で再現する `.hako` を追加
|
||||
- integration で実行し、exit code で判定(stdout比較はしない)
|
||||
|
||||
2. **StepTree-based lowering implementation**
|
||||
- StepTree を辿って、inner loop を outer loop の中で正しく lowering できるようにする
|
||||
- 入口は “StepTree→JoinIR” のどこか(LoopFormベースの router は使わない)
|
||||
|
||||
3. **Docs update**
|
||||
- Phase 188.1 の “Pattern6 specification” が design であることは維持
|
||||
- Phase 188.3 で “実装済み/未実装の境界” を明確に書く
|
||||
|
||||
---
|
||||
|
||||
## Acceptance Criteria
|
||||
|
||||
- `./tools/smokes/v2/run.sh --profile quick` が常にグリーン維持
|
||||
- integration selfhost が FAIL=0 を維持
|
||||
- 追加した nested loop fixture が PASS(JoinIR lowering が使われたことをログ/タグで確認可能)
|
||||
|
||||
---
|
||||
|
||||
## Next (schedule)
|
||||
|
||||
- **Phase 188.3**: depth=2 の最小形を “確実に通す” + PoC fixture を smoke 固定
|
||||
- **Phase 188.4+**: write-back(outer carrier reconnection)と “再帰 lowering の一般化(depthを増やしても壊れない)” を docs-first で設計してから実装
|
||||
|
||||
---
|
||||
|
||||
## Out of Scope
|
||||
|
||||
- nested loop + break/continue の一般対応
|
||||
- LoopRegion を使った MIR-level nesting SSOT(Option B)
|
||||
Reference in New Issue
Block a user