cover/Elixir.Tools.User.Ast.html

1 defmodule Tools.User.Ast do
2 import Enum, only: [reduce: 3]
3 import Macro, only: [prewalk: 3]
4
5 def bound(ast) do
6
:-(
{_ast, bound} = prewalk(ast, [], &bind/2)
7
:-(
bound
8 end
9
10 def refs(ast) do
11
:-(
{_ast, refs} = prewalk(ast, [], &mark/2)
12
:-(
refs
13 end
14
15
:-(
defp bind({:=, _meta, [pattern, _expr]}, bound) do
16 {nil, names(pattern, bound)}
17 end
18
19
:-(
defp bind(node, bound) do
20 {node, bound}
21 end
22
23
:-(
defp names({:_, _, nil}, acc), do: acc
24
:-(
defp names({nil, _, nil}, acc), do: acc
25
:-(
defp names({true, _, nil}, acc), do: acc
26
:-(
defp names({false, _, nil}, acc), do: acc
27
28
:-(
defp names({name, _, nil}, acc) when is_atom(name) do
29
:-(
[to_string(name) | acc]
30 end
31
32 defp names({_name, _, args}, acc) when is_list(args) do
33
:-(
reduce(args, acc, &names/2)
34 end
35
36 defp names({left, right}, acc) do
37
:-(
names(left, names(right, acc))
38 end
39
40 defp names(list, acc) when is_list(list) do
41
:-(
reduce(list, acc, &names/2)
42 end
43
44
:-(
defp names(_node, acc), do: acc
45
46
:-(
defp mark({nil, _meta, nil}, refs), do: {nil, refs}
47
:-(
defp mark({true, _meta, nil}, refs), do: {true, refs}
48
:-(
defp mark({false, _meta, nil}, refs), do: {false, refs}
49
50
:-(
defp mark({name, _meta, nil}, refs) when is_atom(name) do
51
:-(
{nil, [to_string(name) | refs]}
52 end
53
54
:-(
defp mark(node, refs), do: {node, refs}
55 end
Line Hits Source