Skip to content

Commit 8b097c4

Browse files
committed
Don't try to promote already promoted out temporaries
1 parent 088fc73 commit 8b097c4

File tree

3 files changed

+33
-4
lines changed

3 files changed

+33
-4
lines changed

src/librustc_mir/transform/promote_consts.rs

+2
Original file line numberDiff line numberDiff line change
@@ -332,6 +332,8 @@ impl<'a, 'tcx> Promoter<'a, 'tcx> {
332332
let operand = Operand::Copy(promoted_place(ty, span));
333333
mem::replace(&mut args[index], operand)
334334
}
335+
// already promoted out
336+
TerminatorKind::Goto { .. } => return,
335337
_ => bug!()
336338
}
337339
}

src/librustc_mir/transform/qualify_consts.rs

+14-4
Original file line numberDiff line numberDiff line change
@@ -812,7 +812,9 @@ impl<'a, 'tcx> Visitor<'tcx> for Qualifier<'a, 'tcx, 'tcx> {
812812

813813
let fn_ty = func.ty(self.mir, self.tcx);
814814
let mut callee_def_id = None;
815-
let (mut is_shuffle, mut is_const_fn) = (false, false);
815+
let mut is_shuffle = false;
816+
let mut is_const_fn = false;
817+
let mut is_promotable_const_fn = false;
816818
if let ty::FnDef(def_id, _) = fn_ty.sty {
817819
callee_def_id = Some(def_id);
818820
match self.tcx.fn_sig(def_id).abi() {
@@ -873,6 +875,9 @@ impl<'a, 'tcx> Visitor<'tcx> for Qualifier<'a, 'tcx, 'tcx> {
873875
// functions without #[rustc_promotable]
874876
if self.tcx.is_promotable_const_fn(def_id) {
875877
is_const_fn = true;
878+
is_promotable_const_fn = true;
879+
} else if self.tcx.is_const_fn(def_id) {
880+
is_const_fn = true;
876881
}
877882
} else {
878883
// stable const fn or unstable const fns with their feature gate
@@ -974,7 +979,9 @@ impl<'a, 'tcx> Visitor<'tcx> for Qualifier<'a, 'tcx, 'tcx> {
974979
if !constant_arguments.contains(&i) {
975980
return
976981
}
977-
if this.qualif.is_empty() {
982+
// if the argument requires a constant, we care about constness, not
983+
// promotability
984+
if (this.qualif - Qualif::NOT_PROMOTABLE).is_empty() {
978985
this.promotion_candidates.push(candidate);
979986
} else {
980987
this.tcx.sess.span_err(this.span,
@@ -985,7 +992,11 @@ impl<'a, 'tcx> Visitor<'tcx> for Qualifier<'a, 'tcx, 'tcx> {
985992
}
986993

987994
// non-const fn calls.
988-
if !is_const_fn {
995+
if is_const_fn {
996+
if !is_promotable_const_fn && self.mode == Mode::Fn {
997+
self.qualif = Qualif::NOT_PROMOTABLE;
998+
}
999+
} else {
9891000
self.qualif = Qualif::NOT_CONST;
9901001
if self.mode != Mode::Fn {
9911002
self.tcx.sess.delay_span_bug(
@@ -1003,7 +1014,6 @@ impl<'a, 'tcx> Visitor<'tcx> for Qualifier<'a, 'tcx, 'tcx> {
10031014
// Be conservative about the returned value of a const fn.
10041015
let tcx = self.tcx;
10051016
let ty = dest.ty(self.mir, tcx).to_ty(tcx);
1006-
self.qualif = Qualif::empty();
10071017
self.add_type(ty);
10081018
}
10091019
self.assign(dest, location);
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,17 @@
1+
// compile-pass
2+
3+
#![feature(const_fn, rustc_attrs)]
4+
5+
#[rustc_args_required_const(0)]
6+
pub const fn a(value: u8) -> u8 {
7+
value
8+
}
9+
10+
#[rustc_args_required_const(0)]
11+
pub fn b(_: u8) {
12+
unimplemented!()
13+
}
14+
15+
fn main() {
16+
let _ = b(a(0));
17+
}

0 commit comments

Comments
 (0)