Skip to content

Commit 00e6c10

Browse files
committed
ZJIT: Standardize to Iterator::map in Invariants::update_references
The old code was doing a manual HashSet/HashMap rebuild, and there isn't a clear performance advantage over `Iterator::map`. So let's use `map` since it looks clearer and it's easier to see that everything was indeed updated. This also adds assertions the old code did not have by way of as_iseq() and as_cme().
1 parent 1a52c42 commit 00e6c10

File tree

1 file changed

+14
-29
lines changed

1 file changed

+14
-29
lines changed

zjit/src/invariants.rs

Lines changed: 14 additions & 29 deletions
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,7 @@
22
33
use std::{collections::{HashMap, HashSet}, mem};
44

5-
use crate::{backend::lir::{asm_comment, Assembler}, cruby::{iseq_name, rb_callable_method_entry_t, rb_gc_location, ruby_basic_operators, src_loc, with_vm_lock, IseqPtr, RedefinitionFlag, ID, VALUE}, gc::IseqPayload, hir::Invariant, options::debug, state::{zjit_enabled_p, ZJITState}, virtualmem::CodePtr};
5+
use crate::{backend::lir::{asm_comment, Assembler}, cruby::{iseq_name, rb_callable_method_entry_t, rb_gc_location, ruby_basic_operators, src_loc, with_vm_lock, IseqPtr, RedefinitionFlag, ID}, gc::IseqPayload, hir::Invariant, options::debug, state::{zjit_enabled_p, ZJITState}, virtualmem::CodePtr};
66
use crate::stats::with_time_stat;
77
use crate::stats::Counter::invalidation_time_ns;
88
use crate::gc::remove_gc_offsets;
@@ -70,38 +70,23 @@ impl Invariants {
7070

7171
/// Update ISEQ references in Invariants::ep_escape_iseqs
7272
fn update_ep_escape_iseqs(&mut self) {
73-
let mut moved: Vec<IseqPtr> = Vec::with_capacity(self.ep_escape_iseqs.len());
74-
75-
self.ep_escape_iseqs.retain(|&old_iseq| {
76-
let new_iseq = unsafe { rb_gc_location(VALUE(old_iseq as usize)) }.0 as IseqPtr;
77-
if old_iseq != new_iseq {
78-
moved.push(new_iseq);
79-
}
80-
old_iseq == new_iseq
81-
});
82-
83-
for new_iseq in moved {
84-
self.ep_escape_iseqs.insert(new_iseq);
85-
}
73+
let updated = std::mem::take(&mut self.ep_escape_iseqs)
74+
.into_iter()
75+
.map(|iseq| unsafe { rb_gc_location(iseq.into()) }.as_iseq())
76+
.collect();
77+
self.ep_escape_iseqs = updated;
8678
}
8779

8880
/// Update ISEQ references in Invariants::no_ep_escape_iseq_patch_points
8981
fn update_no_ep_escape_iseq_patch_points(&mut self) {
90-
let mut moved: Vec<(IseqPtr, HashSet<PatchPoint>)> = Vec::with_capacity(self.no_ep_escape_iseq_patch_points.len());
91-
let iseqs: Vec<IseqPtr> = self.no_ep_escape_iseq_patch_points.keys().cloned().collect();
92-
93-
for old_iseq in iseqs {
94-
let new_iseq = unsafe { rb_gc_location(VALUE(old_iseq as usize)) }.0 as IseqPtr;
95-
if old_iseq != new_iseq {
96-
let patch_points = self.no_ep_escape_iseq_patch_points.remove(&old_iseq).unwrap();
97-
// Do not insert patch points to no_ep_escape_iseq_patch_points yet to avoid corrupting keys that had a different ISEQ
98-
moved.push((new_iseq, patch_points));
99-
}
100-
}
101-
102-
for (new_iseq, patch_points) in moved {
103-
self.no_ep_escape_iseq_patch_points.insert(new_iseq, patch_points);
104-
}
82+
let updated = std::mem::take(&mut self.no_ep_escape_iseq_patch_points)
83+
.into_iter()
84+
.map(|(iseq, patch_points)| {
85+
let new_iseq = unsafe { rb_gc_location(iseq.into()) };
86+
(new_iseq.as_iseq(), patch_points)
87+
})
88+
.collect();
89+
self.no_ep_escape_iseq_patch_points = updated;
10590
}
10691
}
10792

0 commit comments

Comments
 (0)