Skip to content

Constant expression evaluation in statics is broken #17074

Closed
@mahkoh

Description

@mahkoh
static X: u64 = -1 as u16 as u64;
static Y: u64 = -1 as u32 as u64;

fn main() {
    match 1 {
        X => { },
        Y => { },
        _ => { },
    }
}
<anon>:7:9: 7:10 error: unreachable pattern [E0001] (pass `--explain E0001` to see a detailed explanation)
<anon>:7         Y => { },
   eddyb_ | http://is.gd/skhSd8
   eddyb_ | hmm
   eddyb_ | I wonder
  Gliptic | well, they have the same value in this case
arrrrrrr1 | Gliptic: do they?
   eddyb_ | ah, yes
   eddyb_ | arrrrrrr1: it's abug
   eddyb_ | probably filed a dozen times already
arrrrrrr1 | don't tell me it matches against -1
   eddyb_ | under different and seemingly unrelated descriptions
   eddyb_ | arrrrrrr1: yes it does
   eddyb_ | and it's very complicated to even get there
   eddyb_ | arrrrrrr1: jakub- has worked on that code ~recently
   eddyb_ | I don't know anyknow who knows everything about pattern handling
   eddyb_ | maybe nmatsakis, if you give him a few hours to read it all :P
   eddyb_ | http://is.gd/HDrH3f this is worse
   eddyb_ | and this works http://is.gd/aOHVkr
   eddyb_ | hmm
   eddyb_ | arrrrrrr1: I wonder if they are computed wrong
   eddyb_ | how can we check...
   eddyb_ | enum discriminants :D
   eddyb_ | "error: discriminant value already exists"
   eddyb_ | arrrrrrr1: okay, this might be simpler
   eddyb_ | const_eval is simply wrong
   eddyb_ | eugh
   eddyb_ | so what is this cast... u8 as u64?
   eddyb_ | arrrrrrr1: it ignores the size, lol
   eddyb_ | but, hmm
   eddyb_ | what is the order of operations
   eddyb_ | (-(1u8)) as u64
   eddyb_ | arrrrrrr1: lol it's so wrong
   eddyb_ | arrrrrrr1: it doesn't normalize the expression to its type
   eddyb_ | arrrrrrr1: so -(1u8) produces const_uint(-1u64)
   eddyb_ | same for !0u8
   eddyb_ | arrrrrrr1: and... casts ignore bit sizes so there's no truncate or zero/sign-extend
   eddyb_ | arrrrrrr1: rustc::middle::const_eval::eval_const_expr_partial is just wrong. if you want the location of the wrong code :P

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions