Add the br_icmp instruction.

This instruction behaves like icmp fused with brnz, and it can be used
to represent fused compare+branch instruction on Intel when optimizing
for macro-op fusion.

RISC-V provides compare-and-branch instructions directly, and it is
needed there too.
This commit is contained in:
Jakob Stoklund Olesen
2017-04-03 13:44:15 -07:00
parent 175b269760
commit d2ddc700a8
8 changed files with 73 additions and 23 deletions

View File

@@ -241,20 +241,14 @@ impl<'a> Context<'a> {
self.map.rewrite_values(args.as_mut_slice(value_lists), loc)?;
}
InstructionData::Jump { ref mut destination, ref mut args, .. } => {
InstructionData::Jump { ref mut destination, ref mut args, .. } |
InstructionData::Branch { ref mut destination, ref mut args, .. } |
InstructionData::BranchIcmp { ref mut destination, ref mut args, .. } => {
self.map.rewrite_ebb(destination, loc)?;
self.map.rewrite_values(args.as_mut_slice(value_lists), loc)?;
}
InstructionData::Branch { ref mut destination, ref mut args, .. } => {
self.map.rewrite_ebb(destination, loc)?;
self.map.rewrite_values(args.as_mut_slice(value_lists), loc)?;
}
InstructionData::Call { ref mut args, .. } => {
self.map.rewrite_values(args.as_mut_slice(value_lists), loc)?;
}
InstructionData::Call { ref mut args, .. } |
InstructionData::IndirectCall { ref mut args, .. } => {
self.map.rewrite_values(args.as_mut_slice(value_lists), loc)?;
}
@@ -1521,6 +1515,23 @@ impl<'a> Parser<'a> {
args: args.into_value_list(&[ctrl_arg], &mut ctx.function.dfg.value_lists),
}
}
InstructionFormat::BranchIcmp => {
let cond = self.match_enum("expected intcc condition code")?;
self.match_token(Token::Comma, "expected ',' between operands")?;
let lhs = self.match_value("expected SSA value first operand")?;
self.match_token(Token::Comma, "expected ',' between operands")?;
let rhs = self.match_value("expected SSA value second operand")?;
self.match_token(Token::Comma, "expected ',' between operands")?;
let ebb_num = self.match_ebb("expected branch destination EBB")?;
let args = self.parse_opt_value_list()?;
InstructionData::BranchIcmp {
opcode: opcode,
ty: VOID,
cond: cond,
destination: ebb_num,
args: args.into_value_list(&[lhs, rhs], &mut ctx.function.dfg.value_lists),
}
}
InstructionFormat::InsertLane => {
let lhs = self.match_value("expected SSA value first operand")?;
self.match_token(Token::Comma, "expected ',' between operands")?;