Skip to content
Closed
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
10 changes: 9 additions & 1 deletion compiler/rustc_trait_selection/src/solve/fulfill.rs
Original file line number Diff line number Diff line change
Expand Up @@ -209,7 +209,15 @@ where
let mut errors = Vec::new();
loop {
let mut any_changed = false;
for (mut obligation, stalled_on) in mem::take(&mut self.obligations.pending) {

// This loop empties and reconstructs `self.obligations.pending`, which can have many
// items (thousands in extreme cases) and very often the new length is the same as the
// old. Reserving capacity up front avoids repeated reallocations during the
// reconstruction.
let pending = mem::take(&mut self.obligations.pending);
self.obligations.pending.reserve(pending.capacity());

for (mut obligation, stalled_on) in pending {

@lcnr lcnr Aug 3, 2026

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

could we rewrite this as a retain instead? i think that's what waffle's PR #158126 does?

View changes since the review

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

actually no, @WaffleLapkin's PR only does this in the trait solver internal loop, which I think is significantly less hot?

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Something like that. That's the "other possible changes" I mentioned in the PR description.

let goal = obligation.as_goal();
let delegate = <&SolverDelegate<'tcx>>::from(infcx);

Expand Down
Loading