chore(joinir): Phase 203-A remove dead code after JoinValueSpace unification
Remove obsolete v1 API and unused imports after Phase 201-202 JoinValueSpace unification. Changes: - Remove v1 API build_for_break_condition() (70 lines) - Converted 3 unit tests to v2 API (build_for_break_condition_v2) - Updated module documentation to reflect v2 as standard - Remove 2 unused imports (JoinValueSpace, ValueId) - inline_boundary_builder.rs: Remove unused JoinValueSpace import - loop_with_if_phi_minimal.rs: Remove unused ValueId import - Document stub function (lower_loop_with_break_to_joinir) - Add Phase 203-A documentation clarifying stub status - Explain why stub exists and migration options - Kept stub as it's called by router (line 148 in loop_pattern_router.rs) Stats: - 4 files changed - 75 net lines removed (117 deletions, 42 insertions) - All tests passing (821 passed) - Build clean with no errors Related: - Phase 201: JoinValueSpace unified ValueId allocation - Phase 202: Pattern 2 conversion to v2 API 🤖 Generated with [Claude Code](https://claude.com/claude-code) Co-Authored-By: Claude Sonnet 4.5 <noreply@anthropic.com>
This commit is contained in:
@ -15,12 +15,14 @@
|
||||
//! # Usage
|
||||
//!
|
||||
//! ```rust
|
||||
//! // Standard break condition analysis
|
||||
//! let (env, bindings) = ConditionEnvBuilder::build_for_break_condition(
|
||||
//! // Standard break condition analysis (Phase 201+)
|
||||
//! let mut space = JoinValueSpace::new();
|
||||
//! let (env, bindings, loop_var_join_id) = ConditionEnvBuilder::build_for_break_condition_v2(
|
||||
//! break_condition,
|
||||
//! &loop_var_name,
|
||||
//! &variable_map,
|
||||
//! loop_var_id,
|
||||
//! &mut space,
|
||||
//! )?;
|
||||
//! ```
|
||||
|
||||
@ -36,78 +38,6 @@ use std::collections::BTreeMap;
|
||||
pub struct ConditionEnvBuilder;
|
||||
|
||||
impl ConditionEnvBuilder {
|
||||
/// Build ConditionEnv and ConditionBindings from break condition
|
||||
///
|
||||
/// This extracts all variables used in the break condition (excluding the loop parameter)
|
||||
/// and creates:
|
||||
/// 1. ConditionEnv: Maps variable names to JoinIR-local ValueIds
|
||||
/// 2. ConditionBindings: Records HOST ValueId ↔ JoinIR ValueId mappings for merge
|
||||
///
|
||||
/// # Arguments
|
||||
///
|
||||
/// * `break_condition` - AST node for the break condition
|
||||
/// * `loop_var_name` - Loop parameter name (excluded from condition-only variables)
|
||||
/// * `variable_map` - HOST function's variable_map (for looking up HOST ValueIds)
|
||||
/// * `loop_var_id` - HOST ValueId for the loop parameter
|
||||
///
|
||||
/// # Returns
|
||||
///
|
||||
/// Tuple of:
|
||||
/// - ConditionEnv: Variable name → JoinIR ValueId mapping
|
||||
/// - Vec<ConditionBinding>: HOST↔JoinIR value mappings for merge
|
||||
///
|
||||
/// # Errors
|
||||
///
|
||||
/// Returns error if a condition variable is not found in variable_map
|
||||
pub fn build_for_break_condition(
|
||||
break_condition: &ASTNode,
|
||||
loop_var_name: &str,
|
||||
variable_map: &BTreeMap<String, ValueId>,
|
||||
_loop_var_id: ValueId,
|
||||
) -> Result<(ConditionEnv, Vec<ConditionBinding>), String> {
|
||||
// Extract all variables used in the condition (excluding loop parameter)
|
||||
let condition_var_names = extract_condition_variables(
|
||||
break_condition,
|
||||
&[loop_var_name.to_string()],
|
||||
);
|
||||
|
||||
let mut env = ConditionEnv::new();
|
||||
let mut bindings = Vec::new();
|
||||
|
||||
// Add loop parameter to env (ValueId(0) in JoinIR space)
|
||||
// The loop parameter is NOT a condition binding (it's a join_input instead)
|
||||
env.insert(loop_var_name.to_string(), ValueId(0));
|
||||
|
||||
// Create a local allocator for JoinIR-local ValueIds for condition-only variables
|
||||
let mut join_value_counter = 1u32; // Start from 1 (0 is reserved for loop param)
|
||||
|
||||
// For each condition variable, allocate JoinIR-local ValueId and build binding
|
||||
for var_name in &condition_var_names {
|
||||
let host_id = variable_map
|
||||
.get(var_name)
|
||||
.copied()
|
||||
.ok_or_else(|| {
|
||||
format!(
|
||||
"Condition variable '{}' not found in variable_map. \
|
||||
Loop condition references undefined variable.",
|
||||
var_name
|
||||
)
|
||||
})?;
|
||||
|
||||
let join_id = ValueId(join_value_counter);
|
||||
join_value_counter += 1;
|
||||
|
||||
env.insert(var_name.clone(), join_id);
|
||||
bindings.push(ConditionBinding {
|
||||
name: var_name.clone(),
|
||||
host_value: host_id,
|
||||
join_value: join_id,
|
||||
});
|
||||
}
|
||||
|
||||
Ok((env, bindings))
|
||||
}
|
||||
|
||||
/// Build ConditionEnv with loop parameter only
|
||||
///
|
||||
/// Used when there are no additional condition-only variables,
|
||||
@ -339,17 +269,22 @@ mod tests {
|
||||
let mut variable_map = BTreeMap::new();
|
||||
variable_map.insert("i".to_string(), ValueId(100));
|
||||
|
||||
let (env, bindings) = ConditionEnvBuilder::build_for_break_condition(
|
||||
let mut space = JoinValueSpace::new();
|
||||
let (env, bindings, loop_var_join_id) = ConditionEnvBuilder::build_for_break_condition_v2(
|
||||
&condition,
|
||||
"i",
|
||||
&variable_map,
|
||||
ValueId(100),
|
||||
&mut space,
|
||||
)
|
||||
.unwrap();
|
||||
|
||||
// Should have loop parameter in env
|
||||
assert!(env.get("i").is_some());
|
||||
|
||||
// Loop var should be in param region (100+)
|
||||
assert!(loop_var_join_id.0 >= 100);
|
||||
|
||||
// Should have no condition-only bindings
|
||||
assert_eq!(bindings.len(), 0);
|
||||
}
|
||||
@ -374,16 +309,19 @@ mod tests {
|
||||
variable_map.insert("i".to_string(), ValueId(100));
|
||||
variable_map.insert("max".to_string(), ValueId(200));
|
||||
|
||||
let (env, bindings) = ConditionEnvBuilder::build_for_break_condition(
|
||||
let mut space = JoinValueSpace::new();
|
||||
let (env, bindings, loop_var_join_id) = ConditionEnvBuilder::build_for_break_condition_v2(
|
||||
&condition,
|
||||
"i",
|
||||
&variable_map,
|
||||
ValueId(100),
|
||||
&mut space,
|
||||
)
|
||||
.unwrap();
|
||||
|
||||
// Should have loop parameter in env
|
||||
assert!(env.get("i").is_some());
|
||||
assert!(loop_var_join_id.0 >= 100);
|
||||
|
||||
// Should have "max" in env with JoinIR-local ValueId
|
||||
assert!(env.get("max").is_some());
|
||||
@ -392,7 +330,8 @@ mod tests {
|
||||
assert_eq!(bindings.len(), 1);
|
||||
assert_eq!(bindings[0].name, "max");
|
||||
assert_eq!(bindings[0].host_value, ValueId(200));
|
||||
assert!(bindings[0].join_value.0 > 0); // JoinIR-local ID
|
||||
// Phase 201: Condition-only variables are allocated from Param region (100+), not Local region
|
||||
assert!(bindings[0].join_value.0 >= 100); // Should be in param region (100+)
|
||||
}
|
||||
|
||||
#[test]
|
||||
@ -415,11 +354,13 @@ mod tests {
|
||||
variable_map.insert("i".to_string(), ValueId(100));
|
||||
// "undefined_var" is NOT in variable_map
|
||||
|
||||
let result = ConditionEnvBuilder::build_for_break_condition(
|
||||
let mut space = JoinValueSpace::new();
|
||||
let result = ConditionEnvBuilder::build_for_break_condition_v2(
|
||||
&condition,
|
||||
"i",
|
||||
&variable_map,
|
||||
ValueId(100),
|
||||
&mut space,
|
||||
);
|
||||
|
||||
// Should return error
|
||||
|
||||
@ -27,7 +27,6 @@
|
||||
use crate::mir::ValueId;
|
||||
use super::inline_boundary::{JoinInlineBoundary, LoopExitBinding};
|
||||
use super::condition_to_joinir::ConditionBinding;
|
||||
use super::join_value_space::JoinValueSpace;
|
||||
|
||||
/// Role of a parameter in JoinIR lowering (Phase 200-A)
|
||||
///
|
||||
|
||||
@ -86,44 +86,30 @@ pub fn lower_loop_with_break_to_joinir(
|
||||
_loop_form: &LoopForm,
|
||||
_lowerer: &mut LoopToJoinLowerer,
|
||||
) -> Option<JoinInst> {
|
||||
// Phase 188-Impl-2: Delegate to minimal lowerer
|
||||
// TODO: Extract LoopScopeShape from loop_form for generic implementation
|
||||
use crate::mir::join_ir::lowering::loop_scope_shape::LoopScopeShape;
|
||||
|
||||
use crate::mir::BasicBlockId;
|
||||
use std::collections::{BTreeMap, BTreeSet};
|
||||
|
||||
// For now, use a placeholder LoopScopeShape
|
||||
// TODO: Build actual LoopScopeShape from loop_form
|
||||
let _placeholder_scope = LoopScopeShape {
|
||||
header: BasicBlockId(0),
|
||||
body: BasicBlockId(0),
|
||||
latch: BasicBlockId(0),
|
||||
exit: BasicBlockId(0),
|
||||
pinned: BTreeSet::new(),
|
||||
carriers: BTreeSet::new(),
|
||||
body_locals: BTreeSet::new(),
|
||||
exit_live: BTreeSet::new(),
|
||||
progress_carrier: None,
|
||||
variable_definitions: BTreeMap::new(),
|
||||
};
|
||||
|
||||
// Generate JoinIR module
|
||||
// Phase 169: lower_loop_with_break_minimal now requires condition AST and builder
|
||||
// This test stub is not used by the actual router, so commenting out for now
|
||||
// let _join_module = lower_loop_with_break_minimal(placeholder_scope, condition, builder)?;
|
||||
|
||||
// Phase 188-Impl-2: Pattern 2 is now integrated in control_flow.rs via cf_loop_pattern2_with_break()
|
||||
// This function (lower_loop_with_break_to_joinir) is currently not used by the router.
|
||||
// The actual lowering happens directly in control_flow.rs which calls loop_with_break_minimal.
|
||||
// Phase 203-A: STUB FUNCTION - Called by router but always returns None
|
||||
//
|
||||
// TODO: Either:
|
||||
// 1. Remove this function and rely only on control_flow.rs integration, OR
|
||||
// 2. Implement JoinModule → JoinInst conversion here (future phase)
|
||||
// Status: This function is called by loop_pattern_router.rs:148 but is a NO-OP stub.
|
||||
// The actual Pattern 2 lowering happens via control_flow.rs.
|
||||
//
|
||||
// Why this stub exists:
|
||||
// - Router expects unified interface: lower_*_to_joinir(loop_form, lowerer)
|
||||
// - Pattern 2 is tightly integrated with control_flow.rs
|
||||
// - Removing it would require updating router dispatch logic
|
||||
//
|
||||
// Current behavior:
|
||||
// 1. Router calls this function (line 148 in loop_pattern_router.rs)
|
||||
// 2. Function logs a message and returns None
|
||||
// 3. Router falls back to control_flow.rs hardcoded Pattern 2 route
|
||||
//
|
||||
// Migration options (future):
|
||||
// - Option 1: Remove stub and update router to call control_flow.rs directly
|
||||
// - Option 2: Implement JoinModule → JoinInst conversion here
|
||||
//
|
||||
// Related code:
|
||||
// - Router callsite: loop_pattern_router.rs:148
|
||||
// - Actual implementation: control_flow::cf_loop_pattern2_with_break()
|
||||
// - Minimal lowerer: loop_with_break_minimal::lower_loop_with_break_minimal()
|
||||
|
||||
eprintln!("[loop_patterns] Pattern 2: Lowering delegated to control_flow.rs");
|
||||
|
||||
// Temporary: Return None to trigger fallback
|
||||
// Pattern 2 currently works via hardcoded route in control_flow.rs
|
||||
eprintln!("[loop_patterns] Pattern 2: Lowering delegated to control_flow.rs (stub)");
|
||||
None
|
||||
}
|
||||
|
||||
@ -73,7 +73,6 @@ use crate::mir::join_ir::{
|
||||
BinOpKind, CompareOp, ConstValue, JoinFuncId, JoinFunction, JoinInst, JoinModule,
|
||||
MirLikeInst, UnaryOp,
|
||||
};
|
||||
use crate::mir::ValueId;
|
||||
|
||||
/// Lower Pattern 3 (Loop with If-Else PHI) to JoinIR
|
||||
///
|
||||
|
||||
Reference in New Issue
Block a user