aboutsummaryrefslogtreecommitdiffstats
path: root/lib/compiler/src/beam_ssa_codegen.erl
diff options
context:
space:
mode:
authorBjörn Gustavsson <[email protected]>2018-09-04 14:16:16 +0200
committerBjörn Gustavsson <[email protected]>2018-09-17 06:41:02 +0200
commitec1f35c9f52be894ba295b9a48237020855e3c46 (patch)
treef27e0062b987762529b784862bbc8dfa220d02af /lib/compiler/src/beam_ssa_codegen.erl
parent354c64f4c0a568e7c4766228c21d7f5e276fd549 (diff)
downloadotp-ec1f35c9f52be894ba295b9a48237020855e3c46.tar.gz
otp-ec1f35c9f52be894ba295b9a48237020855e3c46.tar.bz2
otp-ec1f35c9f52be894ba295b9a48237020855e3c46.zip
beam_ssa_codegen: Don't emit kill instructions before exit BIFs
Omitting `kill` instructions before BIFs that throw exceptions will reduce the code size. This optimization supersedes the same optimizations in beam_dead.
Diffstat (limited to 'lib/compiler/src/beam_ssa_codegen.erl')
-rw-r--r--lib/compiler/src/beam_ssa_codegen.erl16
1 files changed, 12 insertions, 4 deletions
diff --git a/lib/compiler/src/beam_ssa_codegen.erl b/lib/compiler/src/beam_ssa_codegen.erl
index becfe56b3a..40c2d8c07a 100644
--- a/lib/compiler/src/beam_ssa_codegen.erl
+++ b/lib/compiler/src/beam_ssa_codegen.erl
@@ -1270,21 +1270,29 @@ cg_call(#cg_set{anno=Anno,op=call,dst=Dst0,args=[#b_local{}=Func0|Args0]},
Call = build_call(call, Arity, {f,FuncLbl}, Context, Dst),
Is = setup_args(Args, Anno, Context, St) ++ Line ++ Call,
{Is,St};
-cg_call(#cg_set{anno=Anno,op=call,dst=Dst0,args=[#b_remote{}=Func0|Args0]},
+cg_call(#cg_set{anno=Anno0,op=call,dst=Dst0,args=[#b_remote{}=Func0|Args0]},
Where, Context, St) ->
[Dst|Args] = beam_args([Dst0|Args0], St),
#b_remote{mod=Mod0,name=Name0,arity=Arity} = Func0,
case {beam_arg(Mod0, St),beam_arg(Name0, St)} of
{{atom,Mod},{atom,Name}} ->
Func = {extfunc,Mod,Name,Arity},
- Line = call_line(Where, Func, Anno),
+ Line = call_line(Where, Func, Anno0),
Call = build_call(call_ext, Arity, Func, Context, Dst),
+ Anno = case erl_bifs:is_exit_bif(Mod, Name, Arity) of
+ true ->
+ %% There is no need to kill Y registers
+ %% before calling an exit BIF.
+ maps:remove(kill_yregs, Anno0);
+ false ->
+ Anno0
+ end,
Is = setup_args(Args, Anno, Context, St) ++ Line ++ Call,
{Is,St};
{Mod,Name} ->
Apply = build_apply(Arity, Context, Dst),
- Is = setup_args(Args++[Mod,Name], Anno, Context, St) ++
- [line(Anno)] ++ Apply,
+ Is = setup_args(Args++[Mod,Name], Anno0, Context, St) ++
+ [line(Anno0)] ++ Apply,
{Is,St}
end;
cg_call(#cg_set{anno=Anno,op=call,dst=Dst0,args=Args0},