Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Fix PHP8 crash due to insufficient isset test #670

Merged
merged 1 commit into from
Jan 31, 2021

Conversation

Alkarex
Copy link
Contributor

@Alkarex Alkarex commented Jan 29, 2021

#fix FreshRSS/FreshRSS#3401 (crash with PHP 8+)

ceil() crashes in PHP8+ in case of invalid input such as empty string.
intval() fixes the problem with almost identical behaviour than ceil() in PHP7- (except for floating point values)

#fix FreshRSS/FreshRSS#3401 (crash with PHP 8+)

Example with feed http://podcast.hr2.de/derTag/podcast.xml

<enclosure url="https://mp3podcasthr-a.akamaihd.net:443/mp3/podcast/derTag/derTag_20210129_87093232.mp3"
length="" type="audio/mpeg"/>

isset("") passes and then ceil("") crashes due to wrong type in PHP8+:

Uncaught TypeError: ceil(): Argument #1 ($num) must be of type
int|float, string given in ./SimplePie/SimplePie/Item.php:2871

{
$type = $this->sanitize($enclosure[0]['attribs']['']['type'], SIMPLEPIE_CONSTRUCT_TEXT);
}
if (isset($enclosure[0]['attribs']['']['length']))
if (!empty($enclosure[0]['attribs']['']['length']))
{
$length = ceil($enclosure[0]['attribs']['']['length']);
Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Here was the actual crash with PHP8+

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

It will still crash when invalid enclosure="foo" attribute is provided. Perhaps rather than checking emptiness, we should check if the value is a number.

Copy link
Contributor Author

@Alkarex Alkarex Jan 30, 2021

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@jtojnar Right, this should do the job 3000a70 without costing much, since ceil() needs first to cast to number anyway.

Copy link
Contributor Author

@Alkarex Alkarex Jan 30, 2021

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

intval() will cast any wrong value to 0, which is also the behaviour for ceil() in PHP7-

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

That should work (with slightly different semantics for numbers with decimal point) but now the ceil is not longer necessary.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Ah, right, on mobile now, but will simplify tomorrow

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Otherwise floatval() could be an option to keep ceil()

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

intval() is probably better, since length and fileSize are both expressed in bytes anyway

@Alkarex Alkarex changed the title Fix PHP8 crash due to ensufficient isset test Fix PHP8 crash due to insufficient isset test Jan 29, 2021
@Alkarex
Copy link
Contributor Author

Alkarex commented Jan 30, 2021

The Travis integration does not work, but I passed the tests manually, and they are unchanged before/after my PR:

composer test
> phpunit
PHPUnit 6.5.14 by Sebastian Bergmann and contributors.

..............R..............................................   61 / 1314 (  4%)
.............................................................  122 / 1314 (  9%)
.............................................................  183 / 1314 ( 13%)
.............................................................  244 / 1314 ( 18%)
.............................................................  305 / 1314 ( 23%)
.............................................................  366 / 1314 ( 27%)
.............................................................  427 / 1314 ( 32%)
.............................................................  488 / 1314 ( 37%)
.............................................................  549 / 1314 ( 41%)
.............................................................  610 / 1314 ( 46%)
.............................................................  671 / 1314 ( 51%)
.............................................................  732 / 1314 ( 55%)
.............................................................  793 / 1314 ( 60%)
.............................................................  854 / 1314 ( 64%)
.............................................................  915 / 1314 ( 69%)
.............................................................  976 / 1314 ( 74%)
............................................................. 1037 / 1314 ( 78%)
............................................................. 1098 / 1314 ( 83%)
............................................................. 1159 / 1314 ( 88%)
............................................................. 1220 / 1314 ( 92%)
............................................................. 1281 / 1314 ( 97%)
.................................                             1314 / 1314 (100%)

Time: 1.45 seconds, Memory: 18.00MB

There was 1 risky test:

1) EncodingTest::test_convert_UTF8_uconverter with data set #0 (Binary String: 0xfeff221e, '∞', 'UTF-16')
This test did not perform any assertions

OK, but incomplete, skipped, or risky tests!
Tests: 1314, Assertions: 1422, Risky: 1.

@mblaney
Copy link
Member

mblaney commented Jan 30, 2021

thanks for fixing the ceil bug @Alkarex, but I don't agree with a blanket change from isset to empty because you're saying "0" isn't a valid string.

@Alkarex
Copy link
Contributor Author

Alkarex commented Jan 30, 2021

@mblaney I kept isset() for href, so I did not change all of them. Which other attribute are you thinking about?

`ceil()` crashes in PHP8+ in case of invalid input such as empty string.
`intval()` fixes the problem with almost identical beahviour than
`ceil()` in PHP7- (except for flotting point values)

#fix FreshRSS/FreshRSS#3401 (crash with PHP
8+)

Example with feed http://podcast.hr2.de/derTag/podcast.xml

```xml
<enclosure

url="https://mp3podcasthr-a.akamaihd.net:443/mp3/podcast/derTag/derTag_20210129_87093232.mp3"
length="" type="audio/mpeg"/>
```

`isset("")` passes and then `ceil("")` crashes due to wrong type in
PHP8+:

```
Uncaught TypeError: ceil(): Argument #1 ($num) must be of type
int|float, string given in ./SimplePie/SimplePie/Item.php:2871
```
@Alkarex
Copy link
Contributor Author

Alkarex commented Jan 30, 2021

@mblaney I have reverted to address only the specific problem of ceil()

@mblaney mblaney merged commit 98ab0fe into simplepie:master Jan 31, 2021
Alkarex added a commit to FreshRSS/FreshRSS that referenced this pull request Jan 31, 2021
#fix #3401 (crash with PHP 8+)

`ceil()` crashes in PHP8+ in case of invalid input such as empty string.
`intval()` fixes the problem with almost identical behaviour than `ceil()` in PHP7- (except for floating point values)

#fix #3401 (crash with PHP 8+)

Example with feed http://podcast.hr2.de/derTag/podcast.xml

```xml
<enclosure url="https://mp3podcasthr-a.akamaihd.net:443/mp3/podcast/derTag/derTag_20210129_87093232.mp3"
length="" type="audio/mpeg"/>
```

`isset("")` passes and then `ceil("")` crashes due to wrong type in PHP8+:

```
Uncaught TypeError: ceil(): Argument #1 ($num) must be of type
int|float, string given in ./SimplePie/SimplePie/Item.php:2871
```

Upstream patch simplepie/simplepie#670
@Alkarex Alkarex deleted the PHP8-fix_isset branch February 5, 2021 14:46
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Projects
None yet
Development

Successfully merging this pull request may close these issues.

Uncaught TypeError: ceil(): Argument #1 ($num) must be of type int|float, string given
3 participants