Auto merge of #83663 - AngelicosPhosphoros:simplify_binary_and_to_get_better_asm, r=nagisa
Simplify logical operations CFG This is basically same commit ase38e954a0d
which was reverted later in676953fde9
In both cases, this changes weren't benchmarked.e38e954a0d
leads to missed optimization described in [this issue](https://github.com/rust-lang/rust/issues/62993)676953fde9
leads to missed optimization described in [this issue](https://github.com/rust-lang/rust/issues/83623)
This commit is contained in:
commit
d1065e6cef
8 changed files with 360 additions and 325 deletions
|
@ -111,18 +111,17 @@ impl<'a, 'tcx> Builder<'a, 'tcx> {
|
|||
ExprKind::LogicalOp { op, lhs, rhs } => {
|
||||
// And:
|
||||
//
|
||||
// [block: If(lhs)] -true-> [else_block: If(rhs)] -true-> [true_block]
|
||||
// | | (false)
|
||||
// +----------false-----------+------------------> [false_block]
|
||||
// [block: If(lhs)] -true-> [else_block: dest = (rhs)]
|
||||
// | (false)
|
||||
// [shortcurcuit_block: dest = false]
|
||||
//
|
||||
// Or:
|
||||
//
|
||||
// [block: If(lhs)] -false-> [else_block: If(rhs)] -true-> [true_block]
|
||||
// | (true) | (false)
|
||||
// [true_block] [false_block]
|
||||
// [block: If(lhs)] -false-> [else_block: dest = (rhs)]
|
||||
// | (true)
|
||||
// [shortcurcuit_block: dest = true]
|
||||
|
||||
let (true_block, false_block, mut else_block, join_block) = (
|
||||
this.cfg.start_new_block(),
|
||||
let (shortcircuit_block, mut else_block, join_block) = (
|
||||
this.cfg.start_new_block(),
|
||||
this.cfg.start_new_block(),
|
||||
this.cfg.start_new_block(),
|
||||
|
@ -130,41 +129,31 @@ impl<'a, 'tcx> Builder<'a, 'tcx> {
|
|||
|
||||
let lhs = unpack!(block = this.as_local_operand(block, lhs));
|
||||
let blocks = match op {
|
||||
LogicalOp::And => (else_block, false_block),
|
||||
LogicalOp::Or => (true_block, else_block),
|
||||
LogicalOp::And => (else_block, shortcircuit_block),
|
||||
LogicalOp::Or => (shortcircuit_block, else_block),
|
||||
};
|
||||
let term = TerminatorKind::if_(this.tcx, lhs, blocks.0, blocks.1);
|
||||
this.cfg.terminate(block, source_info, term);
|
||||
|
||||
this.cfg.push_assign_constant(
|
||||
shortcircuit_block,
|
||||
source_info,
|
||||
destination,
|
||||
Constant {
|
||||
span: expr_span,
|
||||
user_ty: None,
|
||||
literal: match op {
|
||||
LogicalOp::And => ty::Const::from_bool(this.tcx, false).into(),
|
||||
LogicalOp::Or => ty::Const::from_bool(this.tcx, true).into(),
|
||||
},
|
||||
},
|
||||
);
|
||||
this.cfg.goto(shortcircuit_block, source_info, join_block);
|
||||
|
||||
let rhs = unpack!(else_block = this.as_local_operand(else_block, rhs));
|
||||
let term = TerminatorKind::if_(this.tcx, rhs, true_block, false_block);
|
||||
this.cfg.terminate(else_block, source_info, term);
|
||||
this.cfg.push_assign(else_block, source_info, destination, Rvalue::Use(rhs));
|
||||
this.cfg.goto(else_block, source_info, join_block);
|
||||
|
||||
this.cfg.push_assign_constant(
|
||||
true_block,
|
||||
source_info,
|
||||
destination,
|
||||
Constant {
|
||||
span: expr_span,
|
||||
user_ty: None,
|
||||
literal: ty::Const::from_bool(this.tcx, true).into(),
|
||||
},
|
||||
);
|
||||
|
||||
this.cfg.push_assign_constant(
|
||||
false_block,
|
||||
source_info,
|
||||
destination,
|
||||
Constant {
|
||||
span: expr_span,
|
||||
user_ty: None,
|
||||
literal: ty::Const::from_bool(this.tcx, false).into(),
|
||||
},
|
||||
);
|
||||
|
||||
// Link up both branches:
|
||||
this.cfg.goto(true_block, source_info, join_block);
|
||||
this.cfg.goto(false_block, source_info, join_block);
|
||||
join_block.unit()
|
||||
}
|
||||
ExprKind::Loop { body } => {
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue