refactor(joinir): Phase 189 - Remove hardcoded 'sum' variable, generalize exit PHI connection
Key improvements: 1. **Eliminate hardcoded variable name**: Replace hardcoded "sum" with generic ValueId-based variable_map updates. Add new JoinInlineBoundary constructor `new_with_input_and_host_outputs()` for Pattern 3. 2. **Generalize output slot mapping**: Exit PHI result now updates all host_outputs entries in variable_map, not just hardcoded "sum". Prepares for future multi-carrier patterns. 3. **PHI preservation in blocks**: Fix block finalization to preserve existing PHI instructions (from handle_select) instead of overwriting them. 4. **Stable function name→ValueId mapping**: Ensure consistent ValueId assignment for tail call detection across multi-function merges. 5. **Enhanced debugging**: Add detailed logging in block converter and meta analysis for PHI verification. Files modified: - src/mir/builder/control_flow.rs: Remove hardcoded "sum", use boundary outputs - src/mir/join_ir/lowering/inline_boundary.rs: Add new constructor - src/mir/join_ir_vm_bridge/joinir_block_converter.rs: Stable mappings, PHI preservation - src/mir/join_ir_vm_bridge/meta.rs: Debug output for PHI tracking - src/mir/builder/joinir_id_remapper.rs: PHI value remapping - src/mir/builder/joinir_inline_boundary_injector.rs: Span preservation Test status: Pattern 3 (loop_if_phi.hako) still produces correct result (sum=9, RC=9) 🤖 Generated with [Claude Code](https://claude.com/claude-code) Co-Authored-By: ChatGPT <noreply@openai.com> Co-Authored-By: Claude <noreply@anthropic.com>
This commit is contained in:
@ -795,29 +795,17 @@ impl super::MirBuilder {
|
||||
// Phase 188-Impl-3: Create and pass JoinInlineBoundary for Pattern 3
|
||||
// Pattern 3 has TWO carriers: i and sum
|
||||
self.trace_varmap("pattern3_before_merge");
|
||||
let boundary = crate::mir::join_ir::lowering::inline_boundary::JoinInlineBoundary::new_inputs_only(
|
||||
let boundary = crate::mir::join_ir::lowering::inline_boundary::JoinInlineBoundary::new_with_input_and_host_outputs(
|
||||
vec![ValueId(0), ValueId(1)], // JoinIR's main() parameters (i, sum init)
|
||||
vec![loop_var_id, sum_var_id], // Host's loop variables
|
||||
vec![sum_var_id], // Host output slot to be updated with exit PHI
|
||||
);
|
||||
let exit_phi_result = self.merge_joinir_mir_blocks(&mir_module, Some(&boundary), debug)?;
|
||||
self.trace_varmap("pattern3_after_merge");
|
||||
|
||||
// Phase 189-Fix: Update variable_map["sum"] to point to exit PHI result
|
||||
// The exit PHI contains the final value of sum after the loop completes.
|
||||
// This ensures subsequent references to "sum" (e.g., `return sum`) use the correct value.
|
||||
if let Some(exit_phi) = exit_phi_result {
|
||||
self.variable_map.insert("sum".to_string(), exit_phi);
|
||||
if debug {
|
||||
eprintln!(
|
||||
"[cf_loop/joinir/pattern3] Updated variable_map['sum'] to exit PHI {:?}",
|
||||
exit_phi
|
||||
);
|
||||
}
|
||||
self.trace_varmap("pattern3_exit_phi_connected");
|
||||
}
|
||||
|
||||
// Phase 188-Impl-3: Return Void (the loop itself doesn't produce a value, but its result
|
||||
// is now accessible via variable_map["sum"])
|
||||
// Phase 189-Refine: variable_map の更新は merge_joinir_mir_blocks 内で
|
||||
// JoinInlineBoundary.host_outputs を用いて行われる。
|
||||
// この関数では Void を返すだけでよい(戻り値は後続の `return sum` が扱う)。
|
||||
let void_val = crate::mir::builder::emission::constant::emit_void(self);
|
||||
|
||||
if debug {
|
||||
@ -864,8 +852,9 @@ impl super::MirBuilder {
|
||||
/// # Returns
|
||||
///
|
||||
/// Returns `Ok(Some(exit_phi_id))` if the merged JoinIR functions have return values
|
||||
/// that were collected into an exit block PHI. This allows the caller to connect
|
||||
/// the exit PHI result to the appropriate host variable.
|
||||
/// that were collected into an exit block PHI. さらに、`boundary` に
|
||||
/// host_outputs が指定されている場合は、exit PHI の結果をホスト側の
|
||||
/// SSA スロットへ再接続する(variable_map 内の ValueId を更新する)。
|
||||
fn merge_joinir_mir_blocks(
|
||||
&mut self,
|
||||
mir_module: &crate::mir::MirModule,
|
||||
@ -1349,19 +1338,29 @@ impl super::MirBuilder {
|
||||
};
|
||||
|
||||
// Phase 189-Fix: Store exit PHI result in variable_map so host code can reference it
|
||||
// The loop result should update the corresponding carrier variable
|
||||
// The loop result should update the corresponding carrier variable(s) declared
|
||||
// in JoinInlineBoundary.host_outputs.
|
||||
if let Some(phi_result) = exit_phi_result_id {
|
||||
// Use boundary output info to connect exit PHI to host variables
|
||||
if let Some(ref boundary) = boundary {
|
||||
// If boundary has outputs, map JoinIR output to host output
|
||||
if !boundary.join_outputs.is_empty() && !boundary.host_outputs.is_empty() {
|
||||
// For now, we assume single output (sum in the pattern)
|
||||
// Future: support multiple outputs
|
||||
if debug {
|
||||
eprintln!(
|
||||
"[cf_loop/joinir] Would connect exit PHI {:?} to host output {:?}",
|
||||
phi_result, boundary.host_outputs
|
||||
);
|
||||
// Phase 189-Refine: 現時点では単一出力 (Pattern 3 の sum) のみを想定し、
|
||||
// host_outputs に登録された ValueId と同じ値を持つ variable_map の
|
||||
// エントリを exit PHI 結果に差し替える。
|
||||
//
|
||||
// 将来 Multi-carrier を扱う際は、join_outputs と host_outputs の
|
||||
// ペアに対して同様の処理を行う。
|
||||
for &host_out in &boundary.host_outputs {
|
||||
// variable_map は name → ValueId のマップなので、
|
||||
// 値が host_out になっているものを exit PHI に更新する。
|
||||
for (name, vid) in self.variable_map.iter_mut() {
|
||||
if *vid == host_out {
|
||||
*vid = phi_result;
|
||||
if debug {
|
||||
eprintln!(
|
||||
"[cf_loop/joinir] Updated variable_map['{}'] to exit PHI {:?}",
|
||||
name, phi_result
|
||||
);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user