diff --git a/lib/cretonne/meta/gen_instr.py b/lib/cretonne/meta/gen_instr.py index ece67dfb2f..4d71e1e5b4 100644 --- a/lib/cretonne/meta/gen_instr.py +++ b/lib/cretonne/meta/gen_instr.py @@ -110,8 +110,6 @@ def gen_instruction_data_impl(fmt): - `pub fn opcode(&self) -> Opcode` - `pub fn first_type(&self) -> Type` - - `pub fn second_result(&self) -> Option` - - `pub fn second_result_mut(&mut self) -> Option<&mut PackedOption>` - `pub fn arguments(&self, &pool) -> &[Value]` - `pub fn arguments_mut(&mut self, &pool) -> &mut [Value]` - `pub fn take_value_list(&mut self) -> Option` @@ -147,42 +145,6 @@ def gen_instruction_data_impl(fmt): 'InstructionData::{} {{ ref mut ty, .. }} => ty,' .format(f.name)) - # Generate shared and mutable accessors for `second_result` which only - # applies to instruction formats that can produce multiple results. - # Everything else returns `None`. - fmt.doc_comment('Second result value, if any.') - with fmt.indented( - 'pub fn second_result(&self) -> Option {', '}'): - with fmt.indented('match *self {', '}'): - for f in InstructionFormat.all_formats: - if f.multiple_results: - fmt.line( - 'InstructionData::' + f.name + - ' { second_result, .. }' + - ' => second_result.into(),') - else: - # Single or no results. - fmt.line( - 'InstructionData::{} {{ .. }} => None,' - .format(f.name)) - - fmt.doc_comment('Mutable reference to second result value, if any.') - with fmt.indented( - "pub fn second_result_mut(&mut self)" + - " -> Option<&mut PackedOption> {", '}'): - with fmt.indented('match *self {', '}'): - for f in InstructionFormat.all_formats: - if f.multiple_results: - fmt.line( - 'InstructionData::' + f.name + - ' { ref mut second_result, .. }' + - ' => Some(second_result),') - else: - # Single or no results. - fmt.line( - 'InstructionData::{} {{ .. }} => None,' - .format(f.name)) - fmt.doc_comment('Get the controlling type variable operand.') with fmt.indented( 'pub fn typevar_operand(&self, pool: &ValueListPool) -> ' @@ -529,8 +491,6 @@ def gen_format_constructor(iform, fmt): 'let data = InstructionData::{} {{'.format(iform.name), '};'): fmt.line('opcode: opcode,') fmt.line('ty: types::VOID,') - if iform.multiple_results: - fmt.line('second_result: None.into(),') gen_member_inits(iform, fmt) fmt.line('self.build(data, ctrl_typevar)') diff --git a/lib/cretonne/src/ir/builder.rs b/lib/cretonne/src/ir/builder.rs index c64ce79dc5..312e5144da 100644 --- a/lib/cretonne/src/ir/builder.rs +++ b/lib/cretonne/src/ir/builder.rs @@ -118,13 +118,6 @@ impl<'f> InstBuilderBase<'f> for ReplaceBuilder<'f> { // Construct new ones. self.dfg.make_inst_results(self.inst, ctrl_typevar); } else { - // Reattach the old secondary values. - let old_second_value = self.dfg.inst_results(self.inst).get(1).cloned(); - if let Some(val_ref) = self.dfg[self.inst].second_result_mut() { - // Don't check types here. Leave that to the verifier. - *val_ref = old_second_value.into(); - } - // Normally, make_inst_results() would also set the first result type, but we're not // going to call that, so set it manually. *self.dfg[self.inst].first_type_mut() = self.dfg diff --git a/lib/cretonne/src/ir/dfg.rs b/lib/cretonne/src/ir/dfg.rs index 6fe3f91d57..dc321030b3 100644 --- a/lib/cretonne/src/ir/dfg.rs +++ b/lib/cretonne/src/ir/dfg.rs @@ -457,12 +457,6 @@ impl DataFlowGraph { first_type = Some(constraints.result_type(res_idx, ctrl_typevar)); } - // Update the second_result pointer in `inst`. - if head.is_some() { - *self.insts[inst] - .second_result_mut() - .expect("instruction format doesn't allow multiple results") = head.into(); - } *self.insts[inst].first_type_mut() = first_type.unwrap_or_default(); // Include the first result in the results vector. @@ -497,11 +491,16 @@ impl DataFlowGraph { /// Use this method to detach secondary values before using `replace(inst)` to provide an /// alternate instruction for computing the primary result value. pub fn detach_secondary_results(&mut self, inst: Inst) -> Option { + if !self.has_results(inst) { + return None; + } + + let second = self.results[inst].get(1, &mut self.value_lists); self.results[inst].clear(&mut self.value_lists); if !self.insts[inst].first_type().is_void() { self.results[inst].push(Value::new_direct(inst), &mut self.value_lists); } - self[inst].second_result_mut().and_then(|r| r.take()) + second } /// Get the next secondary result after `value`. @@ -524,32 +523,21 @@ impl DataFlowGraph { /// created automatically. The `res` value must be a secondary instruction result detached from /// somewhere else. pub fn attach_secondary_result(&mut self, last_res: Value, res: Value) { - let (res_inst, res_num) = match last_res.expand() { - ExpandedValue::Direct(inst) => { - // We're adding the second value to `inst`. - let next = self[inst].second_result_mut().expect("bad inst format"); - assert!(next.is_none(), "last_res is not the last result"); - *next = res.into(); - (inst, 1) - } + let res_inst = match last_res.expand() { + ExpandedValue::Direct(inst) => inst, ExpandedValue::Table(idx) => { - if let ValueData::Inst { - num, - inst, - ref mut next, - .. - } = self.extended_values[idx] { + if let ValueData::Inst { inst, ref mut next, .. } = self.extended_values[idx] { assert!(next.is_none(), "last_res is not the last result"); *next = res.into(); - assert!(num < u16::MAX, "Too many arguments to EBB"); - (inst, num + 1) + inst } else { panic!("last_res is not an instruction result"); } } }; - self.results[res_inst].push(res, &mut self.value_lists); + let res_num = self.results[res_inst].push(res, &mut self.value_lists); + assert!(res_num <= u16::MAX as usize, "Too many result values"); // Now update `res` itself. if let ExpandedValue::Table(idx) = res.expand() { @@ -559,7 +547,7 @@ impl DataFlowGraph { ref mut next, .. } = self.extended_values[idx] { - *num = res_num; + *num = res_num as u16; *inst = res_inst; *next = None.into(); return; diff --git a/lib/cretonne/src/ir/instructions.rs b/lib/cretonne/src/ir/instructions.rs index 626c130740..29e3e6662f 100644 --- a/lib/cretonne/src/ir/instructions.rs +++ b/lib/cretonne/src/ir/instructions.rs @@ -17,7 +17,6 @@ use ir::types; use ir::DataFlowGraph; use entity_list; -use packed_option::PackedOption; use ref_slice::{ref_slice, ref_slice_mut}; /// Some instructions use an external list of argument values because there is not enough space in @@ -126,7 +125,6 @@ pub enum InstructionData { UnarySplit { opcode: Opcode, ty: Type, - second_result: PackedOption, arg: Value, }, Binary { @@ -143,7 +141,6 @@ pub enum InstructionData { BinaryOverflow { opcode: Opcode, ty: Type, - second_result: PackedOption, args: [Value; 2], }, Ternary { @@ -154,7 +151,6 @@ pub enum InstructionData { MultiAry { opcode: Opcode, ty: Type, - second_result: PackedOption, args: ValueList, }, InsertLane { @@ -216,14 +212,12 @@ pub enum InstructionData { Call { opcode: Opcode, ty: Type, - second_result: PackedOption, func_ref: FuncRef, args: ValueList, }, IndirectCall { opcode: Opcode, ty: Type, - second_result: PackedOption, sig_ref: SigRef, args: ValueList, }, diff --git a/lib/reader/src/parser.rs b/lib/reader/src/parser.rs index 5f51b4c342..f948b1f586 100644 --- a/lib/reader/src/parser.rs +++ b/lib/reader/src/parser.rs @@ -1442,7 +1442,6 @@ impl<'a> Parser<'a> { InstructionData::UnarySplit { opcode: opcode, ty: VOID, - second_result: None.into(), arg: self.match_value("expected SSA value operand")?, } } @@ -1474,7 +1473,6 @@ impl<'a> Parser<'a> { InstructionData::BinaryOverflow { opcode: opcode, ty: VOID, - second_result: None.into(), args: [lhs, rhs], } } @@ -1497,7 +1495,6 @@ impl<'a> Parser<'a> { InstructionData::MultiAry { opcode: opcode, ty: VOID, - second_result: None.into(), args: args.into_value_list(&[], &mut ctx.function.dfg.value_lists), } } @@ -1610,7 +1607,6 @@ impl<'a> Parser<'a> { InstructionData::Call { opcode: opcode, ty: VOID, - second_result: None.into(), func_ref: func_ref, args: args.into_value_list(&[], &mut ctx.function.dfg.value_lists), } @@ -1626,7 +1622,6 @@ impl<'a> Parser<'a> { InstructionData::IndirectCall { opcode: opcode, ty: VOID, - second_result: None.into(), sig_ref: sig_ref, args: args.into_value_list(&[callee], &mut ctx.function.dfg.value_lists), }