Bug 235174

Summary: Setting undefined to video.playbackRate causes Safari to crash
Product: WebKit Reporter: Takeshi Sone <takeshi.sone>
Component: MediaAssignee: Nobody <webkit-unassigned>
Status: RESOLVED FIXED    
Severity: Major CC: calvaris, cdumez, changseok, darin, eric.carlson, esprehn+autocc, ews-watchlist, glenn, gyuyoung.kim, hi, jean-yves.avenard, jer.noble, jonlee, kondapallykalyan, peng.liu6, philipj, sergio, webkit-bug-importer
Priority: P2 Keywords: InRadar
Version: Safari 15   
Hardware: iPhone / iPad   
OS: iOS 15   
URL: https://jsitor.com/NPeIszqH_
See Also: https://bugs.webkit.org/show_bug.cgi?id=228939
Attachments:
Description Flags
Crash Report
none
Patch
none
Chrome and Firefox snapshot
none
Patch
darin: review-
Patch take 3 none

Description Takeshi Sone 2022-01-13 00:41:14 PST
Created attachment 449030 [details]
Crash Report

1. Open this on iPhone or iPad:
https://jsitor.com/NPeIszqH_
2. Tap play button.
3. Safari crashes
Comment 1 Takeshi Sone 2022-01-13 00:43:38 PST
Created attachment 449031 [details]
Patch
Comment 2 Alexey Proskuryakov 2022-01-14 16:21:07 PST
Thank you for the patch!

Would you be willing to formally submit it for review as described at <https://webkit.org/contributing-code/> (with a ChangeLog, regression test, and marked as r?)?
Comment 3 Takeshi Sone 2022-01-16 19:06:15 PST
I tried to write automated test, but the behavior is inconsistent when the playbackRate is NaN, including on macOS, it's hard to clarify my patch fix the crash.

So I'm considering to add additional guards in HTMLMediaElement.
I'm not sure if it is better to just ignore NaN silently, or throw DOMException like Chrome and Firefox do.
What do you think?
Comment 4 Takeshi Sone 2022-01-16 19:08:10 PST
Created attachment 449301 [details]
Chrome and Firefox snapshot
Comment 5 Radar WebKit Bug Importer 2022-01-20 00:42:15 PST
<rdar://problem/87815745>
Comment 6 Takeshi Sone 2022-01-20 05:49:28 PST
Created attachment 449567 [details]
Patch

Added guards to ignore all non-finite value silently.
Added a test to confirm that fails without these patches and passes with patches.
Comment 7 Eric Carlson 2022-01-20 08:38:00 PST
Comment on attachment 449567 [details]
Patch

View in context: https://bugs.webkit.org/attachment.cgi?id=449567&action=review

> Source/WebCore/ChangeLog:5
> +	rdar://problem/87815745

Nit: You have a tab here.

> Source/WebCore/html/HTMLMediaElement.cpp:3498
> +    if (!isfinite(rate))
> +        return;
> +

The spec defines `defaultPlaybackRate` and `playbackRate` as `double`:

  attribute double defaultPlaybackRate;
  attribute double playbackRate;

but HTMLMediaElement.idl uses `unrestricted double`:

    attribute unrestricted double defaultPlaybackRate;
    attribute unrestricted double playbackRate;

I wonder if the changes to setDefaultPlaybackRate and setPlaybackRate would be unnecessary if this was fixed?
Comment 8 Chris Dumez 2022-01-20 08:48:28 PST
Comment on attachment 449567 [details]
Patch

View in context: https://bugs.webkit.org/attachment.cgi?id=449567&action=review

>> Source/WebCore/html/HTMLMediaElement.cpp:3498
>> +
> 
> The spec defines `defaultPlaybackRate` and `playbackRate` as `double`:
> 
>   attribute double defaultPlaybackRate;
>   attribute double playbackRate;
> 
> but HTMLMediaElement.idl uses `unrestricted double`:
> 
>     attribute unrestricted double defaultPlaybackRate;
>     attribute unrestricted double playbackRate;
> 
> I wonder if the changes to setDefaultPlaybackRate and setPlaybackRate would be unnecessary if this was fixed?

Eric is completely right. if our IDL matched the spec, it wouldn't be possible for the implementation to be called with infinite.
Comment 9 Darin Adler 2022-01-20 09:59:59 PST
Comment on attachment 449567 [details]
Patch

View in context: https://bugs.webkit.org/attachment.cgi?id=449567&action=review

>>> Source/WebCore/html/HTMLMediaElement.cpp:3498
>>> +
>> 
>> The spec defines `defaultPlaybackRate` and `playbackRate` as `double`:
>> 
>>   attribute double defaultPlaybackRate;
>>   attribute double playbackRate;
>> 
>> but HTMLMediaElement.idl uses `unrestricted double`:
>> 
>>     attribute unrestricted double defaultPlaybackRate;
>>     attribute unrestricted double playbackRate;
>> 
>> I wonder if the changes to setDefaultPlaybackRate and setPlaybackRate would be unnecessary if this was fixed?
> 
> Eric is completely right. if our IDL matched the spec, it wouldn't be possible for the implementation to be called with infinite.

Another way to put this is: The correct fix would be to change the .idl, not to change the .cpp file. I suspect we won’t need any changes to WebAVPlayerController.mm either. Please pursue that solution.

> Source/WebCore/platform/ios/WebAVPlayerController.mm:201
> +    /* NaN == NaN is false.
> +     * Catch that case to prevent infinite mutual recursion. */

Incorrect coding style. Please follow WebKit coding style, using "//" comments.
Comment 10 Takeshi Sone 2022-01-20 16:24:16 PST
Created attachment 449621 [details]
Patch take 3
Comment 11 Eric Carlson 2022-01-21 09:53:38 PST
Comment on attachment 449621 [details]
Patch take 3

Thank you for the fix!
Comment 12 Darin Adler 2022-01-21 10:44:43 PST
Comment on attachment 449621 [details]
Patch take 3

Surprised there is not an existing Web Platform Test that covers this. Would be nice to follow up and make sure this test case is covered there, not just in our WebKit project tests.
Comment 13 Jon Lee 2022-01-31 11:39:39 PST
any update on this?
Comment 14 Eric Carlson 2022-01-31 12:00:23 PST
Comment on attachment 449621 [details]
Patch take 3

(In reply to Jon Lee from comment #13)
> any update on this?

Lets land this and follow up about a WPT test.
Comment 15 EWS 2022-01-31 12:09:58 PST
Committed r288827 (246597@main): <https://commits.webkit.org/246597@main>

All reviewed patches have been landed. Closing bug and clearing flags on attachment 449621 [details].