-
Notifications
You must be signed in to change notification settings - Fork 17
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
khepri_fun: Resolve label inside {call_fun2, {u,Idx}, ...}
instruction
#149
Conversation
Codecov ReportBase: 90.82% // Head: 90.99% // Increases project coverage by
Additional details and impacted files@@ Coverage Diff @@
## main #149 +/- ##
==========================================
+ Coverage 90.82% 90.99% +0.16%
==========================================
Files 16 16
Lines 2868 2886 +18
==========================================
+ Hits 2605 2626 +21
+ Misses 263 260 -3
Flags with carried forward coverage won't be shown. Click here to find out more.
Help us with your feedback. Take ten seconds to tell us how you rate us. Have a feature suggestion? Share it here. ☔ View full report at Codecov. |
FTR,
The code to decode all chunks is in |
In pull request #134, the `{u,Idx}` argument was discarded and replaced by `{atom, safe}` because the module was already compiled successfully and the register used in the instruction must point to a valid function. `Idx` is an offset in the Lambda table ("FunT" in the beam chunks). In this patch, we decode this table. This allows us to resolve the label used by `call_fun2` and replace `{u,Idx}` by a valid `{f,Label}`. This is probably a small optimization of the resulting code, but it closer to what the Erlang compiler would do. The testcase is expanded to execute the extracted function to make sure it still works.
51810f0
to
958169b
Compare
Since #149, we resolve and adjust the jump label inside the `call_fun2` instruction. This way we are as close as possible to the code originally produced by the compiler and benefit from its optimizations. However, there is one situation where we can't keep the jump label: it is when the called local function is not local anymore after extraction. To avoid many almost identical copies of the same anonymous function where only the environment changes, `khepri_fun` will extract the function in a dedicated module and keep the environment separate. If there is another anonymous function inside this environment, it will become its own module. Therefore, it's possible that in the original Beam code, the two anonymous functions were inside the same module. If the compiler emitted a `call_fun2` instruction, it could use a jump label in the outer function to call the inner function passed in the environment. After extraction by `khepri_fun`, this is no longer possible because the inner function will be in another module. `call_fun2` must use the `{atom, safe}` argument instead.
Since #149, we resolve and adjust the jump label inside the `call_fun2` instruction. This way we are as close as possible to the code originally produced by the compiler and benefit from its optimizations. However, there is one situation where we can't keep the jump label: it is when the called local function is not local anymore after extraction. To avoid many almost identical copies of the same anonymous function where only the environment changes, `khepri_fun` will extract the function in a dedicated module and keep the environment separate. If there is another anonymous function inside this environment, it will become its own module. Therefore, it's possible that in the original Beam code, the two anonymous functions were inside the same module. If the compiler emitted a `call_fun2` instruction, it could use a jump label in the outer function to call the inner function passed in the environment. After extraction by `khepri_fun`, this is no longer possible because the inner function will be in another module. `call_fun2` must use the `{atom, safe}` argument instead.
In pull request #134, the
{u,Idx}
argument was discarded and replaced by{atom, safe}
because the module was already compiled successfully and the register used in the instruction must point to a valid function.Idx
is an offset in the Lambda table ("FunT" in the beam chunks). In this patch, we decode this table. This allows us to resolve the label used bycall_fun2
and replace{u,Idx}
by a valid{f,Label}
.This is probably a small optimization of the resulting code, but it closer to what the Erlang compiler would do.
The testcase is expanded to execute the extracted function to make sure it still works.