Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Type validation mistreats layout errors #71353

Closed
Michael-F-Bryan opened this issue Apr 20, 2020 · 30 comments · Fixed by #71663 or #71950
Closed

Type validation mistreats layout errors #71353

Michael-F-Bryan opened this issue Apr 20, 2020 · 30 comments · Fixed by #71663 or #71950
Assignees
Labels
A-const-eval Area: Constant evaluation, covers all const contexts (static, const fn, ...) C-cleanup Category: PRs that clean code up or issues documenting cleanup. T-compiler Relevant to the compiler team, which will review and decide on the PR/issue.

Comments

@Michael-F-Bryan
Copy link

Michael-F-Bryan commented Apr 20, 2020

The original problem got fixed by avoiding the broken code paths; this issue now tracks fixing those code paths.

Original issue

In the ffi_helpers crate we have a Nullable trait which gives you a generic way to do null pointer checks.

pub trait Nullable {
    const NULL: Self;

    fn is_null(&self) -> bool;
}

A user recently reported that the crate no longer compiles on nightly (Michael-F-Bryan/ffi_helpers#2) because type validation detects that std::ptr::null() and std::ptr::null_mut() create uninitialized raw pointers.

  Compiling playground v0.0.1 (/playground)
error[E0080]: it is undefined behavior to use this value
  --> src/lib.rs:17:5
   |
17 |     const NULL: Self = std::ptr::null_mut();
   |     ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ type validation failed: encountered uninitialized raw pointer
   |
   = note: The rules on what exactly is undefined behavior aren't clear, so this check might be overzealous. Please open an issue on the rustc repository if you believe it should not be considered undefined behavior.

error: aborting due to previous error

For more information about this error, try `rustc --explain E0080`.
error: could not compile `playground`.

I can reproduce this on the playground with the latest nightly, 1.44.0-nightly (2020-04-19 dbf8b6bf116c7bece298).

Is the use shown in that playground example (*self == Self::NULL on a *mut T) actually UB?

Also, I noticed that calling the is_null() method defined on a raw pointer with <*const T>::is_null(*self) doesn't trigger this error, implying that the problem isn't with declaring a constant that contains a null pointer (const NULL: Self = std::ptr::null_mut()), but the fact that we're using it for a comparison. Was this intended, or is it just an oversight in the error detection code?

Full example with output
pub trait Nullable {
    const NULL: Self;

    fn is_null(&self) -> bool;
}

impl<T> Nullable for *const T {
    const NULL: Self = std::ptr::null();

    #[inline]
    fn is_null(&self) -> bool {
        <*const T>::is_null(*self)
    }
}

impl<T> Nullable for *mut T {
    const NULL: Self = std::ptr::null_mut();

    #[inline]
    fn is_null(&self) -> bool {
        *self == Self::NULL
    }
}
Compiling playground v0.0.1 (/playground)
error[E0080]: it is undefined behavior to use this value
  --> src/lib.rs:17:5
   |
17 |     const NULL: Self = std::ptr::null_mut();
   |     ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ type validation failed: encountered uninitialized raw pointer
   |
   = note: The rules on what exactly is undefined behavior aren't clear, so this check might be overzealous. Please open an issue on the rustc repository if you believe it should not be considered undefined behavior.

error: aborting due to previous error

For more information about this error, try `rustc --explain E0080`.
error: could not compile `playground`.

To learn more, run the command again with --verbose.

CC: @RalfJung because it looks like they were the last person to touch that error message (9ee4d1a).

This issue has been assigned to @jumbatm via this comment.

@jonas-schievink jonas-schievink added A-const-eval Area: Constant evaluation, covers all const contexts (static, const fn, ...) C-bug Category: This is a bug. I-prioritize Issue: Indicates that prioritization has been requested for this issue. regression-from-stable-to-nightly Performance or correctness regression from stable to nightly. T-compiler Relevant to the compiler team, which will review and decide on the PR/issue. labels Apr 20, 2020
@RalfJung
Copy link
Member

RalfJung commented Apr 20, 2020

Cc @rust-lang/wg-const-eval

This is definitely not intended, that example you gave is entirely safe code and should compile just fine.

The odd thing is, I am indeed responsible for the error but that was back in #66147 which has long arrived on stable -- so the error itself cannot be the source of the regression. Would be good to get the regression narrowed down a bit more.

I also don't understand why == seems to be needed to trigger this. Might be some interaction with promotion?

The error message is probably (hopefully!) just wrong, I doubt the pointer is actually uninitialized. We just show that error when anything goes wrong in this line:

let place = try_validation!(
self.ecx.ref_to_mplace(self.ecx.read_immediate(value)?),
"uninitialized raw pointer",
self.path
);

Likely ref_to_mplace really doesn't like that the pointer is NULL. The thing is, this code works fine, and that just makes no sense:

fn main() {
    const NULL: *mut i32 = std::ptr::null_mut();
    println!("{:?}", NULL);
}

@jonas-schievink jonas-schievink added the E-needs-bisection Call for participation: This issue needs bisection: https://github.com/rust-lang/cargo-bisect-rustc label Apr 20, 2020
@jonas-schievink
Copy link
Contributor

@rustbot ping bisect

@rustbot rustbot added the ICEBreaker-Cleanup-Crew Helping to "clean up" bugs with minimal examples and bisections label Apr 20, 2020
@rustbot
Copy link
Collaborator

rustbot commented Apr 20, 2020

Hey Cleanup Crew ICE-breakers! This bug has been identified as a good
"Cleanup ICE-breaking candidate". In case it's useful, here are some
instructions for tackling these sorts of bugs. Maybe take a look?
Thanks! <3

cc @AminArria @chrissimpkins @contrun @DutchGhost @elshize @ethanboxx @h-michael @HallerPatrick @hdhoang @hellow554 @imtsuki @jakevossen5 @kanru @KarlK90 @LeSeulArtichaut @MAdrianMattocks @matheus-consoli @mental32 @nmccarty @Noah-Kennedy @pard68 @PeytonT @pierreN @Redblueflame @RobbieClarken @RobertoSnap @robjtede @SarthakSingh31 @senden9 @shekohex @sinato @spastorino @turboladen @woshilapin @yerke

@RalfJung
Copy link
Member

It's not an ICE, but if ICE-breakers also help with other bisects then yes this would be awesome. :)

@Michael-F-Bryan
Copy link
Author

If it helps pinpoint when the error was introduced, my rustc is usually within a couple days of the latest nightly and I made a release of that crate on 2020-04-07 without hitting any compilation errors.

@senden9
Copy link

senden9 commented Apr 20, 2020

Regression in nightly-2020-04-17. Looking currently for regression commit between 2020-04-17 and 2020-04-16.

searched nightlies: from nightly-2020-04-07 to nightly-2020-04-19
regressed nightly: nightly-2020-04-17
searched commits: from d223029 to 7f3df57
regressed commit: 7f3df57

Full Log:

root@ubuntu-c-32-64gib-fra1-01:~# cargo bisect-rustc --preserve --test-dir=foo --start=2020-04-07 --end=2020-04-19installing nightly-2020-04-07
testing...
RESULT: nightly-2020-04-07, ===> No

installing nightly-2020-04-19
testing...
RESULT: nightly-2020-04-19, ===> Yes

installing nightly-2020-04-13
testing...
RESULT: nightly-2020-04-13, ===> No

installing nightly-2020-04-16
testing...
RESULT: nightly-2020-04-16, ===> No

installing nightly-2020-04-17
testing...
RESULT: nightly-2020-04-17, ===> Yes

searched toolchains nightly-2020-04-07 through nightly-2020-04-19
regression in nightly-2020-04-17
fetching https://static.rust-lang.org/dist/2020-04-17/channel-rust-nightly-git-commit-hash.txt
converted 2020-04-17 to 7f3df5772439eee1c512ed2eb540beef1124d236
fetching https://static.rust-lang.org/dist/2020-04-16/channel-rust-nightly-git-commit-hash.txt
converted 2020-04-16 to d2230290f7220e740ec08f4d844bf5951e1b74b8
looking for regression commit between 2020-04-17 and 2020-04-16
opening existing repository at "rust.git"
refreshing repository
fetching (via local git) commits from d2230290f7220e740ec08f4d844bf5951e1b74b8 to 7f3df5772439eee1c512ed2eb540beef1124d236
opening existing repository at "rust.git"
refreshing repository
looking up first commit
looking up second commit
checking that commits are by bors and thus have ci artifacts...
finding bors merge commits
found 7 bors merge commits in the specified range
  commit[0] 2020-04-15UTC: Auto merge of #71139 - matthiaskrgr:submodule_upd, r=Dylan-DPC
  commit[1] 2020-04-15UTC: Auto merge of #71180 - Dylan-DPC:rollup-pscpg6q, r=Dylan-DPC
  commit[2] 2020-04-16UTC: Auto merge of #71159 - topecongiro:rustfmt-1.4.14, r=Dylan-DPC
  commit[3] 2020-04-16UTC: Auto merge of #71173 - RalfJung:miri, r=RalfJung
  commit[4] 2020-04-16UTC: Auto merge of #70831 - sfackler:shrink-future-stack, r=matthewjasper
  commit[5] 2020-04-16UTC: Auto merge of #70755 - wesleywiser:simplify_locals_2_electric_boogaloo, r=oli-obk
  commit[6] 2020-04-16UTC: Auto merge of #71201 - Dylan-DPC:rollup-23202uf, r=Dylan-DPC
validated commits found, specifying toolchains
installing d2230290f7220e740ec08f4d844bf5951e1b74b8
testing...
RESULT: d2230290f7220e740ec08f4d844bf5951e1b74b8, ===> No

installing 7f3df5772439eee1c512ed2eb540beef1124d236
testing...
RESULT: 7f3df5772439eee1c512ed2eb540beef1124d236, ===> Yes

installing 534a41a32952d36ec73656357777ebbea707aeb4
testing...
RESULT: 534a41a32952d36ec73656357777ebbea707aeb4, ===> No

installing 4e4d49d60fd696c4036d438292673a2d7fd34519
testing...
RESULT: 4e4d49d60fd696c4036d438292673a2d7fd34519, ===> No

installing 7fb5187d0423f4cd0441526571b8cd61927123c9
testing...
RESULT: 7fb5187d0423f4cd0441526571b8cd61927123c9, ===> No

searched toolchains d2230290f7220e740ec08f4d844bf5951e1b74b8 through 7f3df5772439eee1c512ed2eb540beef1124d236
installing 7f3df5772439eee1c512ed2eb540beef1124d236
testing...
regression in 7f3df5772439eee1c512ed2eb540beef1124d236


searched nightlies: from nightly-2020-04-07 to nightly-2020-04-19
regressed nightly: nightly-2020-04-17
searched commits: from https://github.com/rust-lang/rust/commit/d2230290f7220e740ec08f4d844bf5951e1b74b8 to https://github.com/rust-lang/rust/commit/7f3df5772439eee1c512ed2eb540beef1124d236
regressed commit: https://github.com/rust-lang/rust/commit/7f3df5772439eee1c512ed2eb540beef1124d236
source code: URL OF A REPOSITORY THAT REPRODUCES THE ERROR

@LeSeulArtichaut
Copy link
Contributor

If it regressed in 7f3df57, I guess the only PR that could have caused this is #71141? It might explain why == is needed to trigger the error. Otherwise the culprit might be #71149?

@jonas-schievink
Copy link
Contributor

My guess would've been #70566

@RalfJung
Copy link
Member

@senden9 awesome, thanks a lot.

I am very sure it's not #71149, that would ICE complaining about bad types in a function call.

I doubt it's #71141, that doesn't sound likely to me.

My guess is that it's #70566 (Cc @jumbatm), which affects const-prop and what code const-eval gets run on. But still that doesn't explain why it would suddenly stop liking NULL pointers. In fact it's not just NULL, this also fails:

impl<T> Nullable for *mut T {
    const NULL: Self = 4usize as *mut _;

    #[inline]
    fn is_null(&self) -> bool {
        *self == Self::NULL
    }
}

Hm... actually... that const-prop change will mean we run const-prop on some generic code. Maybe it tries to evaluate that == test up there, but because the code is generic cannot actually evaluate enough operands and then some stuff is still uninitialized.

@RalfJung
Copy link
Member

RalfJung commented Apr 20, 2020

Bingo, the RUSTC_MIRI_BACKTRACE also points at const-prop:

backtrace where errors is created
   0: <rustc_middle::mir::interpret::error::InterpErrorInfo as core::convert::From<rustc_middle::mir::interpret::error::InterpError>>::from
             at src/librustc_middle/mir/interpret/error.rs:268
   1: rustc_mir::interpret::validity::ValidityVisitor<M>::try_visit_primitive
             at src/librustc_mir/interpret/validity.rs:486
   2: <rustc_mir::interpret::validity::ValidityVisitor<M> as rustc_mir::interpret::visitor::ValueVisitor<M>>::visit_value
             at src/librustc_mir/interpret/validity.rs:662
      rustc_mir::interpret::validity::<impl rustc_mir::interpret::eval_context::InterpCx<M>>::validate_operand_internal
             at src/librustc_mir/interpret/validity.rs:834
   3: rustc_mir::interpret::validity::<impl rustc_mir::interpret::eval_context::InterpCx<M>>::const_validate_operand
             at src/librustc_mir/interpret/validity.rs:859
      rustc_mir::const_eval::eval_queries::validate_and_turn_into_const::{{closure}}
             at src/librustc_mir/const_eval/eval_queries.rs:192
      rustc_mir::const_eval::eval_queries::validate_and_turn_into_const
             at src/librustc_mir/const_eval/eval_queries.rs:184
      rustc_mir::const_eval::eval_queries::const_eval_validated_provider::{{closure}}
             at src/librustc_mir/const_eval/eval_queries.rs:257
      core::result::Result<T,E>::and_then
             at /home/r/src/rust/rustc/src/libcore/result.rs:729
      rustc_mir::const_eval::eval_queries::const_eval_validated_provider
             at src/librustc_mir/const_eval/eval_queries.rs:257
   4: rustc_middle::ty::query::<impl rustc_query_system::query::config::QueryAccessors<rustc_middle::ty::context::TyCtxt> for rustc_middle::ty::query::queries::const_eval_validated>::compute
             at /home/r/src/rust/rustc/src/librustc_middle/ty/query/plumbing.rs:362
   5: rustc_query_system::dep_graph::graph::DepGraph<K>::with_task_impl
             at /home/r/src/rust/rustc/src/librustc_query_system/dep_graph/graph.rs:303
      rustc_query_system::dep_graph::graph::DepGraph<K>::with_task
             at /home/r/src/rust/rustc/src/librustc_query_system/dep_graph/graph.rs:200
   6: rustc_query_system::query::plumbing::force_query_with_job::{{closure}}::{{closure}}
             at /home/r/src/rust/rustc/src/librustc_query_system/query/plumbing.rs:593
      rustc_middle::ty::query::plumbing::<impl rustc_query_system::query::QueryContext for rustc_middle::ty::context::TyCtxt>::start_query::{{closure}}::{{closure}}
             at /home/r/src/rust/rustc/src/librustc_middle/ty/query/plumbing.rs:71
      rustc_middle::ty::context::tls::enter_context::{{closure}}
             at /home/r/src/rust/rustc/src/librustc_middle/ty/context.rs:1698
      rustc_middle::ty::context::tls::set_tlv
             at /home/r/src/rust/rustc/src/librustc_middle/ty/context.rs:1682
      rustc_middle::ty::context::tls::enter_context
             at /home/r/src/rust/rustc/src/librustc_middle/ty/context.rs:1698
      rustc_middle::ty::query::plumbing::<impl rustc_query_system::query::QueryContext for rustc_middle::ty::context::TyCtxt>::start_query::{{closure}}
             at /home/r/src/rust/rustc/src/librustc_middle/ty/query/plumbing.rs:71
      rustc_middle::ty::context::tls::with_related_context::{{closure}}
             at /home/r/src/rust/rustc/src/librustc_middle/ty/context.rs:1786
      rustc_middle::ty::context::tls::with_context::{{closure}}
             at /home/r/src/rust/rustc/src/librustc_middle/ty/context.rs:1770
      rustc_middle::ty::context::tls::with_context_opt
             at /home/r/src/rust/rustc/src/librustc_middle/ty/context.rs:1759
      rustc_middle::ty::context::tls::with_context
             at /home/r/src/rust/rustc/src/librustc_middle/ty/context.rs:1770
      rustc_middle::ty::context::tls::with_related_context
             at /home/r/src/rust/rustc/src/librustc_middle/ty/context.rs:1783
      rustc_middle::ty::query::plumbing::<impl rustc_query_system::query::QueryContext for rustc_middle::ty::context::TyCtxt>::start_query
             at /home/r/src/rust/rustc/src/librustc_middle/ty/query/plumbing.rs:60
      rustc_query_system::query::plumbing::force_query_with_job::{{closure}}
             at /home/r/src/rust/rustc/src/librustc_query_system/query/plumbing.rs:583
      rustc_query_system::query::plumbing::with_diagnostics
             at /home/r/src/rust/rustc/src/librustc_query_system/query/plumbing.rs:293
      rustc_query_system::query::plumbing::force_query_with_job
             at /home/r/src/rust/rustc/src/librustc_query_system/query/plumbing.rs:582
      rustc_query_system::query::plumbing::try_execute_query
             at /home/r/src/rust/rustc/src/librustc_query_system/query/plumbing.rs:410
      rustc_query_system::query::plumbing::get_query::{{closure}}
             at /home/r/src/rust/rustc/src/librustc_query_system/query/plumbing.rs:627
      <rustc_query_system::query::caches::DefaultCache<K,V> as rustc_query_system::query::caches::QueryCache>::lookup
             at /home/r/src/rust/rustc/src/librustc_query_system/query/caches.rs:91
      rustc_query_system::query::plumbing::try_get_cached
             at /home/r/src/rust/rustc/src/librustc_query_system/query/plumbing.rs:368
      rustc_query_system::query::plumbing::get_query
             at /home/r/src/rust/rustc/src/librustc_query_system/query/plumbing.rs:619
   7: rustc_middle::ty::query::TyCtxtAt::const_eval_validated
             at /home/r/src/rust/rustc/src/librustc_middle/ty/query/plumbing.rs:467
      rustc_middle::ty::query::<impl rustc_middle::ty::context::TyCtxt>::const_eval_validated
             at /home/r/src/rust/rustc/src/librustc_middle/ty/query/plumbing.rs:430
      rustc_mir::const_eval::eval_queries::const_eval_validated_provider
             at src/librustc_mir/const_eval/eval_queries.rs:234
   8: rustc_middle::ty::query::<impl rustc_query_system::query::config::QueryAccessors<rustc_middle::ty::context::TyCtxt> for rustc_middle::ty::query::queries::const_eval_validated>::compute
             at src/librustc_middle/ty/query/plumbing.rs:362
   9: rustc_query_system::dep_graph::graph::DepGraph<K>::with_task_impl
             at /home/r/src/rust/rustc/src/librustc_query_system/dep_graph/graph.rs:303
      rustc_query_system::dep_graph::graph::DepGraph<K>::with_task
             at /home/r/src/rust/rustc/src/librustc_query_system/dep_graph/graph.rs:200
  10: rustc_query_system::query::plumbing::force_query_with_job::{{closure}}::{{closure}}
             at /home/r/src/rust/rustc/src/librustc_query_system/query/plumbing.rs:593
      rustc_middle::ty::query::plumbing::<impl rustc_query_system::query::QueryContext for rustc_middle::ty::context::TyCtxt>::start_query::{{closure}}::{{closure}}
             at src/librustc_middle/ty/query/plumbing.rs:71
      rustc_middle::ty::context::tls::enter_context::{{closure}}
             at src/librustc_middle/ty/context.rs:1698
      rustc_middle::ty::context::tls::set_tlv
             at src/librustc_middle/ty/context.rs:1682
      rustc_middle::ty::context::tls::enter_context
             at src/librustc_middle/ty/context.rs:1698
      rustc_middle::ty::query::plumbing::<impl rustc_query_system::query::QueryContext for rustc_middle::ty::context::TyCtxt>::start_query::{{closure}}
             at src/librustc_middle/ty/query/plumbing.rs:71
      rustc_middle::ty::context::tls::with_related_context::{{closure}}
             at src/librustc_middle/ty/context.rs:1786
      rustc_middle::ty::context::tls::with_context::{{closure}}
             at src/librustc_middle/ty/context.rs:1770
      rustc_middle::ty::context::tls::with_context_opt
             at src/librustc_middle/ty/context.rs:1759
      rustc_middle::ty::context::tls::with_context
             at src/librustc_middle/ty/context.rs:1770
      rustc_middle::ty::context::tls::with_related_context
             at src/librustc_middle/ty/context.rs:1783
      rustc_middle::ty::query::plumbing::<impl rustc_query_system::query::QueryContext for rustc_middle::ty::context::TyCtxt>::start_query
             at src/librustc_middle/ty/query/plumbing.rs:60
      rustc_query_system::query::plumbing::force_query_with_job::{{closure}}
             at /home/r/src/rust/rustc/src/librustc_query_system/query/plumbing.rs:583
      rustc_query_system::query::plumbing::with_diagnostics
             at /home/r/src/rust/rustc/src/librustc_query_system/query/plumbing.rs:293
      rustc_query_system::query::plumbing::force_query_with_job
             at /home/r/src/rust/rustc/src/librustc_query_system/query/plumbing.rs:582
      rustc_query_system::query::plumbing::try_execute_query
             at /home/r/src/rust/rustc/src/librustc_query_system/query/plumbing.rs:410
      rustc_query_system::query::plumbing::get_query::{{closure}}
             at /home/r/src/rust/rustc/src/librustc_query_system/query/plumbing.rs:627
      <rustc_query_system::query::caches::DefaultCache<K,V> as rustc_query_system::query::caches::QueryCache>::lookup
             at /home/r/src/rust/rustc/src/librustc_query_system/query/caches.rs:91
      rustc_query_system::query::plumbing::try_get_cached
             at /home/r/src/rust/rustc/src/librustc_query_system/query/plumbing.rs:368
      rustc_query_system::query::plumbing::get_query
             at /home/r/src/rust/rustc/src/librustc_query_system/query/plumbing.rs:619
  11: rustc_middle::mir::interpret::queries::<impl rustc_middle::ty::context::TyCtxt>::const_eval_global_id
             at src/librustc_middle/mir/interpret/queries.rs:0
      rustc_middle::mir::interpret::queries::<impl rustc_middle::ty::context::TyCtxt>::const_eval_resolve
             at src/librustc_middle/mir/interpret/queries.rs:45
  12: rustc_middle::ty::sty::Const::eval
             at /home/r/src/rust/rustc/src/librustc_middle/ty/sty.rs:2366
      <rustc_trait_selection::traits::query::normalize::QueryNormalizer as rustc_middle::ty::fold::TypeFolder>::fold_const
             at src/librustc_trait_selection/traits/query/normalize.rs:206
  13: rustc_middle::ty::structural_impls::<impl rustc_middle::ty::fold::TypeFoldable for &rustc_middle::ty::sty::Const>::fold_with
             at /home/r/src/rust/rustc/src/librustc_middle/ty/structural_impls.rs:1005
      <rustc_middle::ty::subst::GenericArg as rustc_middle::ty::fold::TypeFoldable>::super_fold_with
             at /home/r/src/rust/rustc/src/librustc_middle/ty/subst.rs:158
      rustc_middle::ty::fold::TypeFoldable::fold_with
             at /home/r/src/rust/rustc/src/librustc_middle/ty/fold.rs:49
  14: <rustc_infer::infer::at::At as rustc_trait_selection::traits::query::normalize::AtExt>::normalize
             at /home/r/src/rust/rustc/src/librustc_trait_selection/traits/query/normalize.rs:62
  15: rustc_traits::normalize_erasing_regions::normalize_generic_arg_after_erasing_regions::{{closure}}
             at src/librustc_traits/normalize_erasing_regions.rs:24
      rustc_infer::infer::InferCtxtBuilder::enter::{{closure}}
             at /home/r/src/rust/rustc/src/librustc_infer/infer/mod.rs:595
      rustc_middle::ty::context::GlobalCtxt::enter_local::{{closure}}::{{closure}}
             at /home/r/src/rust/rustc/src/librustc_middle/ty/context.rs:1530
      rustc_middle::ty::context::tls::enter_context::{{closure}}
             at /home/r/src/rust/rustc/src/librustc_middle/ty/context.rs:1698
      rustc_middle::ty::context::tls::set_tlv
             at /home/r/src/rust/rustc/src/librustc_middle/ty/context.rs:1682
      rustc_middle::ty::context::tls::enter_context
             at /home/r/src/rust/rustc/src/librustc_middle/ty/context.rs:1698
      rustc_middle::ty::context::GlobalCtxt::enter_local::{{closure}}
             at /home/r/src/rust/rustc/src/librustc_middle/ty/context.rs:1530
      rustc_middle::ty::context::tls::with_related_context::{{closure}}
             at /home/r/src/rust/rustc/src/librustc_middle/ty/context.rs:1786
      rustc_middle::ty::context::tls::with_context::{{closure}}
             at /home/r/src/rust/rustc/src/librustc_middle/ty/context.rs:1770
      rustc_middle::ty::context::tls::with_context_opt
             at /home/r/src/rust/rustc/src/librustc_middle/ty/context.rs:1759
      rustc_middle::ty::context::tls::with_context
             at /home/r/src/rust/rustc/src/librustc_middle/ty/context.rs:1770
      rustc_middle::ty::context::tls::with_related_context
             at /home/r/src/rust/rustc/src/librustc_middle/ty/context.rs:1783
      rustc_middle::ty::context::GlobalCtxt::enter_local
             at /home/r/src/rust/rustc/src/librustc_middle/ty/context.rs:1522
  16: rustc_infer::infer::InferCtxtBuilder::enter
             at /home/r/src/rust/rustc/src/librustc_infer/infer/mod.rs:594
  17: rustc_traits::normalize_erasing_regions::normalize_generic_arg_after_erasing_regions
             at src/librustc_traits/normalize_erasing_regions.rs:22
  18: rustc_middle::ty::query::<impl rustc_query_system::query::config::QueryAccessors<rustc_middle::ty::context::TyCtxt> for rustc_middle::ty::query::queries::normalize_generic_arg_after_erasing_regions>::compute
             at src/librustc_middle/ty/query/plumbing.rs:362
  19: rustc_query_system::dep_graph::graph::DepGraph<K>::with_task_impl
             at /home/r/src/rust/rustc/src/librustc_query_system/dep_graph/graph.rs:303
      rustc_query_system::dep_graph::graph::DepGraph<K>::with_task
             at /home/r/src/rust/rustc/src/librustc_query_system/dep_graph/graph.rs:200
  20: rustc_query_system::query::plumbing::force_query_with_job::{{closure}}::{{closure}}
             at /home/r/src/rust/rustc/src/librustc_query_system/query/plumbing.rs:593
      rustc_middle::ty::query::plumbing::<impl rustc_query_system::query::QueryContext for rustc_middle::ty::context::TyCtxt>::start_query::{{closure}}::{{closure}}
             at src/librustc_middle/ty/query/plumbing.rs:71
      rustc_middle::ty::context::tls::enter_context::{{closure}}
             at src/librustc_middle/ty/context.rs:1698
      rustc_middle::ty::context::tls::set_tlv
             at src/librustc_middle/ty/context.rs:1682
      rustc_middle::ty::context::tls::enter_context
             at src/librustc_middle/ty/context.rs:1698
      rustc_middle::ty::query::plumbing::<impl rustc_query_system::query::QueryContext for rustc_middle::ty::context::TyCtxt>::start_query::{{closure}}
             at src/librustc_middle/ty/query/plumbing.rs:71
      rustc_middle::ty::context::tls::with_related_context::{{closure}}
             at src/librustc_middle/ty/context.rs:1786
      rustc_middle::ty::context::tls::with_context::{{closure}}
             at src/librustc_middle/ty/context.rs:1770
      rustc_middle::ty::context::tls::with_context_opt
             at src/librustc_middle/ty/context.rs:1759
      rustc_middle::ty::context::tls::with_context
             at src/librustc_middle/ty/context.rs:1770
      rustc_middle::ty::context::tls::with_related_context
             at src/librustc_middle/ty/context.rs:1783
      rustc_middle::ty::query::plumbing::<impl rustc_query_system::query::QueryContext for rustc_middle::ty::context::TyCtxt>::start_query
             at src/librustc_middle/ty/query/plumbing.rs:60
      rustc_query_system::query::plumbing::force_query_with_job::{{closure}}
             at /home/r/src/rust/rustc/src/librustc_query_system/query/plumbing.rs:583
      rustc_query_system::query::plumbing::with_diagnostics
             at /home/r/src/rust/rustc/src/librustc_query_system/query/plumbing.rs:293
      rustc_query_system::query::plumbing::force_query_with_job
             at /home/r/src/rust/rustc/src/librustc_query_system/query/plumbing.rs:582
      rustc_query_system::query::plumbing::try_execute_query
             at /home/r/src/rust/rustc/src/librustc_query_system/query/plumbing.rs:410
      rustc_query_system::query::plumbing::get_query::{{closure}}
             at /home/r/src/rust/rustc/src/librustc_query_system/query/plumbing.rs:627
      <rustc_query_system::query::caches::DefaultCache<K,V> as rustc_query_system::query::caches::QueryCache>::lookup
             at /home/r/src/rust/rustc/src/librustc_query_system/query/caches.rs:91
      rustc_query_system::query::plumbing::try_get_cached
             at /home/r/src/rust/rustc/src/librustc_query_system/query/plumbing.rs:368
      rustc_query_system::query::plumbing::get_query
             at /home/r/src/rust/rustc/src/librustc_query_system/query/plumbing.rs:619
  21: rustc_middle::ty::query::TyCtxtAt::normalize_generic_arg_after_erasing_regions
             at src/librustc_middle/ty/query/plumbing.rs:467
      rustc_middle::ty::query::<impl rustc_middle::ty::context::TyCtxt>::normalize_generic_arg_after_erasing_regions
             at src/librustc_middle/ty/query/plumbing.rs:430
      <rustc_middle::ty::normalize_erasing_regions::NormalizeAfterErasingRegionsFolder as rustc_middle::ty::fold::TypeFolder>::fold_const
             at src/librustc_middle/ty/normalize_erasing_regions.rs:103
  22: rustc_middle::ty::structural_impls::<impl rustc_middle::ty::fold::TypeFoldable for &rustc_middle::ty::sty::Const>::fold_with
             at /home/r/src/rust/rustc/src/librustc_middle/ty/structural_impls.rs:1005
      rustc_middle::ty::normalize_erasing_regions::<impl rustc_middle::ty::context::TyCtxt>::normalize_erasing_regions
             at /home/r/src/rust/rustc/src/librustc_middle/ty/normalize_erasing_regions.rs:37
  23: rustc_middle::ty::normalize_erasing_regions::<impl rustc_middle::ty::context::TyCtxt>::subst_and_normalize_erasing_regions
             at /home/r/src/rust/rustc/src/librustc_middle/ty/normalize_erasing_regions.rs:82
  24: rustc_mir::interpret::eval_context::InterpCx<M>::subst_from_frame_and_normalize_erasing_regions
             at src/librustc_mir/interpret/eval_context.rs:442
      rustc_mir::interpret::eval_context::InterpCx<M>::subst_from_current_frame_and_normalize_erasing_regions
             at src/librustc_mir/interpret/eval_context.rs:431
      rustc_mir::interpret::operand::<impl rustc_mir::interpret::eval_context::InterpCx<M>>::eval_operand
             at src/librustc_mir/interpret/operand.rs:489
  25: rustc_mir::transform::const_prop::ConstPropagator::check_binary_op::{{closure}}
             at src/librustc_mir/transform/const_prop.rs:534
      rustc_mir::transform::const_prop::ConstPropagator::use_ecx
             at src/librustc_mir/transform/const_prop.rs:417
  26: rustc_mir::transform::const_prop::ConstPropagator::check_binary_op
             at src/librustc_mir/transform/const_prop.rs:534
  27: rustc_mir::transform::const_prop::ConstPropagator::const_prop
             at src/librustc_mir/transform/const_prop.rs:0
      <rustc_mir::transform::const_prop::ConstPropagator as rustc_middle::mir::visit::MutVisitor>::visit_statement
             at src/librustc_mir/transform/const_prop.rs:836
  28: rustc_middle::mir::visit::MutVisitor::super_basic_block_data
             at /home/r/src/rust/rustc/src/librustc_middle/mir/visit.rs:322
      rustc_middle::mir::visit::MutVisitor::visit_basic_block_data
             at /home/r/src/rust/rustc/src/librustc_middle/mir/visit.rs:93
      rustc_middle::mir::visit::MutVisitor::super_body
             at /home/r/src/rust/rustc/src/librustc_middle/mir/visit.rs:275
      rustc_middle::mir::visit::MutVisitor::visit_body
             at /home/r/src/rust/rustc/src/librustc_middle/mir/visit.rs:87
  29: <rustc_mir::transform::const_prop::ConstProp as rustc_mir::transform::MirPass>::run_pass
             at src/librustc_mir/transform/const_prop.rs:155
  30: rustc_mir::transform::run_passes::{{closure}}
             at src/librustc_mir/transform/mod.rs:165
      rustc_mir::transform::run_passes
             at src/librustc_mir/transform/mod.rs:172
  31: rustc_mir::transform::run_optimization_passes
             at src/librustc_mir/transform/mod.rs:270
  32: rustc_mir::transform::optimized_mir
             at src/librustc_mir/transform/mod.rs:337

@RalfJung
Copy link
Member

So it is probably this call that is failing:

self.use_ecx(|this| this.ecx.read_immediate(this.ecx.eval_operand(right, None)?))?;

@LeSeulArtichaut
Copy link
Contributor

If it regressed in 7f3df57, I guess the only PR that could have caused this is #71141?

Oops, I meant #70566. I can't even copy-paste correcly 😄

@RalfJung
Copy link
Member

But then it gets weird. We end up here:

self.subst_from_current_frame_and_normalize_erasing_regions(constant.literal);

and then here

self.tcx.normalize_erasing_regions(self.param_env, value)

And then somehow we end up evaluating a const (?!?) even though we just wanted to subst on a Const (not eval, that would be the next thing eval_operand does). And that evaluation goes very wrong as the const is somehow not initialized.

@wesleywiser wesleywiser added P-high High priority and removed I-prioritize Issue: Indicates that prioritization has been requested for this issue. labels Apr 20, 2020
@RalfJung
Copy link
Member

I can see it evaluating <*mut T as Nullable>::NULL. That is quite strange because we don't actually know T, so this really cannot be evaluated... but somehow we do not have sanity checks that catch this?

@jumbatm
Copy link
Contributor

jumbatm commented Apr 20, 2020

We already have a very similar test for Nullable. It's curious that it didn't catch this.

// check-pass
pub trait Nullable {
const NULL: Self;
fn is_null(&self) -> bool;
}
impl<T> Nullable for *const T {
const NULL: Self = core::ptr::null::<T>();
fn is_null(&self) -> bool {
*self == Self::NULL
}
}
fn main() {
}

Ah, changing the test case to // build-pass and adding #![crate_type = "lib"] reproduces the error.

@RalfJung
Copy link
Member

RalfJung commented Apr 21, 2020

Ah, good catch! Probably it was a mistake to not add #![crate_type = "lib]" there in the first place, because built as a binary these impl are just dead code.

The test was added in #51852.

jumbatm added a commit to jumbatm/rust that referenced this issue Apr 21, 2020
@jumbatm
Copy link
Contributor

jumbatm commented Apr 21, 2020

@rustbot claim

@rustbot rustbot self-assigned this Apr 21, 2020
@RalfJung
Copy link
Member

Namely, the proposed solution is to:

  • Equip try_validation! with a pattern of errors to catch, the rest is forwarded. (Figuring out all the right patterns will take a few runs of the test suite here.)
  • Forward InvalidProgram errors out of validation instead of ICEing.

bors added a commit to rust-lang-ci/rust that referenced this issue Apr 25, 2020
…=Mark-Simulacrum

[beta] fix failing const validation

This is the **beta branch fix** for rust-lang#71353, by reverting rust-lang#70566.

r? @oli-obk
Not sure if there is any extra process for the beta part. This is not a backport; we intend to "properly" fix this on master but for beta a revert is faster and less risky.
@RalfJung
Copy link
Member

The beta PR landed, master PR by @pnkfelix is on the way.

@RalfJung
Copy link
Member

This bug is now fixed, so I will remove all the critical label. But let's keep this open to track the issue of validation swallowing TooGeneric errors.

@RalfJung RalfJung added C-cleanup Category: PRs that clean code up or issues documenting cleanup. and removed E-needs-bisection Call for participation: This issue needs bisection: https://github.com/rust-lang/cargo-bisect-rustc ICEBreaker-Cleanup-Crew Helping to "clean up" bugs with minimal examples and bisections P-high High priority regression-from-stable-to-nightly Performance or correctness regression from stable to nightly. labels Apr 25, 2020
@RalfJung RalfJung changed the title Type validation fails when comparing with a null pointer Type validation mistreats layout errors Apr 25, 2020
@pnkfelix
Copy link
Member

The reversion on master landed on PR #71533 .

Still need to assign a priority to the remaining issue of validation swallowing TooGeneric errors, so ...

@rustbot prioritize

@rustbot rustbot added the I-prioritize Issue: Indicates that prioritization has been requested for this issue. label Apr 27, 2020
@spastorino
Copy link
Member

Assigning P-medium as discussed as part of the Prioritization Working Group process and removing I-prioritize.

@spastorino spastorino added P-medium Medium priority and removed I-prioritize Issue: Indicates that prioritization has been requested for this issue. labels Apr 27, 2020
@bors bors closed this as completed in 5b17290 May 3, 2020
@LeSeulArtichaut
Copy link
Contributor

@Mark-Simulacrum As this problem raised in the Crater run, should #71663 be nominated to be backported to beta?

@Mark-Simulacrum
Copy link
Member

My understanding is that #71441 was the intended fix for beta and we expect #71663 to go with the trains, i.e. there is no need for a backport. But if I'm wrong, we should indeed nominate it.

@LeSeulArtichaut
Copy link
Contributor

Oh right, I re-read #71353 (comment)

@RalfJung
Copy link
Member

RalfJung commented May 3, 2020

Indeed, the beta fix was to revert the original incorrect PR. This PR that just landed now just fixed #69021, which doesn't need backporting.

However, I am going to re-open this issue because validation still swallows layout errors in many cases -- just this one particular case got fixed.

@RalfJung RalfJung reopened this May 3, 2020
@RalfJung RalfJung removed C-bug Category: This is a bug. P-medium Medium priority labels May 3, 2020
@bors bors closed this as completed in 066eb08 May 7, 2020
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
A-const-eval Area: Constant evaluation, covers all const contexts (static, const fn, ...) C-cleanup Category: PRs that clean code up or issues documenting cleanup. T-compiler Relevant to the compiler team, which will review and decide on the PR/issue.
Projects
None yet