diff --git a/src/Type/Constant/ConstantArrayType.php b/src/Type/Constant/ConstantArrayType.php index db02994f2d..7bd109897e 100644 --- a/src/Type/Constant/ConstantArrayType.php +++ b/src/Type/Constant/ConstantArrayType.php @@ -618,6 +618,17 @@ public function hasOffsetValueType(Type $offsetType): TrinaryLogic return TrinaryLogic::extremeIdentity(...$results); } + if ($offsetType instanceof IntegerRangeType) { + $finiteTypes = $offsetType->getFiniteTypes(); + if ($finiteTypes !== []) { + $results = []; + foreach ($finiteTypes as $innerType) { + $results[] = $this->hasOffsetValueType($innerType); + } + + return TrinaryLogic::extremeIdentity(...$results); + } + } $result = TrinaryLogic::createNo(); foreach ($this->keyTypes as $i => $keyType) { diff --git a/tests/PHPStan/Rules/Arrays/NonexistentOffsetInArrayDimFetchRuleTest.php b/tests/PHPStan/Rules/Arrays/NonexistentOffsetInArrayDimFetchRuleTest.php index a833f3489a..b48e786af1 100644 --- a/tests/PHPStan/Rules/Arrays/NonexistentOffsetInArrayDimFetchRuleTest.php +++ b/tests/PHPStan/Rules/Arrays/NonexistentOffsetInArrayDimFetchRuleTest.php @@ -853,4 +853,15 @@ public function testReportPossiblyNonexistentArrayOffset(bool $reportPossiblyNon $this->analyse([__DIR__ . '/data/report-possibly-nonexistent-array-offset.php'], $errors); } + public function testBug10997(): void + { + $this->reportPossiblyNonexistentConstantArrayOffset = true; + $this->analyse([__DIR__ . '/data/bug-10997.php'], [ + [ + 'Offset int<0, 4> might not exist on array{1, 2, 3, 4}.', + 15, + ], + ]); + } + } diff --git a/tests/PHPStan/Rules/Arrays/data/bug-10997.php b/tests/PHPStan/Rules/Arrays/data/bug-10997.php new file mode 100644 index 0000000000..183004bdc2 --- /dev/null +++ b/tests/PHPStan/Rules/Arrays/data/bug-10997.php @@ -0,0 +1,17 @@ +