Skip to content

Commit a58ae14

Browse files
committed
Don't prevent checking for curl_init() initialization issues (false return)
1 parent a65f7f8 commit a58ae14

File tree

5 files changed

+51
-32
lines changed

5 files changed

+51
-32
lines changed

src/Type/Php/CurlInitReturnTypeExtension.php

Lines changed: 5 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -15,6 +15,7 @@
1515
use PHPStan\Type\StringType;
1616
use PHPStan\Type\Type;
1717
use PHPStan\Type\TypeCombinator;
18+
use PHPStan\Type\TypeUtils;
1819
use PHPStan\Type\UnionType;
1920
use function array_map;
2021
use function count;
@@ -48,7 +49,10 @@ public function getTypeFromFunctionCall(
4849
$args = $functionCall->getArgs();
4950
$argsCount = count($args);
5051
$returnType = ParametersAcceptorSelector::selectSingle($functionReflection->getVariants())->getReturnType();
51-
$notFalseReturnType = TypeCombinator::remove($returnType, new ConstantBooleanType(false));
52+
// curl_init() will return false if it fails to allocate memory or if initialization fails in general.
53+
// The default assumption is that a user doesn't need or want to be concerned about these issues,
54+
// but nothing should prevent checking for them anyway.
55+
$notFalseReturnType = TypeUtils::toBenevolentUnion($returnType);
5256
if ($argsCount === 0) {
5357
return $notFalseReturnType;
5458
}

tests/PHPStan/Analyser/AnalyserIntegrationTest.php

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1437,6 +1437,12 @@ public function testBug11511(): void
14371437
$this->assertSame('Access to an undefined property object::$bar.', $errors[0]->getMessage());
14381438
}
14391439

1440+
public function testBug11640(): void
1441+
{
1442+
$errors = $this->runAnalyse(__DIR__ . '/data/bug-11640.php');
1443+
$this->assertNoErrors($errors);
1444+
}
1445+
14401446
/**
14411447
* @param string[]|null $allAnalysedFiles
14421448
* @return Error[]
Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,9 @@
1+
<?php declare(strict_types = 1);
2+
3+
namespace Bug11640;
4+
5+
$ch = curl_init('https://example.com');
6+
7+
if (!$ch) {
8+
9+
}

tests/PHPStan/Type/Php/data/curl-init-php-7.php

Lines changed: 14 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -5,58 +5,58 @@
55
use function PHPStan\Testing\assertType;
66

77
function (string $unknownString) {
8-
assertType('resource', curl_init());
9-
assertType('resource', curl_init('https://phpstan.org'));
8+
assertType('(resource|false)', curl_init());
9+
assertType('(resource|false)', curl_init('https://phpstan.org'));
1010
assertType('resource|false', curl_init($unknownString));
11-
assertType('resource', curl_init(null));
12-
assertType('resource', curl_init(''));
11+
assertType('(resource|false)', curl_init(null));
12+
assertType('(resource|false)', curl_init(''));
1313
assertType('resource|false', curl_init(':'));
1414
assertType('resource|false', curl_init('file://host/text.txt'));
1515
assertType('resource|false', curl_init('FIle://host/text.txt'));
16-
assertType('resource', curl_init('host/text.txt'));
16+
assertType('(resource|false)', curl_init('host/text.txt'));
1717
assertType('false', curl_init("\0"));
1818
assertType('false', curl_init("https://phpstan.org\0"));
1919

2020
$url = 'https://phpstan.org';
2121
if (rand(0,1)) $url = null;
22-
assertType('resource', curl_init($url));
22+
assertType('(resource|false)', curl_init($url));
2323

2424
$url = 'https://phpstan.org';
2525
if (rand(0,1)) $url = 'https://phpstan.org/try';
26-
assertType('resource', curl_init($url));
26+
assertType('(resource|false)', curl_init($url));
2727

2828
$url = 'https://phpstan.org';
2929
if (rand(0,1)) $url = "\0";
30-
assertType('resource|false', curl_init($url));
30+
assertType('(resource|false)', curl_init($url));
3131

3232
$url = 'https://phpstan.org';
3333
if (rand(0,1)) $url = "https://phpstan.org\0";
34-
assertType('resource|false', curl_init($url));
34+
assertType('(resource|false)', curl_init($url));
3535

3636
$url = 'https://phpstan.org';
3737
if (rand(0,1)) $url = $unknownString;
3838
assertType('resource|false', curl_init($url));
3939

4040
$url = 'https://phpstan.org';
4141
if (rand(0,1)) $url = ':';
42-
assertType('resource|false', curl_init($url));
42+
assertType('(resource|false)', curl_init($url));
4343

4444
$url = 'https://phpstan.org';
4545
if (rand(0,1)) $url = 'file://host/text.txt';
46-
assertType('resource|false', curl_init($url));
46+
assertType('(resource|false)', curl_init($url));
4747

4848
$url = 'https://phpstan.org';
4949
if (rand(0,1)) $url = 'FIle://host/text.txt';
50-
assertType('resource|false', curl_init($url));
50+
assertType('(resource|false)', curl_init($url));
5151

5252
$url = 'https://phpstan.org';
5353
if (rand(0,1)) $url = 'host/text.txt';
54-
assertType('resource', curl_init($url));
54+
assertType('(resource|false)', curl_init($url));
5555

5656
$url = 'https://phpstan.org';
5757
if (rand(0,1)) $url = 'file://host/text.txt';
5858
if (rand(0,1)) $url = null;
59-
assertType('resource|false', curl_init($url));
59+
assertType('(resource|false)', curl_init($url));
6060

6161
$url = 'https://phpstan.org';
6262
if (rand(0,1)) $url = null;

tests/PHPStan/Type/Php/data/curl-init-php-8.php

Lines changed: 17 additions & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -5,33 +5,33 @@
55
use function PHPStan\Testing\assertType;
66

77
function (string $unknownString) {
8-
assertType('CurlHandle', curl_init());
9-
assertType('CurlHandle', curl_init('https://phpstan.org'));
8+
assertType('(CurlHandle|false)', curl_init());
9+
assertType('(CurlHandle|false)', curl_init('https://phpstan.org'));
1010
assertType('CurlHandle|false', curl_init($unknownString));
11-
assertType('CurlHandle', curl_init(null));
12-
assertType('CurlHandle', curl_init(''));
13-
assertType('CurlHandle', curl_init(':'));
14-
assertType('CurlHandle', curl_init('file://host/text.txt'));
15-
assertType('CurlHandle', curl_init('FIle://host/text.txt'));
16-
assertType('CurlHandle', curl_init('host/text.txt'));
11+
assertType('(CurlHandle|false)', curl_init(null));
12+
assertType('(CurlHandle|false)', curl_init(''));
13+
assertType('(CurlHandle|false)', curl_init(':'));
14+
assertType('(CurlHandle|false)', curl_init('file://host/text.txt'));
15+
assertType('(CurlHandle|false)', curl_init('FIle://host/text.txt'));
16+
assertType('(CurlHandle|false)', curl_init('host/text.txt'));
1717
assertType('*NEVER*', curl_init("\0"));
1818
assertType('*NEVER*', curl_init("https://phpstan.org\0"));
1919

2020
$url = 'https://phpstan.org';
2121
if (rand(0,1)) $url = null;
22-
assertType('CurlHandle', curl_init($url));
22+
assertType('(CurlHandle|false)', curl_init($url));
2323

2424
$url = 'https://phpstan.org';
2525
if (rand(0,1)) $url = 'https://phpstan.org/try';
26-
assertType('CurlHandle', curl_init($url));
26+
assertType('(CurlHandle|false)', curl_init($url));
2727

2828
$url = 'https://phpstan.org';
2929
if (rand(0,1)) $url = "\0";
30-
assertType('CurlHandle', curl_init($url));
30+
assertType('(CurlHandle|false)', curl_init($url));
3131

3232
$url = 'https://phpstan.org';
3333
if (rand(0,1)) $url = "https://phpstan.org\0";
34-
assertType('CurlHandle', curl_init($url));
34+
assertType('(CurlHandle|false)', curl_init($url));
3535

3636
$url = 'https://phpstan.org';
3737
if (rand(0,1)) $url = $unknownString;
@@ -43,24 +43,24 @@ function (string $unknownString) {
4343

4444
$url = 'https://phpstan.org';
4545
if (rand(0,1)) $url = ':';
46-
assertType('CurlHandle', curl_init($url));
46+
assertType('(CurlHandle|false)', curl_init($url));
4747

4848
$url = 'https://phpstan.org';
4949
if (rand(0,1)) $url = 'file://host/text.txt';
50-
assertType('CurlHandle', curl_init($url));
50+
assertType('(CurlHandle|false)', curl_init($url));
5151

5252
$url = 'https://phpstan.org';
5353
if (rand(0,1)) $url = 'FIle://host/text.txt';
54-
assertType('CurlHandle', curl_init($url));
54+
assertType('(CurlHandle|false)', curl_init($url));
5555

5656
$url = 'https://phpstan.org';
5757
if (rand(0,1)) $url = 'host/text.txt';
58-
assertType('CurlHandle', curl_init($url));
58+
assertType('(CurlHandle|false)', curl_init($url));
5959

6060
$url = 'https://phpstan.org';
6161
if (rand(0,1)) $url = 'file://host/text.txt';
6262
if (rand(0,1)) $url = null;
63-
assertType('CurlHandle', curl_init($url));
63+
assertType('(CurlHandle|false)', curl_init($url));
6464

6565
$url = 'https://phpstan.org';
6666
if (rand(0,1)) $url = null;

0 commit comments

Comments
 (0)