"Fossies" - the Fresh Open Source Software Archive  

Source code changes of the file "analysis/typeCheck.ml" between
pyre-check-0.0.54.tar.gz and pyre-check-0.0.55.tar.gz

About: Pyre is a performant type checker for Python (ships with Pysa, a security focused static analysis tool).

typeCheck.ml  (pyre-check-0.0.54):typeCheck.ml  (pyre-check-0.0.55)
skipping to change at line 121 skipping to change at line 121
[Some location, Error.InvalidArgument (Error.ConcreteVariable { expression ; annotation })] [Some location, Error.InvalidArgument (Error.ConcreteVariable { expression ; annotation })]
| Mismatch mismatch -> | Mismatch mismatch ->
let { SignatureSelectionTypes.actual; expected; name; position } = Node.va lue mismatch in let { SignatureSelectionTypes.actual; expected; name; position } = Node.va lue mismatch in
let mismatch, name, position, location = let mismatch, name, position, location =
( Error.create_mismatch ~resolution:global_resolution ~actual ~expected ~covariant:true, ( Error.create_mismatch ~resolution:global_resolution ~actual ~expected ~covariant:true,
name, name,
position, position,
Node.location mismatch ) Node.location mismatch )
in in
let kind = let kind =
let normal = let normal = Error.IncompatibleParameterType { name; position; callee; m
Error.IncompatibleParameterType (Argument { name; position; callee; mi ismatch } in
smatch })
in
let typed_dictionary_error let typed_dictionary_error
~method_name ~method_name
~position ~position
{ Type.Record.TypedDictionary.fields; name = typed_dictionary_name } { Type.Record.TypedDictionary.fields; name = typed_dictionary_name }
= =
if if
Type.TypedDictionary.is_special_mismatch Type.TypedDictionary.is_special_mismatch
~class_name:typed_dictionary_name ~class_name:typed_dictionary_name
~method_name ~method_name
~position ~position
skipping to change at line 186 skipping to change at line 184
List.last_exn callee_reference_list |> inverse_operator >>= oper ator_name_to_symbol List.last_exn callee_reference_list |> inverse_operator >>= oper ator_name_to_symbol
in in
match operator_symbol, callee_expression >>| Node.value with match operator_symbol, callee_expression >>| Node.value with
| Some operator_name, Some (Expression.Name (Attribute { special = t rue; _ })) -> | Some operator_name, Some (Expression.Name (Attribute { special = t rue; _ })) ->
let left_operand, right_operand = let left_operand, right_operand =
if is_uninverted then if is_uninverted then
self_annotation, actual self_annotation, actual
else else
actual, self_annotation actual, self_annotation
in in
Error.IncompatibleParameterType Error.UnsupportedOperand (Binary { operator_name; left_operand;
(Operand { operator_name; left_operand; right_operand }) right_operand })
| _ -> normal ) | _ -> normal )
| Some (Type.Primitive _ as annotation), Some [_; method_name] -> | Some (Type.Primitive _ as annotation), Some [_; method_name] ->
GlobalResolution.get_typed_dictionary ~resolution:global_resolution annotation GlobalResolution.get_typed_dictionary ~resolution:global_resolution annotation
>>| typed_dictionary_error ~method_name ~position >>| typed_dictionary_error ~method_name ~position
|> Option.value ~default:normal |> Option.value ~default:normal
| _ -> normal | _ -> normal
in in
[Some location, kind] [Some location, kind]
| MismatchWithListVariadicTypeVariable { variable; mismatch } -> | MismatchWithListVariadicTypeVariable { variable; mismatch } ->
[None, Error.InvalidArgument (ListVariadicVariable { variable; mismatch }) ] [None, Error.InvalidArgument (ListVariadicVariable { variable; mismatch }) ]
skipping to change at line 1903 skipping to change at line 1900
Build up the original error in case the inverse operator does not typec heck. *) Build up the original error in case the inverse operator does not typec heck. *)
let potential_missing_operator_error = let potential_missing_operator_error =
match resolved, Node.value callee, target with match resolved, Node.value callee, target with
| Type.Top, Expression.Name (Attribute { attribute; _ }), Some target | Type.Top, Expression.Name (Attribute { attribute; _ }), Some target
when Option.is_some (inverse_operator attribute) when Option.is_some (inverse_operator attribute)
&& (not (Type.is_any target)) && (not (Type.is_any target))
&& not (Type.is_unbound target) -> ( && not (Type.is_unbound target) -> (
match arguments, operator_name_to_symbol attribute with match arguments, operator_name_to_symbol attribute with
| [{ AttributeResolution.Argument.resolved; _ }], Some operator_name -> | [{ AttributeResolution.Argument.resolved; _ }], Some operator_name ->
Some Some
(Error.IncompatibleParameterType (Error.UnsupportedOperand
(Operand { operator_name; left_operand = target; right_oper (Binary { operator_name; left_operand = target; right_opera
and = resolved })) nd = resolved }))
| _ -> Some (Error.UndefinedAttribute { attribute; origin = Error.Cl ass target }) ) | _ -> Some (Error.UndefinedAttribute { attribute; origin = Error.Cl ass target }) )
| _ -> None | _ -> None
in in
let signatures = let signatures =
let callables, arguments, was_operator_inverted = let callables, arguments, was_operator_inverted =
let callable resolved = let callable resolved =
match unpack_callable_and_self_argument resolved with match unpack_callable_and_self_argument resolved with
| Some unpacked -> Some unpacked | Some unpacked -> Some unpacked
| _ -> find_method ~parent:resolved ~name:"__call__" ~special_method :true | _ -> find_method ~parent:resolved ~name:"__call__" ~special_method :true
in in
skipping to change at line 1956 skipping to change at line 1953
in in
get_callables resolved get_callables resolved
in in
Context.Builder.add_callee Context.Builder.add_callee
~global_resolution ~global_resolution
~target ~target
~callables:(callables >>| List.map ~f:(fun { callable; _ } -> callable )) ~callables:(callables >>| List.map ~f:(fun { callable; _ } -> callable ))
~arguments:original_arguments ~arguments:original_arguments
~dynamic ~dynamic
~qualifier:Context.qualifier ~qualifier:Context.qualifier
~callee_type:resolved
~callee; ~callee;
let signature_with_unpacked_callable_and_self_argument let signature_with_unpacked_callable_and_self_argument
({ callable; self_argument } as unpacked_callable_and_self_argument) ({ callable; self_argument } as unpacked_callable_and_self_argument)
= =
let signature = let signature =
GlobalResolution.signature_select GlobalResolution.signature_select
(* TODO use Resolved to reuse resolved types from above *) (* TODO use Resolved to reuse resolved types from above *)
~arguments:(Resolved arguments) ~arguments:(Resolved arguments)
~global_resolution ~global_resolution
~resolve_with_locals:(resolve_expression_type_with_locals ~resolut ion) ~resolve_with_locals:(resolve_expression_type_with_locals ~resolut ion)
skipping to change at line 2303 skipping to change at line 2301
errors errors
in in
{ resolution; errors; resolved = cast_annotation; resolved_annotation = None; base = None } { resolution; errors; resolved = cast_annotation; resolved_annotation = None; base = None }
| Call | Call
{ {
callee = { Node.value = Name (Name.Identifier "isinstance"); _ } as ca llee; callee = { Node.value = Name (Name.Identifier "isinstance"); _ } as ca llee;
arguments = arguments =
[{ Call.Argument.value = expression; _ }; { Call.Argument.value = an notations; _ }] as [{ Call.Argument.value = expression; _ }; { Call.Argument.value = an notations; _ }] as
arguments; arguments;
} -> } ->
let { Resolved.resolved; _ } = forward_expression ~resolution ~expressio n:callee in
let callables = let callables =
let { Resolved.resolved; _ } = forward_expression ~resolution ~express ion:callee in
match resolved with match resolved with
| Type.Callable callable -> Some [callable] | Type.Callable callable -> Some [callable]
| _ -> None | _ -> None
in in
Context.Builder.add_callee Context.Builder.add_callee
~global_resolution ~global_resolution
~target:None ~target:None
~callables ~callables
~arguments ~arguments
~dynamic:false ~dynamic:false
~qualifier:Context.qualifier ~qualifier:Context.qualifier
~callee_type:resolved
~callee; ~callee;
(* Be angelic and compute errors using the typeshed annotation for isins tance. *) (* Be angelic and compute errors using the typeshed annotation for isins tance. *)
(* We special case type inference for `isinstance` in asserted, and the typeshed stubs are (* We special case type inference for `isinstance` in asserted, and the typeshed stubs are
imprecise (doesn't correctly declare the arguments as a recursive tup le. *) imprecise (doesn't correctly declare the arguments as a recursive tup le. *)
let resolution, errors = let resolution, errors =
let { Resolved.resolution; errors; _ } = forward_expression ~resolutio n ~expression in let { Resolved.resolution; errors; _ } = forward_expression ~resolutio n ~expression in
let resolution, errors, annotations = let resolution, errors, annotations =
let rec collect_types (state, errors, collected) = function let rec collect_types (state, errors, collected) = function
skipping to change at line 2351 skipping to change at line 2350
resolution, List.append expression_errors errors, new_annotati ons @ collected resolution, List.append expression_errors errors, new_annotati ons @ collected
in in
collect_types (resolution, errors, []) annotations collect_types (resolution, errors, []) annotations
in in
let add_incompatible_non_meta_error errors (non_meta, location) = let add_incompatible_non_meta_error errors (non_meta, location) =
emit_error emit_error
~errors ~errors
~location ~location
~kind: ~kind:
(Error.IncompatibleParameterType (Error.IncompatibleParameterType
(Argument {
{ name = None;
name = None; position = 2;
position = 2; callee = Some (Reference.create "isinstance");
callee = Some (Reference.create "isinstance"); mismatch =
mismatch = {
{ Error.actual = non_meta;
Error.actual = non_meta; expected =
expected = Type.union
Type.union [Type.meta Type.Any; Type.Tuple (Type.Unbounded (Ty
[ pe.meta Type.Any))];
Type.meta Type.Any; due_to_invariance = false;
Type.Tuple (Type.Unbounded (Type.meta Type.Any };
)); })
];
due_to_invariance = false;
};
}))
in in
let rec is_compatible annotation = let rec is_compatible annotation =
match annotation with match annotation with
| _ when Type.is_meta annotation -> true | _ when Type.is_meta annotation -> true
| Type.Primitive "typing._Alias" -> true | Type.Primitive "typing._Alias" -> true
| Type.Tuple (Type.Unbounded annotation) -> Type.is_meta annotation | Type.Tuple (Type.Unbounded annotation) -> Type.is_meta annotation
| Type.Tuple (Type.Bounded (Type.OrderedTypes.Concrete annotations)) -> | Type.Tuple (Type.Bounded (Type.OrderedTypes.Concrete annotations)) ->
List.for_all ~f:Type.is_meta annotations List.for_all ~f:Type.is_meta annotations
| Type.Union annotations -> List.for_all annotations ~f:is_compatibl e | Type.Union annotations -> List.for_all annotations ~f:is_compatibl e
| _ -> false | _ -> false
skipping to change at line 2495 skipping to change at line 2490
~resolved:resolved_callee ~resolved:resolved_callee
~arguments ~arguments
in in
{ {
resolution = updated_resolution; resolution = updated_resolution;
errors = updated_errors; errors = updated_errors;
resolved; resolved;
resolved_annotation = None; resolved_annotation = None;
base = None; base = None;
} }
| ComparisonOperator { ComparisonOperator.left; right; operator = Comparison | ComparisonOperator
Operator.In } { ComparisonOperator.left; right; operator = ComparisonOperator.In as op
| ComparisonOperator { ComparisonOperator.left; right; operator = Comparison erator }
Operator.NotIn } -> | ComparisonOperator
{ ComparisonOperator.left; right; operator = ComparisonOperator.NotIn as
operator } ->
let resolve_in_call let resolve_in_call
(resolution, errors, joined_annotation) (resolution, errors, joined_annotation)
{ Type.instantiated; class_name; accessed_through_class } { Type.instantiated; class_name; accessed_through_class }
= =
let resolve_method let resolve_method
?(accessed_through_class = false) ?(accessed_through_class = false)
?(special_method = false) ?(special_method = false)
class_name class_name
instantiated instantiated
name name
skipping to change at line 2656 skipping to change at line 2653
(Name.Attribute (Name.Attribute
{ base = getitem; attribute = "__eq__"; special = true }); { base = getitem; attribute = "__eq__"; special = true });
}; };
arguments = [{ Call.Argument.name = None; value = left }]; arguments = [{ Call.Argument.name = None; value = left }];
}; };
} }
in in
let ({ Resolved.resolved; _ } as getitem_resolution) = let ({ Resolved.resolved; _ } as getitem_resolution) =
forward_expression ~resolution ~expression:getitem_attribu te forward_expression ~resolution ~expression:getitem_attribu te
in in
let is_valid_getitem = function
| Type.Parametric
{
name = "BoundMethod";
parameters =
[
Single
(Type.Callable
{
implementation =
{ parameters = Defined (_ :: index_param
eter :: _); _ };
_;
});
_;
];
}
| Type.Callable
{
implementation = { parameters = Defined (_ :: index_
parameter :: _); _ };
_;
}
when GlobalResolution.less_or_equal
global_resolution
~left:Type.integer
~right:
( Type.Callable.Parameter.annotation index_para
meter
|> Option.value ~default:Type.Bottom ) ->
true
| _ -> false
in
match resolved with match resolved with
| Type.Parametric | Type.Union elements when List.for_all ~f:is_valid_getitem
{ elements ->
name = "BoundMethod"; forward_expression ~resolution ~expression:call
parameters = | _ when is_valid_getitem resolved ->
[
Single
(Type.Callable
{
implementation =
{ parameters = Defined (_ :: index_paramet
er :: _); _ };
_;
});
_;
];
}
| Type.Callable
{
implementation = { parameters = Defined (_ :: index_pa
rameter :: _); _ };
_;
}
when GlobalResolution.less_or_equal
global_resolution
~left:Type.integer
~right:
( Type.Callable.Parameter.annotation index_parame
ter
|> Option.value ~default:Type.Bottom ) ->
(* TODO: Throw new error type here warning on invalid me
mbership check. *)
forward_expression ~resolution ~expression:call forward_expression ~resolution ~expression:call
| _ -> { getitem_resolution with Resolved.resolved = Type.An | _ ->
y } ) ) let errors =
let { Resolved.resolved; _ } =
forward_expression ~resolution ~expression:right
in
emit_error
~errors
~location
~kind:
(Error.UnsupportedOperand
(Unary
{
operator_name =
Format.asprintf
"%a"
ComparisonOperator.pp_comparison_opera
tor
operator;
operand = resolved;
}))
in
{ getitem_resolution with Resolved.resolved = Type.Any;
errors } ) )
in in
resolution, errors, GlobalResolution.join global_resolution joined_ann otation resolved resolution, errors, GlobalResolution.join global_resolution joined_ann otation resolved
in in
let { Resolved.resolution; resolved; errors; _ } = let { Resolved.resolution; resolved; errors; _ } =
forward_expression ~resolution ~expression:right forward_expression ~resolution ~expression:right
in in
let resolution, errors, resolved = let resolution, errors, resolved =
(* We should really error here if resolve_class fails *) (* We should really error here if resolve_class fails *)
Type.resolve_class resolved Type.resolve_class resolved
>>| List.fold ~f:resolve_in_call ~init:(resolution, errors, Type.Botto m) >>| List.fold ~f:resolve_in_call ~init:(resolution, errors, Type.Botto m)
 End of changes. 12 change blocks. 
65 lines changed or deleted 90 lines changed or added

Home  |  About  |  Features  |  All  |  Newest  |  Dox  |  Diffs  |  RSS Feeds  |  Screenshots  |  Comments  |  Imprint  |  Privacy  |  HTTP(S)