Skip to content

Commit 2021fed

Browse files
author
José Valim
committed
Do not traverse clauses table to retrieve defaults
Closes #6553
1 parent e74701e commit 2021fed

File tree

1 file changed

+20
-14
lines changed

1 file changed

+20
-14
lines changed

lib/elixir/src/elixir_def.erl

Lines changed: 20 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -186,6 +186,13 @@ store_definition(Check, Kind, Meta, Name, Arity, File, Module, Defaults, Clauses
186186
Tuple = {Name, Arity},
187187
HasBody = Clauses =/= [],
188188

189+
if
190+
Defaults > 0 ->
191+
ets:insert(Defs, {{default, Name}, Arity, Defaults});
192+
true ->
193+
ok
194+
end,
195+
189196
MaxDefaults =
190197
case ets:take(Defs, {def, Tuple}) of
191198
[{_, StoredKind, StoredMeta, StoredFile, StoredCheck,
@@ -194,14 +201,14 @@ store_definition(Check, Kind, Meta, Name, Arity, File, Module, Defaults, Clauses
194201
(Check and StoredCheck) andalso
195202
check_valid_clause(Meta, File, Name, Arity, Kind, Data, StoredMeta, StoredFile),
196203
check_valid_defaults(Meta, File, Name, Arity, Kind, Defaults, StoredDefaults, LastDefaults, LastHasBody),
197-
{max(Defaults, StoredDefaults), HasBody, Defaults};
204+
max(Defaults, StoredDefaults);
198205
[] ->
199-
{Defaults, HasBody, Defaults}
206+
Defaults
200207
end,
201208

202209
Check andalso ets:insert(Data, {?last_def, Tuple}),
203210
ets:insert(Defs, [{{clauses, Tuple}, Clause} || Clause <- Clauses]),
204-
ets:insert(Defs, {{def, Tuple}, Kind, Meta, File, Check, MaxDefaults}).
211+
ets:insert(Defs, {{def, Tuple}, Kind, Meta, File, Check, {MaxDefaults, HasBody, Defaults}}).
205212

206213
%% Handling of defaults
207214

@@ -271,7 +278,7 @@ check_valid_defaults(Meta, File, Name, Arity, Kind, Defaults, 0, 0, _) when Defa
271278
check_valid_defaults(Meta, File, Name, Arity, Kind, 0, _, LastDefaults, true) when LastDefaults > 0 ->
272279
elixir_errors:form_warn(Meta, File, ?MODULE, {clauses_with_defaults, {Kind, Name, Arity}});
273280
% Clause without defaults
274-
check_valid_defaults(_Meta, _File, _Name, _Arity, _Kind, 0, _, _, _) -> [].
281+
check_valid_defaults(_Meta, _File, _Name, _Arity, _Kind, 0, _, _, _) -> ok.
275282

276283
warn_bodyless_function(Check, _Meta, _File, Module, _Kind, _Tuple)
277284
when Check == false; Module == 'Elixir.Module' ->
@@ -289,12 +296,11 @@ invalid_arg({Name, _, Kind}) when is_atom(Name), is_atom(Kind) -> false;
289296
invalid_arg(_) -> true.
290297

291298
check_previous_defaults(Meta, Module, Name, Arity, Kind, Defaults, E) ->
292-
Matches = ets:match(elixir_module:defs_table(Module),
293-
{{def, {Name, '$2'}}, '$1', '_', '_', '_', {'$3', '_', '_'}}),
299+
Matches = ets:lookup(elixir_module:defs_table(Module), {default, Name}),
294300
[begin
295301
elixir_errors:form_error(Meta, ?key(E, file), ?MODULE,
296-
{defs_with_defaults, Name, {Kind, Arity}, {K, A}})
297-
end || [K, A, D] <- Matches, A /= Arity, D /= 0, defaults_conflict(A, D, Arity, Defaults)].
302+
{defs_with_defaults, Kind, Name, Arity, A})
303+
end || {_, A, D} <- Matches, A /= Arity, D /= 0, defaults_conflict(A, D, Arity, Defaults)].
298304

299305
defaults_conflict(A, D, Arity, Defaults) ->
300306
((Arity >= (A - D)) andalso (Arity < A)) orelse
@@ -324,13 +330,13 @@ format_error({bodyless_clause, Kind, {Name, Arity}}) ->
324330
format_error({no_module, {Kind, Name, Arity}}) ->
325331
io_lib:format("cannot define function outside module, invalid scope for ~ts ~ts/~B", [Kind, Name, Arity]);
326332

327-
format_error({defs_with_defaults, Name, {Kind, Arity}, {K, A}}) when Arity > A ->
328-
io_lib:format("~ts ~ts/~B defaults conflicts with ~ts ~ts/~B",
329-
[Kind, Name, Arity, K, Name, A]);
333+
format_error({defs_with_defaults, Kind, Name, Arity, A}) when Arity > A ->
334+
io_lib:format("~ts ~ts/~B defaults conflicts with ~ts/~B",
335+
[Kind, Name, Arity, Name, A]);
330336

331-
format_error({defs_with_defaults, Name, {Kind, Arity}, {K, A}}) when Arity < A ->
332-
io_lib:format("~ts ~ts/~B conflicts with defaults from ~ts ~ts/~B",
333-
[Kind, Name, Arity, K, Name, A]);
337+
format_error({defs_with_defaults, Kind, Name, Arity, A}) when Arity < A ->
338+
io_lib:format("~ts ~ts/~B conflicts with defaults from ~ts/~B",
339+
[Kind, Name, Arity, Name, A]);
334340

335341
format_error({clauses_with_defaults, {Kind, Name, Arity}}) ->
336342
io_lib:format(""

0 commit comments

Comments
 (0)