Skip to content

Commit ea59662

Browse files
committed
Ensure refinements propagate across pins, clauses, and body
1 parent be0f3ae commit ea59662

4 files changed

Lines changed: 281 additions & 110 deletions

File tree

lib/elixir/lib/module/types/expr.ex

Lines changed: 4 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -501,8 +501,10 @@ defmodule Module.Types.Expr do
501501
end
502502

503503
# var
504-
def of_expr(var, expected, expr, stack, context) when is_var(var) do
505-
Of.refine_body_var(var, expected, expr, stack, context)
504+
def of_expr({_, meta, _} = var, expected, expr, stack, context) when is_var(var) do
505+
version = Keyword.fetch!(meta, :version)
506+
{type, context} = Of.refine_body_var(version, expected, expr, stack, context)
507+
{type, Pattern.of_changed([version], stack, context)}
506508
end
507509

508510
## Tuples

lib/elixir/lib/module/types/of.ex

Lines changed: 7 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -34,9 +34,11 @@ defmodule Module.Types.Of do
3434
This purposedly deletes all traces of the variable,
3535
as it is often invoked when the cause for error is elsewhere.
3636
"""
37-
def error_var({_var_name, meta, _var_context}, context) do
38-
version = Keyword.fetch!(meta, :version)
37+
def error_var({_, meta, _}, context) do
38+
error_var(Keyword.fetch!(meta, :version), context)
39+
end
3940

41+
def error_var(version, context) do
4042
update_in(context.vars[version], fn
4143
%{errored: true} = data -> data
4244
data -> Map.put(%{data | type: error_type(), off_traces: []}, :errored, true)
@@ -496,10 +498,10 @@ defmodule Module.Types.Of do
496498
end
497499

498500
# If the segment is a literal, the compiler has already checked its validity,
499-
# so we just skip it.
500-
defp binary_segment({:"::", _meta, [left, _right]}, _kind, _args, _stack, context)
501+
# so we just check the size.
502+
defp binary_segment({:"::", _meta, [left, right]}, kind, _args, stack, context)
501503
when is_binary(left) or is_number(left) do
502-
context
504+
specifier_size(kind, right, stack, context)
503505
end
504506

505507
defp binary_segment({:"::", meta, [left, right]}, kind, args, stack, context) do

0 commit comments

Comments
 (0)