aboutsummaryrefslogtreecommitdiffstats
path: root/lib/compiler/src/v3_kernel.erl
diff options
context:
space:
mode:
authorBjörn Gustavsson <[email protected]>2018-03-20 07:34:00 +0100
committerBjörn Gustavsson <[email protected]>2018-03-24 07:32:26 +0100
commita5e80861faedc84d373ccda95ae6f8c7aff11bcf (patch)
treedd5eabc7bcc1cb7e3402b7cc00749a9f04be45d8 /lib/compiler/src/v3_kernel.erl
parent9d2f5cde19cffca9a00b8fad8075bf160cc872d3 (diff)
downloadotp-a5e80861faedc84d373ccda95ae6f8c7aff11bcf.tar.gz
otp-a5e80861faedc84d373ccda95ae6f8c7aff11bcf.tar.bz2
otp-a5e80861faedc84d373ccda95ae6f8c7aff11bcf.zip
Avoid overflowing the atom table
Use integer variable names instead of atoms in v3_core, sys_core_fold, and v3_kernel to avoid overflowing the atom table. It is a deliberate design decision to calculate the first free integer variable name (in sys_core_fold and v3_kernel) instead of somehow passing it from one pass to another. I don't want that kind of dependency between compiler passes. Also note that the next free variable name is not easily available after running the inliner.
Diffstat (limited to 'lib/compiler/src/v3_kernel.erl')
-rw-r--r--lib/compiler/src/v3_kernel.erl11
1 files changed, 8 insertions, 3 deletions
diff --git a/lib/compiler/src/v3_kernel.erl b/lib/compiler/src/v3_kernel.erl
index dfe8d26afb..4e3ceedbc0 100644
--- a/lib/compiler/src/v3_kernel.erl
+++ b/lib/compiler/src/v3_kernel.erl
@@ -157,7 +157,13 @@ include_attribute(_) -> true.
function({#c_var{name={F,Arity}=FA},Body}, St0) ->
%%io:format("~w/~w~n", [F,Arity]),
try
- St1 = St0#kern{func=FA,ff=undefined,vcount=0,fcount=0,ds=cerl_sets:new()},
+ %% Find a suitable starting value for the variable counter. Note
+ %% that this pass assumes that new_var_name/1 returns a variable
+ %% name distinct from any variable used in the entire body of
+ %% the function. We use integers as variable names to avoid
+ %% filling up the atom table when compiling huge functions.
+ Count = cerl_trees:next_free_variable_name(Body),
+ St1 = St0#kern{func=FA,ff=undefined,vcount=Count,fcount=0,ds=cerl_sets:new()},
{#ifun{anno=Ab,vars=Kvs,body=B0},[],St2} = expr(Body, new_sub(), St1),
{B1,_,St3} = ubody(B0, return, St2),
%%B1 = B0, St3 = St2, %Null second pass
@@ -168,7 +174,6 @@ function({#c_var{name={F,Arity}=FA},Body}, St0) ->
erlang:raise(Class, Error, Stack)
end.
-
%% body(Cexpr, Sub, State) -> {Kexpr,[PreKepxr],State}.
%% Do the main sequence of a body. A body ends in an atomic value or
%% values. Must check if vector first so do expr.
@@ -1356,7 +1361,7 @@ new_fun_name(Type, #kern{func={F,Arity},fcount=C}=St) ->
%% new_var_name(State) -> {VarName,State}.
new_var_name(#kern{vcount=C}=St) ->
- {list_to_atom("@k" ++ integer_to_list(C)),St#kern{vcount=C+1}}.
+ {C,St#kern{vcount=C+1}}.
%% new_var(State) -> {#k_var{},State}.