Skip to content

Add rustc_index::StableIdx - #162731

Open
susitsm wants to merge 1 commit into
rust-lang:mainfrom
susitsm:stable-idx
Open

susitsm wants to merge 1 commit into
rust-lang:mainfrom
susitsm:stable-idx

Conversation

@susitsm

@susitsm susitsm commented Sep 13, 2026 •

Copy link
Copy Markdown
Contributor

StableIdx is for Idx types where iteration is stable between runs. Allows usage of iterator functions for IndexVec and IndexSlice. Otherwise only the unstable_* variants of these functions is available

This is related to #162202 and #162203 and #90317

`StableIdx` is for index types where iteration is stable between runs.
Allows usage of iterator functions for `IndexVec` and `IndexSlice`.
Otherwise only the `unstable_*` variants of these functions is available
@rustbot

rustbot commented Sep 13, 2026

Copy link
Copy Markdown
Collaborator

Some changes occurred in coverage instrumentation.

cc @Zalathar

Some changes occurred to MIR optimizations

cc @rust-lang/wg-mir-opt

Some changes occurred in exhaustiveness checking

cc @Nadrieril

@rustbot rustbot added S-waiting-on-review Status: Awaiting review from the assignee but also interested parties. T-compiler Relevant to the compiler team, which will review and decide on the PR/issue. labels Sep 13, 2026
@rustbot

rustbot commented Sep 13, 2026

Copy link
Copy Markdown
Collaborator

r? @hanna-kruppe

rustbot has assigned @hanna-kruppe.
They will have a look at your PR within the next two weeks and either review your PR or reassign to another reviewer.

Use r? to explicitly pick a reviewer

Why was this reviewer chosen?

The reviewer was selected based on:

  • Owners of files modified in this PR: compiler
  • compiler expanded to 76 candidates
  • Random selection from 18 candidates

@rust-log-analyzer

Copy link
Copy Markdown
Collaborator

The job test-pr-check-2 failed! Check out the build log: (web) (plain enhanced) (plain)

Click to see the possible cause of the failure (guessed by this bot)
    Checking ui_test v0.30.7
[RUSTC-TIMING] ui_test test:false 0.622
[RUSTC-TIMING] chrono_tz test:false 3.373
    Checking miri v0.1.0 (/checkout/src/tools/miri)
error[E0599]: the method `iter_enumerated` exists for struct `rustc_index::IndexVec<concurrency::thread::ThreadId, concurrency::thread::Thread<'tcx>>`, but its trait bounds were not satisfied
   --> src/tools/miri/src/concurrency/thread.rs:494:22
    |
 47 | pub struct ThreadId(u32);
    | ------------------- doesn't satisfy `concurrency::thread::ThreadId: StableIdx`
...
---
            `concurrency::thread::ThreadId: StableIdx`
note: the trait `StableIdx` must be implemented
   --> compiler/rustc_index/src/idx.rs:35:1
    |
 35 | pub trait StableIdx: Idx {}
    | ^^^^^^^^^^^^^^^^^^^^^^^^

error[E0599]: the method `iter_enumerated` exists for struct `rustc_index::IndexVec<concurrency::thread::ThreadId, concurrency::thread::Thread<'tcx>>`, but its trait bounds were not satisfied
   --> src/tools/miri/src/concurrency/thread.rs:501:14
    |
 47 |   pub struct ThreadId(u32);
    |   ------------------- doesn't satisfy `concurrency::thread::ThreadId: StableIdx`
...
---
            `concurrency::thread::ThreadId: StableIdx`
note: the trait `StableIdx` must be implemented
   --> compiler/rustc_index/src/idx.rs:35:1
    |
 35 | pub trait StableIdx: Idx {}
    | ^^^^^^^^^^^^^^^^^^^^^^^^

error[E0599]: the method `iter_enumerated` exists for struct `std::cell::Ref<'_, rustc_index::IndexVec<VectorIdx, ThreadClockSet>>`, but its trait bounds were not satisfied
    --> src/tools/miri/src/concurrency/data_race.rs:1689:30
     |
1689 |             if vector_clocks.iter_enumerated().all(|(clock_idx, clock)| {
     |                              ^^^^^^^^^^^^^^^
     |
    ::: src/tools/miri/src/concurrency/vector_clock.rs:16:1
     |
  16 | pub(super) struct VectorIdx(u32);
     | --------------------------- doesn't satisfy `VectorIdx: StableIdx`
     |
     = note: the following trait bounds were not satisfied:
             `VectorIdx: StableIdx`
note: the trait `StableIdx` must be implemented
    --> compiler/rustc_index/src/idx.rs:35:1
     |
  35 | pub trait StableIdx: Idx {}
     | ^^^^^^^^^^^^^^^^^^^^^^^^

error[E0599]: the method `iter_enumerated` exists for mutable reference `&mut rustc_index::IndexVec<VectorIdx, ThreadClockSet>`, but its trait bounds were not satisfied
    --> src/tools/miri/src/concurrency/data_race.rs:1808:22
     |
1807 |                   if vector_clocks
     |  ____________________-
1808 | |                     .iter_enumerated()
     | |_____________________-^^^^^^^^^^^^^^^
     |
    ::: src/tools/miri/src/concurrency/vector_clock.rs:16:1
     |
  16 |   pub(super) struct VectorIdx(u32);
     |   --------------------------- doesn't satisfy `VectorIdx: StableIdx`
     |
     = note: the following trait bounds were not satisfied:
             `VectorIdx: StableIdx`
note: the trait `StableIdx` must be implemented
    --> compiler/rustc_index/src/idx.rs:35:1
     |
  35 | pub trait StableIdx: Idx {}
     | ^^^^^^^^^^^^^^^^^^^^^^^^

error[E0277]: `&rustc_index::IndexVec<concurrency::thread::ThreadId, concurrency::thread::Thread<'_>>` is not an iterator
   --> src/tools/miri/src/concurrency/thread.rs:413:23
    |
413 |         for thread in threads {
    |                       ^^^^^^^ `&rustc_index::IndexVec<concurrency::thread::ThreadId, concurrency::thread::Thread<'_>>` is not an iterator
    |
    = help: the trait `IntoIterator` is not implemented for `&rustc_index::IndexVec<concurrency::thread::ThreadId, concurrency::thread::Thread<'_>>`
help: the following other types implement trait `IntoIterator`
   --> compiler/rustc_index/src/vec.rs:353:1
    |
353 | impl<I: StableIdx, T> IntoIterator for IndexVec<I, T> {
    | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ `rustc_index::IndexVec<I, T>`
...
363 | impl<'a, I: StableIdx, T> IntoIterator for &'a IndexVec<I, T> {
    | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ `&rustc_index::IndexVec<I, T>`
...
373 | impl<'a, I: StableIdx, T> IntoIterator for &'a mut IndexVec<I, T> {
    | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ `&mut rustc_index::IndexVec<I, T>`

error[E0599]: the method `iter` exists for struct `rustc_index::IndexVec<concurrency::thread::ThreadId, concurrency::thread::Thread<'tcx>>`, but its trait bounds were not satisfied
   --> src/tools/miri/src/concurrency/thread.rs:537:22
    |
 47 | pub struct ThreadId(u32);
    | ------------------- doesn't satisfy `concurrency::thread::ThreadId: StableIdx`
...
537 |         self.threads.iter().filter(|t| !t.state.is_terminated()).count()
    |                      ^^^^ method cannot be called due to unsatisfied trait bounds
    |
    = note: the following trait bounds were not satisfied:
            `concurrency::thread::ThreadId: StableIdx`
note: the trait `StableIdx` must be implemented
   --> compiler/rustc_index/src/idx.rs:35:1
    |
 35 | pub trait StableIdx: Idx {}
    | ^^^^^^^^^^^^^^^^^^^^^^^^

error[E0599]: the method `iter` exists for struct `rustc_index::IndexVec<concurrency::thread::ThreadId, concurrency::thread::Thread<'tcx>>`, but its trait bounds were not satisfied
   --> src/tools/miri/src/concurrency/thread.rs:547:22
    |
 47 | pub struct ThreadId(u32);
    | ------------------- doesn't satisfy `concurrency::thread::ThreadId: StableIdx`
...
547 |         self.threads.iter().all(|thread| thread.state.is_terminated())
    |                      ^^^^ method cannot be called due to unsatisfied trait bounds
    |
    = note: the following trait bounds were not satisfied:
            `concurrency::thread::ThreadId: StableIdx`
note: the trait `StableIdx` must be implemented
   --> compiler/rustc_index/src/idx.rs:35:1
    |
 35 | pub trait StableIdx: Idx {}
    | ^^^^^^^^^^^^^^^^^^^^^^^^

error[E0599]: the method `iter_enumerated` exists for reference `&rustc_index::IndexVec<concurrency::thread::ThreadId, concurrency::thread::Thread<'tcx>>`, but its trait bounds were not satisfied
   --> src/tools/miri/src/concurrency/thread.rs:808:14
    |
 47 |   pub struct ThreadId(u32);
    |   ------------------- doesn't satisfy `concurrency::thread::ThreadId: StableIdx`
...
---
            `concurrency::thread::ThreadId: StableIdx`
note: the trait `StableIdx` must be implemented
   --> compiler/rustc_index/src/idx.rs:35:1
    |
 35 | pub trait StableIdx: Idx {}
    | ^^^^^^^^^^^^^^^^^^^^^^^^

error[E0599]: the method `iter_enumerated_mut` exists for struct `rustc_index::IndexVec<concurrency::thread::ThreadId, concurrency::thread::Thread<'tcx>>`, but its trait bounds were not satisfied
   --> src/tools/miri/src/concurrency/thread.rs:872:58
    |
 47 | pub struct ThreadId(u32);
    | ------------------- doesn't satisfy `concurrency::thread::ThreadId: StableIdx`
...
---
            `concurrency::thread::ThreadId: StableIdx`
note: the trait `StableIdx` must be implemented
   --> compiler/rustc_index/src/idx.rs:35:1
    |
 35 | pub trait StableIdx: Idx {}
    | ^^^^^^^^^^^^^^^^^^^^^^^^

error[E0599]: the method `iter` exists for reference `&rustc_index::IndexVec<concurrency::thread::ThreadId, concurrency::thread::Thread<'tcx>>`, but its trait bounds were not satisfied
    --> src/tools/miri/src/concurrency/thread.rs:1021:18
     |
  47 |   pub struct ThreadId(u32);
     |   ------------------- doesn't satisfy `concurrency::thread::ThreadId: StableIdx`
...
---
             `concurrency::thread::ThreadId: StableIdx`
note: the trait `StableIdx` must be implemented
    --> compiler/rustc_index/src/idx.rs:35:1
     |
  35 | pub trait StableIdx: Idx {}
     | ^^^^^^^^^^^^^^^^^^^^^^^^

Some errors have detailed explanations: E0277, E0599.
For more information about an error, try `rustc --explain E0277`.
[RUSTC-TIMING] miri test:false 4.897

@hanna-kruppe

Copy link
Copy Markdown
Contributor

@Zalathar

Zalathar commented Sep 13, 2026 •

Copy link
Copy Markdown
Member

I don't feel good about this approach, as it:

  • Effectively forces every other Idx type to make false claims about being “stable” as a euphemism for not-LocalDefId
  • Pushes a big chunk of complexity and confusion onto every other usage of a pretty simple and fundamental data type

@susitsm

susitsm commented Sep 14, 2026

Copy link
Copy Markdown
Contributor Author

I understand where you are coming from. Maybe a better solution could be to simply remove Idx from LocalDefId? Other similar indices, like LocalExpndId and SyntaxContext do not implement it. However the query system heavily relies on it (which might be a bad thing, since it can use a relatively large amount of memory for sparse maps, I have seen this in the metadata).

It is also possible to simply gate iteration behind I: Ord, which is similar to this, but there is no single place to document why that is needed. Any other ideas?

@susitsm

susitsm commented Sep 14, 2026

Copy link
Copy Markdown
Contributor Author
* Pushes a big chunk of complexity and confusion onto every other usage of a pretty simple and fundamental data type

This might be a good thing? Like it or not, stable iteration IS something you should think about when creating a new index type, when using maps. Not doing so results in bugs. So as fundamental as IndexVec is, it might be more generic than it should be. It is used both as a vec and a map. For FxHashMap/FxHashSet, iterating over them results in warnings by the compiler. However, adding such warnings to each place where IndexVec iteration is used might be overkill. Adding some kind of UnordIndexVec (or UnordDenseMap could be a better name) counterpart could also help with this

@hanna-kruppe

Copy link
Copy Markdown
Contributor

@rustbot reroll

@rustbot rustbot assigned Walnut356 and unassigned hanna-kruppe Sep 18, 2026
@Zalathar

Copy link
Copy Markdown
Member

I think the more promising approach is to try to make LocalDefId not implement Idx.

That will probably be more intrusive to code currently relying on the impl, but less intrusive to all the other code relying on integration between newtype_idx!, Idx, IndexVec, and IndexSlice.

@Walnut356

Walnut356 commented Sep 19, 2026 •

Copy link
Copy Markdown
Contributor

I'm finishing up GSoC this weekend, so it's probably better if someone else looks into this

@rustbot release-assignment

This branch has not been deployed

No deployments
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

S-waiting-on-review Status: Awaiting review from the assignee but also interested parties. T-compiler Relevant to the compiler team, which will review and decide on the PR/issue.

Projects

None yet

Development

Successfully merging this pull request may close these issues.

6 participants