From f782313c452eebb873cb48d74c7705791cf7e52f Mon Sep 17 00:00:00 2001 From: Bitwise Operators Date: Wed, 3 Aug 2022 15:14:10 +0200 Subject: [PATCH] Add BitwiseNot and BooleanNot operators to SimpleTypeInferer. Should fix #8307. --- .../Expression/SimpleTypeInferer.php | 55 +++++++++++++++++++ 1 file changed, 55 insertions(+) diff --git a/src/Psalm/Internal/Analyzer/Statements/Expression/SimpleTypeInferer.php b/src/Psalm/Internal/Analyzer/Statements/Expression/SimpleTypeInferer.php index 44412fcb091..91460651a4f 100644 --- a/src/Psalm/Internal/Analyzer/Statements/Expression/SimpleTypeInferer.php +++ b/src/Psalm/Internal/Analyzer/Statements/Expression/SimpleTypeInferer.php @@ -203,6 +203,61 @@ public static function infer( } } + if ($stmt instanceof PhpParser\Node\Expr\BitwiseNot) { + $stmt_expr_type = self::infer( + $codebase, + $nodes, + $stmt->expr, + $aliases, + $file_source, + $existing_class_constants, + $fq_classlike_name + ); + + if ($stmt_expr_type === null) { + return null; + } + + $invalidTypes = clone $stmt_expr_type; + $invalidTypes->removeType('string'); + $invalidTypes->removeType('int'); + $invalidTypes->removeType('float'); + + if (!$invalidTypes->isUnionEmpty()) { + return null; + } + + $types = []; + if ($stmt_expr_type->hasString()) { + $types[] = Type::getString(); + } + if ($stmt_expr_type->hasInt() || $stmt_expr_type->hasFloat()) { + $types[] = Type::getInt(); + } + + return $types ? Type::combineUnionTypeArray($types, null) : null; + } + + if ($stmt instanceof PhpParser\Node\Expr\BooleanNot) { + $stmt_expr_type = self::infer( + $codebase, + $nodes, + $stmt->expr, + $aliases, + $file_source, + $existing_class_constants, + $fq_classlike_name + ); + + if ($stmt_expr_type === null || $stmt_expr_type->isAlwaysFalsy()) { + return Type::getTrue(); + } elseif ($stmt_expr_type->isAlwaysTruthy()) { + return Type::getFalse(); + } else { + return Type::getBool(); + } + } + if ($stmt instanceof PhpParser\Node\Expr\ConstFetch) { $name = strtolower($stmt->name->parts[0]); if ($name === 'false') {