Skip to content
Merged
Show file tree
Hide file tree
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
1 change: 1 addition & 0 deletions changelog.d/14059-codegen-contents-stable-bindings.md
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
A property-type proof about an object literal (or a parameter clone guarded by its contents) is kept only when no code can write that object for the binding's whole life: a delete, a store of another type, a write through an alias, a callee, a closure, Object.assign or defineProperty no longer leaves a stale number proof behind, so such reads match node.
1 change: 1 addition & 0 deletions crates/perry-codegen/src/codegen/closure.rs
Original file line number Diff line number Diff line change
Expand Up @@ -1331,6 +1331,7 @@ pub(super) fn compile_closure(
.compiler_private_async_i1_control_locals,
scope_map: &cross_module.scope_map,
string_accumulator_locals: &cross_module.string_accumulator_locals,
contents_stable_bindings: &cross_module.contents_stable_bindings,
string_length_read_of: None,
closure_rest_params,
local_closure_func_ids: HashMap::new(),
Expand Down
1 change: 1 addition & 0 deletions crates/perry-codegen/src/codegen/entry.rs
Original file line number Diff line number Diff line change
Expand Up @@ -918,6 +918,7 @@ pub(super) fn compile_module_entry(
.compiler_private_async_i1_control_locals,
scope_map: &cross_module.scope_map,
string_accumulator_locals: &cross_module.string_accumulator_locals,
contents_stable_bindings: &cross_module.contents_stable_bindings,
string_length_read_of: None,
closure_rest_params,
local_closure_func_ids: HashMap::new(),
Expand Down
1 change: 1 addition & 0 deletions crates/perry-codegen/src/codegen/entry/module_init.rs
Original file line number Diff line number Diff line change
Expand Up @@ -370,6 +370,7 @@ pub(super) fn compile_module_init(
.compiler_private_async_i1_control_locals,
scope_map: &cross_module.scope_map,
string_accumulator_locals: &cross_module.string_accumulator_locals,
contents_stable_bindings: &cross_module.contents_stable_bindings,
string_length_read_of: None,
closure_rest_params,
local_closure_func_ids: HashMap::new(),
Expand Down
1 change: 1 addition & 0 deletions crates/perry-codegen/src/codegen/function.rs
Original file line number Diff line number Diff line change
Expand Up @@ -1404,6 +1404,7 @@ pub(super) fn compile_function(
.compiler_private_async_i1_control_locals,
scope_map: &cross_module.scope_map,
string_accumulator_locals: &cross_module.string_accumulator_locals,
contents_stable_bindings: &cross_module.contents_stable_bindings,
string_length_read_of: None,
closure_rest_params,
local_closure_func_ids: HashMap::new(),
Expand Down
1 change: 1 addition & 0 deletions crates/perry-codegen/src/codegen/method.rs
Original file line number Diff line number Diff line change
Expand Up @@ -674,6 +674,7 @@ pub(super) fn compile_method(
.compiler_private_async_i1_control_locals,
scope_map: &cross_module.scope_map,
string_accumulator_locals: &cross_module.string_accumulator_locals,
contents_stable_bindings: &cross_module.contents_stable_bindings,
string_length_read_of: None,
closure_rest_params,
local_closure_func_ids: HashMap::new(),
Expand Down
1 change: 1 addition & 0 deletions crates/perry-codegen/src/codegen/method_static.rs
Original file line number Diff line number Diff line change
Expand Up @@ -349,6 +349,7 @@ pub(in crate::codegen) fn compile_static_method(
.compiler_private_async_i1_control_locals,
scope_map: &cross_module.scope_map,
string_accumulator_locals: &cross_module.string_accumulator_locals,
contents_stable_bindings: &cross_module.contents_stable_bindings,
string_length_read_of: None,
closure_rest_params,
local_closure_func_ids: HashMap::new(),
Expand Down
23 changes: 15 additions & 8 deletions crates/perry-codegen/src/codegen/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -3182,6 +3182,7 @@ fn lower_module(
compiler_private_async_i1_control_locals,
scope_map: Default::default(),
string_accumulator_locals: Default::default(),
contents_stable_bindings: Default::default(),
definite_init: Default::default(),
disable_buffer_fast_path,
program_shadows_buffer_read_method:
Expand Down Expand Up @@ -3405,6 +3406,7 @@ fn lower_module(
cross_module.scope_map =
crate::scope_env::ScopeMap::build(hir, &module_boxed_vars, &module_globals);
cross_module.string_accumulator_locals = crate::collectors::string_accumulator_locals(hir);
cross_module.contents_stable_bindings = crate::collectors::contents_stable_bindings(hir);
cross_module.capture_type_proofs =
crate::collectors::typed_locals::capture_proofs(hir, &module_boxed_vars, &module_globals);
cross_module.definite_init = crate::collectors::definite_init::collect(hir);
Expand Down Expand Up @@ -3846,18 +3848,23 @@ fn lower_module(
// on `demoted`, `fill(values: Float64Array, nodes: number)` loses
// `fill$spec_ta7x10000_i32` entirely, because writing an element
// reads as "mutation" of the typed-array parameter.
let body_calls = crate::collectors::body_contains_call(&f.body);
//
// Both halves are the definition of a contents-stable binding
// (`collectors::contents_stable_bindings`), shared with the
// let-binding proofs: a parameter is an entry-aliased binding, so
// it is stable only when no write reaches it (through it, an
// alias or an escape) and the body runs no unknown code and stores
// through no foreign root. A primitive keeps only the rebinding
// half: no callee can reach the caller's copy.
let guard_blocked: Vec<bool> = f
.params
.iter()
.map(|p| {
crate::collectors::has_any_mutation(&f.body, p.id)
|| (body_calls
&& spec_return_proof::is_reference_like(
&cross_module.type_aliases,
&p.ty,
0,
))
if spec_return_proof::is_reference_like(&cross_module.type_aliases, &p.ty, 0) {
!cross_module.contents_stable_bindings.contains(&p.id)
} else {
crate::collectors::has_any_mutation(&f.body, p.id)
}
})
.collect();
let declaration_guards = param_guard::declaration_guards(
Expand Down
3 changes: 3 additions & 0 deletions crates/perry-codegen/src/codegen/opts.rs
Original file line number Diff line number Diff line change
Expand Up @@ -1287,6 +1287,9 @@ pub(crate) struct CrossModuleCtx<'a> {
/// Untyped string accumulators, module-wide
/// (`collectors::string_accumulator_locals`).
pub string_accumulator_locals: std::collections::HashSet<u32>,
/// Bindings whose object no code writes for their whole life
/// (`collectors::contents_stable_bindings`), module-wide.
pub contents_stable_bindings: std::collections::HashSet<u32>,
/// Bindings assigned before any reader can run
/// (`collectors::definite_init`), module-wide.
pub definite_init: crate::collectors::DefiniteInit,
Expand Down
Loading
Loading