Skip to content

Commit

Permalink
Only allow propagating integers.
Browse files Browse the repository at this point in the history
  • Loading branch information
cjgillot committed Jul 21, 2023
1 parent b365b5f commit 542052d
Show file tree
Hide file tree
Showing 2 changed files with 17 additions and 10 deletions.
2 changes: 1 addition & 1 deletion compiler/rustc_mir_transform/src/const_prop.rs
Original file line number Diff line number Diff line change
Expand Up @@ -135,7 +135,7 @@ impl<'tcx> MirPass<'tcx> for ConstProp {
FlatSet::Top
};

if let FlatSet::Elem(value) = value {
if let FlatSet::Elem(value) = value && value.can_const_prop() {
collector.assignments.insert(location, value);
}
}
Expand Down
25 changes: 16 additions & 9 deletions compiler/rustc_mir_transform/src/dataflow_const_prop.rs
Original file line number Diff line number Diff line change
Expand Up @@ -354,6 +354,12 @@ impl<'tcx> std::fmt::Debug for ScalarTy<'tcx> {
}
}

impl<'tcx> ScalarTy<'tcx> {
pub fn can_const_prop(&self) -> bool {
self.0.try_to_int().is_ok()
}
}

impl<'a, 'm, 'tcx> ConstAnalysis<'a, 'm, 'tcx> {
pub fn new(tcx: TyCtxt<'tcx>, body: &'a Body<'tcx>, map: &'m Map) -> Self {
let param_env = tcx.param_env_reveal_all_normalized(body.source.def_id());
Expand Down Expand Up @@ -527,14 +533,10 @@ impl<'mir, 'tcx>
// Don't overwrite the assignment if it already uses a constant (to keep the span).
}
StatementKind::Assign(box (place, _)) => {
match state.get(place.as_ref(), &results.analysis.0.map) {
FlatSet::Top => (),
FlatSet::Elem(value) => {
self.assignments.insert(location, value);
}
FlatSet::Bottom => {
// This assignment is either unreachable, or an uninitialized value is assigned.
}
if let FlatSet::Elem(value) = state.get(place.as_ref(), results.analysis.0.map)
&& value.can_const_prop()
{
self.assignments.insert(location, value);
}
}
_ => (),
Expand All @@ -560,6 +562,7 @@ impl<'tcx> MutVisitor<'tcx> for CollectAndPatch<'tcx> {

fn visit_statement(&mut self, statement: &mut Statement<'tcx>, location: Location) {
if let Some(value) = self.assignments.get(&location) {
assert!(value.can_const_prop(), "trying to propagate a pointer");
match &mut statement.kind {
StatementKind::Assign(box (_, rvalue)) => {
if !matches!(rvalue, Rvalue::Use(Operand::Constant(_))) {
Expand All @@ -578,6 +581,7 @@ impl<'tcx> MutVisitor<'tcx> for CollectAndPatch<'tcx> {
match operand {
Operand::Copy(place) | Operand::Move(place) => {
if let Some(value) = self.before_effect.get(&(location, *place)) {
assert!(value.can_const_prop(), "trying to propagate a pointer");
*operand = self.make_operand(value.clone());
} else if !place.projection.is_empty() {
self.super_operand(operand, location)
Expand Down Expand Up @@ -613,7 +617,9 @@ pub(crate) struct OperandCollector<'tcx, 'map, 'a> {
impl<'tcx, 'map, 'a> Visitor<'tcx> for OperandCollector<'tcx, 'map, 'a> {
fn visit_operand(&mut self, operand: &Operand<'tcx>, location: Location) {
if let Some(place) = operand.place() {
if let FlatSet::Elem(value) = self.state.get(place.as_ref(), self.map) {
if let FlatSet::Elem(value) = self.state.get(place.as_ref(), self.map)
&& value.can_const_prop()
{
self.visitor.before_effect.insert((location, place), value);
} else if !place.projection.is_empty() {
// Try to propagate into `Index` projections.
Expand All @@ -625,6 +631,7 @@ impl<'tcx, 'map, 'a> Visitor<'tcx> for OperandCollector<'tcx, 'map, 'a> {
fn visit_local(&mut self, local: Local, ctxt: PlaceContext, location: Location) {
if let PlaceContext::NonMutatingUse(NonMutatingUseContext::Copy | NonMutatingUseContext::Move) = ctxt
&& let FlatSet::Elem(value) = self.state.get(local.into(), self.map)
&& value.can_const_prop()
{
self.visitor.before_effect.insert((location, local.into()), value);
}
Expand Down

0 comments on commit 542052d

Please sign in to comment.