Skip to content

Commit 7f6b406

Browse files
authored
Rollup merge of #109582 - scottmcm:local-ref-pending, r=oli-obk
Refactor: Separate `LocalRef` variant for not-evaluated-yet operands As I was reading through this, I noticed that almost every place that was using this needed to distinguish between Some vs None in the match arm anyway, so thought that separating the cases at the variant level might be clearer instead. I like how it ended up; let me know what you think!
2 parents 9c73bf9 + 4979860 commit 7f6b406

File tree

7 files changed

+26
-20
lines changed

7 files changed

+26
-20
lines changed

compiler/rustc_codegen_ssa/src/mir/block.rs

+6-6
Original file line numberDiff line numberDiff line change
@@ -397,8 +397,8 @@ impl<'a, 'tcx, Bx: BuilderMethods<'a, 'tcx>> FunctionCx<'a, 'tcx, Bx> {
397397

398398
PassMode::Cast(cast_ty, _) => {
399399
let op = match self.locals[mir::RETURN_PLACE] {
400-
LocalRef::Operand(Some(op)) => op,
401-
LocalRef::Operand(None) => bug!("use of return before def"),
400+
LocalRef::Operand(op) => op,
401+
LocalRef::PendingOperand => bug!("use of return before def"),
402402
LocalRef::Place(cg_place) => OperandRef {
403403
val: Ref(cg_place.llval, None, cg_place.align),
404404
layout: cg_place.layout,
@@ -1673,7 +1673,7 @@ impl<'a, 'tcx, Bx: BuilderMethods<'a, 'tcx>> FunctionCx<'a, 'tcx, Bx> {
16731673
match self.locals[index] {
16741674
LocalRef::Place(dest) => dest,
16751675
LocalRef::UnsizedPlace(_) => bug!("return type must be sized"),
1676-
LocalRef::Operand(None) => {
1676+
LocalRef::PendingOperand => {
16771677
// Handle temporary places, specifically `Operand` ones, as
16781678
// they don't have `alloca`s.
16791679
return if fn_ret.is_indirect() {
@@ -1694,7 +1694,7 @@ impl<'a, 'tcx, Bx: BuilderMethods<'a, 'tcx>> FunctionCx<'a, 'tcx, Bx> {
16941694
ReturnDest::DirectOperand(index)
16951695
};
16961696
}
1697-
LocalRef::Operand(Some(_)) => {
1697+
LocalRef::Operand(_) => {
16981698
bug!("place local already assigned to");
16991699
}
17001700
}
@@ -1737,7 +1737,7 @@ impl<'a, 'tcx, Bx: BuilderMethods<'a, 'tcx>> FunctionCx<'a, 'tcx, Bx> {
17371737
IndirectOperand(tmp, index) => {
17381738
let op = bx.load_operand(tmp);
17391739
tmp.storage_dead(bx);
1740-
self.locals[index] = LocalRef::Operand(Some(op));
1740+
self.locals[index] = LocalRef::Operand(op);
17411741
self.debug_introduce_local(bx, index);
17421742
}
17431743
DirectOperand(index) => {
@@ -1752,7 +1752,7 @@ impl<'a, 'tcx, Bx: BuilderMethods<'a, 'tcx>> FunctionCx<'a, 'tcx, Bx> {
17521752
} else {
17531753
OperandRef::from_immediate_or_packed_pair(bx, llval, ret_abi.layout)
17541754
};
1755-
self.locals[index] = LocalRef::Operand(Some(op));
1755+
self.locals[index] = LocalRef::Operand(op);
17561756
self.debug_introduce_local(bx, index);
17571757
}
17581758
}

compiler/rustc_codegen_ssa/src/mir/debuginfo.rs

+4-4
Original file line numberDiff line numberDiff line change
@@ -312,7 +312,7 @@ impl<'a, 'tcx, Bx: BuilderMethods<'a, 'tcx>> FunctionCx<'a, 'tcx, Bx> {
312312
LocalRef::Place(place) | LocalRef::UnsizedPlace(place) => {
313313
bx.set_var_name(place.llval, name);
314314
}
315-
LocalRef::Operand(Some(operand)) => match operand.val {
315+
LocalRef::Operand(operand) => match operand.val {
316316
OperandValue::Ref(x, ..) | OperandValue::Immediate(x) => {
317317
bx.set_var_name(x, name);
318318
}
@@ -323,7 +323,7 @@ impl<'a, 'tcx, Bx: BuilderMethods<'a, 'tcx>> FunctionCx<'a, 'tcx, Bx> {
323323
bx.set_var_name(b, &(name.clone() + ".1"));
324324
}
325325
},
326-
LocalRef::Operand(None) => {}
326+
LocalRef::PendingOperand => {}
327327
}
328328
}
329329

@@ -332,9 +332,9 @@ impl<'a, 'tcx, Bx: BuilderMethods<'a, 'tcx>> FunctionCx<'a, 'tcx, Bx> {
332332
}
333333

334334
let base = match local_ref {
335-
LocalRef::Operand(None) => return,
335+
LocalRef::PendingOperand => return,
336336

337-
LocalRef::Operand(Some(operand)) => {
337+
LocalRef::Operand(operand) => {
338338
// Don't spill operands onto the stack in naked functions.
339339
// See: https://github.com/rust-lang/rust/issues/42779
340340
let attrs = bx.tcx().codegen_fn_attrs(self.instance.def_id());

compiler/rustc_codegen_ssa/src/mir/mod.rs

+7-4
Original file line numberDiff line numberDiff line change
@@ -123,7 +123,10 @@ enum LocalRef<'tcx, V> {
123123
/// Every time it is initialized, we have to reallocate the place
124124
/// and update the fat pointer. That's the reason why it is indirect.
125125
UnsizedPlace(PlaceRef<'tcx, V>),
126-
Operand(Option<OperandRef<'tcx, V>>),
126+
/// The backend [`OperandValue`] has already been generated.
127+
Operand(OperandRef<'tcx, V>),
128+
/// Will be a `Self::Operand` once we get to its definition.
129+
PendingOperand,
127130
}
128131

129132
impl<'a, 'tcx, V: CodegenObject> LocalRef<'tcx, V> {
@@ -135,9 +138,9 @@ impl<'a, 'tcx, V: CodegenObject> LocalRef<'tcx, V> {
135138
// Zero-size temporaries aren't always initialized, which
136139
// doesn't matter because they don't contain data, but
137140
// we need something in the operand.
138-
LocalRef::Operand(Some(OperandRef::new_zst(bx, layout)))
141+
LocalRef::Operand(OperandRef::new_zst(bx, layout))
139142
} else {
140-
LocalRef::Operand(None)
143+
LocalRef::PendingOperand
141144
}
142145
}
143146
}
@@ -337,7 +340,7 @@ fn arg_local_refs<'a, 'tcx, Bx: BuilderMethods<'a, 'tcx>>(
337340
// We don't have to cast or keep the argument in the alloca.
338341
// FIXME(eddyb): We should figure out how to use llvm.dbg.value instead
339342
// of putting everything in allocas just so we can use llvm.dbg.declare.
340-
let local = |op| LocalRef::Operand(Some(op));
343+
let local = |op| LocalRef::Operand(op);
341344
match arg.mode {
342345
PassMode::Ignore => {
343346
return local(OperandRef::new_zst(bx, arg.layout));

compiler/rustc_codegen_ssa/src/mir/operand.rs

+2-2
Original file line numberDiff line numberDiff line change
@@ -370,7 +370,7 @@ impl<'a, 'tcx, Bx: BuilderMethods<'a, 'tcx>> FunctionCx<'a, 'tcx, Bx> {
370370
debug!("maybe_codegen_consume_direct(place_ref={:?})", place_ref);
371371

372372
match self.locals[place_ref.local] {
373-
LocalRef::Operand(Some(mut o)) => {
373+
LocalRef::Operand(mut o) => {
374374
// Moves out of scalar and scalar pair fields are trivial.
375375
for elem in place_ref.projection.iter() {
376376
match elem {
@@ -395,7 +395,7 @@ impl<'a, 'tcx, Bx: BuilderMethods<'a, 'tcx>> FunctionCx<'a, 'tcx, Bx> {
395395

396396
Some(o)
397397
}
398-
LocalRef::Operand(None) => {
398+
LocalRef::PendingOperand => {
399399
bug!("use of {:?} before def", place_ref);
400400
}
401401
LocalRef::Place(..) | LocalRef::UnsizedPlace(..) => {

compiler/rustc_codegen_ssa/src/mir/place.rs

+3
Original file line numberDiff line numberDiff line change
@@ -558,6 +558,9 @@ impl<'a, 'tcx, Bx: BuilderMethods<'a, 'tcx>> FunctionCx<'a, 'tcx, Bx> {
558558
bug!("using operand local {:?} as place", place_ref);
559559
}
560560
}
561+
LocalRef::PendingOperand => {
562+
bug!("using still-pending operand local {:?} as place", place_ref);
563+
}
561564
};
562565
for elem in place_ref.projection[base..].iter() {
563566
cg_base = match *elem {

compiler/rustc_codegen_ssa/src/mir/rvalue.rs

+1-1
Original file line numberDiff line numberDiff line change
@@ -545,7 +545,7 @@ impl<'a, 'tcx, Bx: BuilderMethods<'a, 'tcx>> FunctionCx<'a, 'tcx, Bx> {
545545
// ZST are passed as operands and require special handling
546546
// because codegen_place() panics if Local is operand.
547547
if let Some(index) = place.as_local() {
548-
if let LocalRef::Operand(Some(op)) = self.locals[index] {
548+
if let LocalRef::Operand(op) = self.locals[index] {
549549
if let ty::Array(_, n) = op.layout.ty.kind() {
550550
let n = n.eval_target_usize(bx.cx().tcx(), ty::ParamEnv::reveal_all());
551551
return bx.cx().const_usize(n);

compiler/rustc_codegen_ssa/src/mir/statement.rs

+3-3
Original file line numberDiff line numberDiff line change
@@ -18,12 +18,12 @@ impl<'a, 'tcx, Bx: BuilderMethods<'a, 'tcx>> FunctionCx<'a, 'tcx, Bx> {
1818
LocalRef::UnsizedPlace(cg_indirect_dest) => {
1919
self.codegen_rvalue_unsized(bx, cg_indirect_dest, rvalue)
2020
}
21-
LocalRef::Operand(None) => {
21+
LocalRef::PendingOperand => {
2222
let operand = self.codegen_rvalue_operand(bx, rvalue);
23-
self.locals[index] = LocalRef::Operand(Some(operand));
23+
self.locals[index] = LocalRef::Operand(operand);
2424
self.debug_introduce_local(bx, index);
2525
}
26-
LocalRef::Operand(Some(op)) => {
26+
LocalRef::Operand(op) => {
2727
if !op.layout.is_zst() {
2828
span_bug!(
2929
statement.source_info.span,

0 commit comments

Comments
 (0)