<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.1//EN"
"http://www.w3.org/TR/xhtml11/DTD/xhtml11.dtd">
<html xmlns="http://www.w3.org/1999/xhtml">
<head><meta http-equiv="content-type" content="text/html; charset=utf-8" />
<title>[207661] trunk</title>
</head>
<body>

<style type="text/css"><!--
#msg dl.meta { border: 1px #006 solid; background: #369; padding: 6px; color: #fff; }
#msg dl.meta dt { float: left; width: 6em; font-weight: bold; }
#msg dt:after { content:':';}
#msg dl, #msg dt, #msg ul, #msg li, #header, #footer, #logmsg { font-family: verdana,arial,helvetica,sans-serif; font-size: 10pt;  }
#msg dl a { font-weight: bold}
#msg dl a:link    { color:#fc3; }
#msg dl a:active  { color:#ff0; }
#msg dl a:visited { color:#cc6; }
h3 { font-family: verdana,arial,helvetica,sans-serif; font-size: 10pt; font-weight: bold; }
#msg pre { overflow: auto; background: #ffc; border: 1px #fa0 solid; padding: 6px; }
#logmsg { background: #ffc; border: 1px #fa0 solid; padding: 1em 1em 0 1em; }
#logmsg p, #logmsg pre, #logmsg blockquote { margin: 0 0 1em 0; }
#logmsg p, #logmsg li, #logmsg dt, #logmsg dd { line-height: 14pt; }
#logmsg h1, #logmsg h2, #logmsg h3, #logmsg h4, #logmsg h5, #logmsg h6 { margin: .5em 0; }
#logmsg h1:first-child, #logmsg h2:first-child, #logmsg h3:first-child, #logmsg h4:first-child, #logmsg h5:first-child, #logmsg h6:first-child { margin-top: 0; }
#logmsg ul, #logmsg ol { padding: 0; list-style-position: inside; margin: 0 0 0 1em; }
#logmsg ul { text-indent: -1em; padding-left: 1em; }#logmsg ol { text-indent: -1.5em; padding-left: 1.5em; }
#logmsg > ul, #logmsg > ol { margin: 0 0 1em 0; }
#logmsg pre { background: #eee; padding: 1em; }
#logmsg blockquote { border: 1px solid #fa0; border-left-width: 10px; padding: 1em 1em 0 1em; background: white;}
#logmsg dl { margin: 0; }
#logmsg dt { font-weight: bold; }
#logmsg dd { margin: 0; padding: 0 0 0.5em 0; }
#logmsg dd:before { content:'\00bb';}
#logmsg table { border-spacing: 0px; border-collapse: collapse; border-top: 4px solid #fa0; border-bottom: 1px solid #fa0; background: #fff; }
#logmsg table th { text-align: left; font-weight: normal; padding: 0.2em 0.5em; border-top: 1px dotted #fa0; }
#logmsg table td { text-align: right; border-top: 1px dotted #fa0; padding: 0.2em 0.5em; }
#logmsg table thead th { text-align: center; border-bottom: 1px solid #fa0; }
#logmsg table th.Corner { text-align: left; }
#logmsg hr { border: none 0; border-top: 2px dashed #fa0; height: 1px; }
#header, #footer { color: #fff; background: #636; border: 1px #300 solid; padding: 6px; }
#patch { width: 100%; }
#patch h4 {font-family: verdana,arial,helvetica,sans-serif;font-size:10pt;padding:8px;background:#369;color:#fff;margin:0;}
#patch .propset h4, #patch .binary h4 {margin:0;}
#patch pre {padding:0;line-height:1.2em;margin:0;}
#patch .diff {width:100%;background:#eee;padding: 0 0 10px 0;overflow:auto;}
#patch .propset .diff, #patch .binary .diff  {padding:10px 0;}
#patch span {display:block;padding:0 10px;}
#patch .modfile, #patch .addfile, #patch .delfile, #patch .propset, #patch .binary, #patch .copfile {border:1px solid #ccc;margin:10px 0;}
#patch ins {background:#dfd;text-decoration:none;display:block;padding:0 10px;}
#patch del {background:#fdd;text-decoration:none;display:block;padding:0 10px;}
#patch .lines, .info {color:#888;background:#fff;}
--></style>
<div id="msg">
<dl class="meta">
<dt>Revision</dt> <dd><a href="http://trac.webkit.org/projects/webkit/changeset/207661">207661</a></dd>
<dt>Author</dt> <dd>jer.noble@apple.com</dd>
<dt>Date</dt> <dd>2016-10-21 01:03:22 -0700 (Fri, 21 Oct 2016)</dd>
</dl>

<h3>Log Message</h3>
<pre>CRASH in SourceBuffer::sourceBufferPrivateDidReceiveSample + 2169
https://bugs.webkit.org/show_bug.cgi?id=163735

Reviewed by Eric Carlson.

Source/WebCore:

Test: media/media-source/media-source-sample-wrong-track-id.html

When SourceBuffer receives a sample in sourceBufferPrivateDidReceiveSample() containing
a trackID not previously seen in an initialization segment, it creates a default TrackBuffer
object to contain that track's samples. One of the fields in TrackBuffer, description, is
normally filled out when an initialization segment is received, but with this default
TrackBuffer, it's still null when it's checked later in sourceBufferPrivateDidReceiveSample().

Rather than adding a null-check on trackBuffer.description, drop any sample that has a
trackID which was not present during a previous initialization segment.

* Modules/mediasource/SourceBuffer.cpp:
(WebCore::SourceBuffer::sourceBufferPrivateDidReceiveSample):

LayoutTests:

* media/media-source/media-source-sample-wrong-track-id-expected.txt: Added.
* media/media-source/media-source-sample-wrong-track-id.html: Added.</pre>

<h3>Modified Paths</h3>
<ul>
<li><a href="#trunkLayoutTestsChangeLog">trunk/LayoutTests/ChangeLog</a></li>
<li><a href="#trunkSourceWebCoreChangeLog">trunk/Source/WebCore/ChangeLog</a></li>
<li><a href="#trunkSourceWebCoreModulesmediasourceSourceBuffercpp">trunk/Source/WebCore/Modules/mediasource/SourceBuffer.cpp</a></li>
</ul>

<h3>Added Paths</h3>
<ul>
<li><a href="#trunkLayoutTestsmediamediasourcemediasourcesamplewrongtrackidexpectedtxt">trunk/LayoutTests/media/media-source/media-source-sample-wrong-track-id-expected.txt</a></li>
<li><a href="#trunkLayoutTestsmediamediasourcemediasourcesamplewrongtrackidhtml">trunk/LayoutTests/media/media-source/media-source-sample-wrong-track-id.html</a></li>
</ul>

</div>
<div id="patch">
<h3>Diff</h3>
<a id="trunkLayoutTestsChangeLog"></a>
<div class="modfile"><h4>Modified: trunk/LayoutTests/ChangeLog (207660 => 207661)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/LayoutTests/ChangeLog        2016-10-21 06:08:59 UTC (rev 207660)
+++ trunk/LayoutTests/ChangeLog        2016-10-21 08:03:22 UTC (rev 207661)
</span><span class="lines">@@ -1,3 +1,13 @@
</span><ins>+2016-10-21  Jer Noble  &lt;jer.noble@apple.com&gt;
+
+        CRASH in SourceBuffer::sourceBufferPrivateDidReceiveSample + 2169
+        https://bugs.webkit.org/show_bug.cgi?id=163735
+
+        Reviewed by Eric Carlson.
+
+        * media/media-source/media-source-sample-wrong-track-id-expected.txt: Added.
+        * media/media-source/media-source-sample-wrong-track-id.html: Added.
+
</ins><span class="cx"> 2016-10-20  Zan Dobersek  &lt;zdobersek@igalia.com&gt;
</span><span class="cx"> 
</span><span class="cx">         Import W3C EME tests
</span></span></pre></div>
<a id="trunkLayoutTestsmediamediasourcemediasourcesamplewrongtrackidexpectedtxt"></a>
<div class="addfile"><h4>Added: trunk/LayoutTests/media/media-source/media-source-sample-wrong-track-id-expected.txt (0 => 207661)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/LayoutTests/media/media-source/media-source-sample-wrong-track-id-expected.txt                                (rev 0)
+++ trunk/LayoutTests/media/media-source/media-source-sample-wrong-track-id-expected.txt        2016-10-21 08:03:22 UTC (rev 207661)
</span><span class="lines">@@ -0,0 +1,9 @@
</span><ins>+
+RUN(video.src = URL.createObjectURL(source))
+EVENT(sourceopen)
+RUN(sourceBuffer = source.addSourceBuffer(&quot;video/mock; codecs=mock&quot;))
+Append a set of invalid, overlapping samples. Should not crash.
+RUN(sourceBuffer.appendBuffer(mediaSegment))
+EVENT(updateend)
+END OF TEST
+
</ins></span></pre></div>
<a id="trunkLayoutTestsmediamediasourcemediasourcesamplewrongtrackidhtml"></a>
<div class="addfile"><h4>Added: trunk/LayoutTests/media/media-source/media-source-sample-wrong-track-id.html (0 => 207661)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/LayoutTests/media/media-source/media-source-sample-wrong-track-id.html                                (rev 0)
+++ trunk/LayoutTests/media/media-source/media-source-sample-wrong-track-id.html        2016-10-21 08:03:22 UTC (rev 207661)
</span><span class="lines">@@ -0,0 +1,40 @@
</span><ins>+&lt;!DOCTYPE html&gt;
+&lt;html&gt;
+&lt;head&gt;
+    &lt;title&gt;media-source-sample-wrong-track-id&lt;/title&gt;
+    &lt;script src=&quot;mock-media-source.js&quot;&gt;&lt;/script&gt;
+    &lt;script src=&quot;../video-test.js&quot;&gt;&lt;/script&gt;
+    &lt;script&gt;
+    var source;
+    var sourceBuffer;
+    var initSegment;
+    var mediaSegment;
+
+    if (window.internals)
+        internals.initializeMockMediaSource();
+
+    function runTest() {
+        findMediaElement();
+
+        source = new MediaSource();
+        waitForEventOn(source, 'sourceopen', sourceOpen, false, true);
+        run('video.src = URL.createObjectURL(source)');
+    }
+
+    function sourceOpen() {
+        run('sourceBuffer = source.addSourceBuffer(&quot;video/mock; codecs=mock&quot;)');
+        waitForEventOn(sourceBuffer, 'updateend', endTest);
+        consoleWrite('Append a set of invalid, overlapping samples. Should not crash.')
+        mediaSegment = concatenateSamples([
+            makeAInit(2, [makeATrack(1, 'mock', TRACK_KIND.AUDIO)]), 
+            makeASample(1, 1, 1, 2, SAMPLE_FLAG.SYNC, 0),
+            makeASample(1, 0, 2, 2, SAMPLE_FLAG.SYNC, 0),
+        ]);
+        run('sourceBuffer.appendBuffer(mediaSegment)');
+    }
+    &lt;/script&gt;
+&lt;/head&gt;
+&lt;body onload=&quot;runTest()&quot;&gt;
+    &lt;video&gt;&lt;/video&gt;
+&lt;/body&gt;
+&lt;/html&gt;
</ins></span></pre></div>
<a id="trunkSourceWebCoreChangeLog"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/ChangeLog (207660 => 207661)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/ChangeLog        2016-10-21 06:08:59 UTC (rev 207660)
+++ trunk/Source/WebCore/ChangeLog        2016-10-21 08:03:22 UTC (rev 207661)
</span><span class="lines">@@ -1,3 +1,24 @@
</span><ins>+2016-10-21  Jer Noble  &lt;jer.noble@apple.com&gt;
+
+        CRASH in SourceBuffer::sourceBufferPrivateDidReceiveSample + 2169
+        https://bugs.webkit.org/show_bug.cgi?id=163735
+
+        Reviewed by Eric Carlson.
+
+        Test: media/media-source/media-source-sample-wrong-track-id.html
+
+        When SourceBuffer receives a sample in sourceBufferPrivateDidReceiveSample() containing
+        a trackID not previously seen in an initialization segment, it creates a default TrackBuffer
+        object to contain that track's samples. One of the fields in TrackBuffer, description, is
+        normally filled out when an initialization segment is received, but with this default
+        TrackBuffer, it's still null when it's checked later in sourceBufferPrivateDidReceiveSample().
+
+        Rather than adding a null-check on trackBuffer.description, drop any sample that has a 
+        trackID which was not present during a previous initialization segment.
+
+        * Modules/mediasource/SourceBuffer.cpp:
+        (WebCore::SourceBuffer::sourceBufferPrivateDidReceiveSample):
+
</ins><span class="cx"> 2016-10-20  Carlos Garcia Campos  &lt;cgarcia@igalia.com&gt;
</span><span class="cx"> 
</span><span class="cx">         [GTK] Configures but fails to link with ENABLE_OPENGL=OFF
</span></span></pre></div>
<a id="trunkSourceWebCoreModulesmediasourceSourceBuffercpp"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/Modules/mediasource/SourceBuffer.cpp (207660 => 207661)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/Modules/mediasource/SourceBuffer.cpp        2016-10-21 06:08:59 UTC (rev 207660)
+++ trunk/Source/WebCore/Modules/mediasource/SourceBuffer.cpp        2016-10-21 08:03:22 UTC (rev 207661)
</span><span class="lines">@@ -1396,8 +1396,12 @@
</span><span class="cx">         // 1.5 Let track buffer equal the track buffer that the coded frame will be added to.
</span><span class="cx">         AtomicString trackID = sample.trackID();
</span><span class="cx">         auto it = m_trackBufferMap.find(trackID);
</span><del>-        if (it == m_trackBufferMap.end())
-            it = m_trackBufferMap.add(trackID, TrackBuffer()).iterator;
</del><ins>+        if (it == m_trackBufferMap.end()) {
+            // The client managed to append a sample with a trackID not present in the initialization
+            // segment. This would be a good place to post an message to the developer console.
+            didDropSample();
+            return;
+        }
</ins><span class="cx">         TrackBuffer&amp; trackBuffer = it-&gt;value;
</span><span class="cx"> 
</span><span class="cx">         // 1.6 ↳ If last decode timestamp for track buffer is set and decode timestamp is less than last
</span></span></pre>
</div>
</div>

</body>
</html>