Skip to content

Commit

Permalink
Fix crash involving unreachable binary ops (#11680)
Browse files Browse the repository at this point in the history
Fixes #11679
  • Loading branch information
hauntsaninja authored Dec 8, 2021
1 parent 01e6aba commit e20042f
Show file tree
Hide file tree
Showing 3 changed files with 19 additions and 3 deletions.
3 changes: 2 additions & 1 deletion mypy/checker.py
Original file line number Diff line number Diff line change
Expand Up @@ -4375,7 +4375,8 @@ def find_isinstance_check(self, node: Expression
If either of the values in the tuple is None, then that particular
branch can never occur.
Guaranteed to not return None, None. (But may return {}, {})
May return {}, {}.
Can return None, None in situations involving NoReturn.
"""
if_map, else_map = self.find_isinstance_check_helper(node)
new_if_map = self.propagate_up_typemap_info(self.type_map, if_map)
Expand Down
7 changes: 5 additions & 2 deletions mypy/checkexpr.py
Original file line number Diff line number Diff line change
Expand Up @@ -2862,13 +2862,16 @@ def check_boolean_op(self, e: OpExpr, context: Context) -> Type:
with (self.msg.disable_errors() if right_map is None else nullcontext()):
right_type = self.analyze_cond_branch(right_map, e.right, expanded_left_type)

if left_map is None and right_map is None:
return UninhabitedType()

if right_map is None:
# The boolean expression is statically known to be the left value
assert left_map is not None # find_isinstance_check guarantees this
assert left_map is not None
return left_type
if left_map is None:
# The boolean expression is statically known to be the right value
assert right_map is not None # find_isinstance_check guarantees this
assert right_map is not None
return right_type

if e.op == 'and':
Expand Down
12 changes: 12 additions & 0 deletions test-data/unit/check-unreachable-code.test
Original file line number Diff line number Diff line change
Expand Up @@ -1416,3 +1416,15 @@ x = 1 # E: Statement is unreachable
raise Exception
x = 1 # E: Statement is unreachable
[builtins fixtures/exception.pyi]

[case testUnreachableNoReturnBinaryOps]
# flags: --warn-unreachable
from typing import NoReturn

a: NoReturn
a and 1 # E: Right operand of "and" is never evaluated
a or 1 # E: Right operand of "or" is never evaluated
a or a # E: Right operand of "or" is never evaluated
1 and a and 1 # E: Right operand of "and" is never evaluated
a and a # E: Right operand of "and" is never evaluated
[builtins fixtures/exception.pyi]

0 comments on commit e20042f

Please sign in to comment.