@@ -367,8 +367,8 @@ defmodule Module.Types.Apply do
367367 right_literal? = Macro . quoted_literal? ( right )
368368
369369 case { left_literal? , right_literal? } do
370- { true , false } -> custom_compare ( name , right , left , expected , expr , stack , context , of_fun )
371- { false , true } -> custom_compare ( name , left , right , expected , expr , stack , context , of_fun )
370+ { true , false } -> literal_compare ( name , right , left , expected , expr , stack , context , of_fun )
371+ { false , true } -> literal_compare ( name , left , right , expected , expr , stack , context , of_fun )
372372 { literal? , _ } -> compare ( name , left , right , literal? , expr , stack , context , of_fun )
373373 end
374374 end
@@ -495,7 +495,7 @@ defmodule Module.Types.Apply do
495495 when ( fun in [ :length , :map_size ] and is_integer ( literal ) and literal >= 0 ) or
496496 ( fun in [ :tuple_size ] and literal in 0 .. 15 )
497497
498- defp custom_compare (
498+ defp literal_compare (
499499 name ,
500500 { { :. , _ , [ :erlang , fun ] } , _ , [ arg ] } = left ,
501501 literal ,
@@ -547,14 +547,18 @@ defmodule Module.Types.Apply do
547547 end
548548 end
549549
550- defp custom_compare ( name , arg , literal , expected , expr , stack , context , of_fun ) do
550+ defp literal_compare ( name , arg , literal , expected , expr , stack , context , of_fun ) do
551+ { type , context } = of_fun . ( literal , term ( ) , expr , stack , context )
552+ literal_compare ( name , arg , type , singleton? ( type ) , expected , expr , stack , context , of_fun )
553+ end
554+
555+ def literal_compare ( name , arg , type , singleton? , expected , expr , stack , context , of_fun ) do
551556 case booleaness ( expected ) do
552557 booleaness when booleaness in [ :maybe_both , :none ] ->
553- compare ( name , arg , literal , false , expr , stack , context , of_fun )
558+ { arg_type , context } = of_fun . ( arg , term ( ) , expr , stack , context )
559+ return_compare ( name , arg_type , type , boolean ( ) , false , expr , stack , context )
554560
555561 { boolean , _maybe_or_always } ->
556- { literal_type , context } = of_fun . ( literal , term ( ) , expr , stack , context )
557-
558562 { polarity , return } =
559563 case boolean do
560564 true -> { name in [ :== , :"=:=" ] , @ atom_true }
@@ -563,28 +567,28 @@ defmodule Module.Types.Apply do
563567
564568 # This logic mirrors the code in `Pattern.of_pattern_tree`
565569 # If it is a singleton, we can always be precise
566- if singleton? ( literal_type ) do
567- expected = if polarity , do: literal_type , else: negation ( literal_type )
570+ if singleton? do
571+ expected = if polarity , do: type , else: negation ( type )
568572 { arg_type , context } = of_fun . ( arg , expected , expr , stack , context )
569573 result = if subtype? ( arg_type , expected ) , do: return , else: boolean ( )
570574
571575 # Because reverse polarity means we will infer negated types
572576 # (which are naturally disjoint), we skip checks in such cases
573577 skip_check? = not polarity
574- return_compare ( name , arg_type , literal_type , result , skip_check? , expr , stack , context )
578+ return_compare ( name , arg_type , type , result , skip_check? , expr , stack , context )
575579 else
576580 expected =
577581 cond do
578582 # We are checking for `not x == 1` or similar, we can't say anything about x
579583 polarity == false -> term ( )
580584 # We are checking for `x == 1`, make sure x is integer or float
581- name in [ :== , :"/=" ] -> numberize ( literal_type )
585+ name in [ :== , :"/=" ] -> numberize ( type )
582586 # Otherwise we have the literal type as is
583- true -> literal_type
587+ true -> type
584588 end
585589
586590 { arg_type , context } = of_fun . ( arg , expected , expr , stack , context )
587- return_compare ( name , arg_type , literal_type , boolean ( ) , false , expr , stack , context )
591+ return_compare ( name , arg_type , type , boolean ( ) , false , expr , stack , context )
588592 end
589593 end
590594 end
0 commit comments