diff options
| author | Taylan Kammer <taylan.kammer@gmail.com> | 2026-08-26 03:47:58 +0200 |
|---|---|---|
| committer | Taylan Kammer <taylan.kammer@gmail.com> | 2026-08-26 03:47:58 +0200 |
| commit | d79758c165add8cb88c7a4e4ba18f9157669a86a (patch) | |
| tree | 2072077a7c0fa5382e27ad3d7fcd875ad8e34ba4 /notes | |
| parent | 6c763c4a27bcb58281568937b9ded714af70b9da (diff) | |
I lied. That wasn't the last addition.
Diffstat (limited to 'notes')
| -rw-r--r-- | notes/260825-code-gc.md | 49 |
1 files changed, 49 insertions, 0 deletions
diff --git a/notes/260825-code-gc.md b/notes/260825-code-gc.md index d1975cc..cbb31f2 100644 --- a/notes/260825-code-gc.md +++ b/notes/260825-code-gc.md @@ -345,3 +345,52 @@ we mask off the "foreign" bits of pointers as part of equality check, making equality more than a single CPU instruction, which is kinda annoying. Then again, a similar issue applies to the rest of the 8 bits used for GC metadata. Oh well, I'll figure it out. + + +## Another try + +I won't be able to sleep unless I crack this, so here we go again. + +* Although constants may be propagated by immediate value or deep + copy, procedures otherwise refer to their own module's bindings + through lexical capture. Private bindings are copied into the + lexicals array by value (which may be a pointer anyway); public + bindings are represented by binding box pointers regardless of + whether it belongs to this or another module. Crucially, the + procedure's code never has a pointer directly copied in; only + through a potential deep copy of a propagated constant. + + This means that even for the module's own public bindings, there's + two layers of indirection: 1. Lexicals array, 2. Binding box. And + interestingly, imported bindings are treated the same. + +* Once a module is sealed, intra-module references can be optimized + two-fold: Regardless of whether it's a private or a public binding, + it's copied directly by-value (may be a pointer anyway) into code. + + Imported bindings are still treated as before: Double-indirection. + +I have to say I don't like this double-indirection that remains even +when a module is sealed. + +After agonizing for over an hour, I think I know the solution. + +A crucial detail to remember about our NaN packing strategy is that +there's already separate NaN tags for references to quoted data in +optimized code. Regular heap pointers can never actually appear in +these optimized code forms. + +So what if we simply special-cased regular pointers in code? It's +really that easy... + +Actually, we can refine this whole system somewhat. + +This has led to yet another minor overhaul of our NaN packing scheme, +but I won't get into that here. Long story short, there is now an +explicit context-dependent meaning of certain NaN tags: Before and +after the code optimization pass. This opens up a ton of room and +finally we have direct module binding pointers in optimized code. + +(It's actually a lie that there was previously no room left, but I'm +trying to make sure I have a few value ranges left to spare, because +you never know when you'll need them.) |
