Description
We like to pretend that MIR is a single language, but that is not actually true. There are at least two different languages represented by MIR; I will call them MIR "dialects" in the following:
- Pre-drop-elaboration MIR: this dialect implicitly keeps a drop flag for each local variable.
Move
operands and callingDrop
sets that flag. TheDrop
andDropAndReplace
terminators honor that flag and do not calldrop_in_place
when the drop flag indicates this variable has already been moved/dropped. - Post-drop-elaboration MIR: this dialect has no implicit drop flags, and each
Drop
terminator indicates an unconditional call todrop_in_place
. (DropAndReplace
terminators AFAIK cannot exist any more in this dialect.)
The problem with multiple dialects is that they can have different rules for interpreters, code generators, and optimizations, so we need to be careful not to use the wrong optimization with the wrong dialect.
Miri can only interpret the latter dialect. All our optimizations run post-drop-elaboration, so I assume they are all correct only for that second dialect (though some might also be correct for the first one).
I'd like to propose that we treat these dialects more explicitly: a mir::Body
should indicate which dialect it is written in, such that optimizations, codegen, and Miri can ensure they are working with MIR of the right dialect. This becomes more pressing since #86155 is suggesting to add yet another dialect.
Cc @oli-obk -- there is some overlap here with the "phase" in the MIR validator, but I don't think this is entirely the same concept. Different dialects correspond to different phases, but we might have phases within a dialect where certain instructions are being lowered without changing the operational semantics of the language.
Cc @bjorn3 @rust-lang/wg-mir-opt