Bug 919979 - Crash when calling WebrtcVideoConduit::SendVideoFrame() with very small resolution. r=derf
authorShian-Yow Wu <swu@mozilla.com>
Wed, 04 Dec 2013 13:34:59 +0800
changeset 174425 ee8b8fa121d0761fa2a651fd574a468bd1cc5796
parent 174424 96d025fe7fb42fa46b8bdf45845082807063531c
child 174426 b3b9d66e27d56570620e09ea6bdc6b93a065b47a
push id445
push userffxbld
push dateMon, 10 Mar 2014 22:05:19 +0000
treeherdermozilla-release@dc38b741b04e [default view] [failures only]
perfherder[talos] [build metrics] [platform microbench] (compared to previous push)
reviewersderf
bugs919979
milestone28.0a1
first release with
nightly linux32
nightly linux64
nightly mac
nightly win32
nightly win64
last release without
nightly linux32
nightly linux64
nightly mac
nightly win32
nightly win64
Bug 919979 - Crash when calling WebrtcVideoConduit::SendVideoFrame() with very small resolution. r=derf
media/webrtc/signaling/test/mediaconduit_unittests.cpp
media/webrtc/trunk/webrtc/modules/video_coding/codecs/vp8/vp8_impl.cc
--- a/media/webrtc/signaling/test/mediaconduit_unittests.cpp
+++ b/media/webrtc/signaling/test/mediaconduit_unittests.cpp
@@ -825,40 +825,47 @@ class TransportConduitTest : public ::te
     orig_width = 160;
     orig_height = 8;
     max_fs = 5;
     GetVideoResolutionWithMaxFs(orig_width, orig_height, max_fs, &width, &height);
     DumpMaxFs(orig_width, orig_height, max_fs, width, height);
     ASSERT_EQ(width, 80);
     ASSERT_EQ(height, 4);
 
+     // Extremely small width and height(see bug 919979).
+    cerr << "Test with extremely small width and height" << endl;
+    orig_width = 2;
+    orig_height = 2;
+    max_fs = 5;
+    GetVideoResolutionWithMaxFs(orig_width, orig_height, max_fs, &width, &height);
+    DumpMaxFs(orig_width, orig_height, max_fs, width, height);
+    ASSERT_EQ(width, 2);
+    ASSERT_EQ(height, 2);
+
     // Random values.
+    cerr << "Test with random values" << endl;
     for (int i = 0; i < 30; i++) {
+      cerr << ".";
       max_fs = rand() % 1000;
       orig_width = ((rand() % 2000) & ~1) + 2;
       orig_height = ((rand() % 2000) & ~1) + 2;
-      // Potential crash on small resolution, see bug 919979.
-      if (orig_width * orig_height <= 20) {
-        cerr << "Temporarily skip resolution " << orig_width << "x" <<
-             orig_height << endl;
-        continue;
-      }
 
       GetVideoResolutionWithMaxFs(orig_width, orig_height, max_fs,
                                   &width, &height);
       if (max_fs > 0 &&
           ceil(width / 16.) * ceil(height / 16.) > max_fs) {
         DumpMaxFs(orig_width, orig_height, max_fs, width, height);
         ADD_FAILURE();
       }
       if ((width & 1) || (height & 1)) {
         DumpMaxFs(orig_width, orig_height, max_fs, width, height);
         ADD_FAILURE();
       }
     }
+    cerr << endl;
  }
 
 private:
   //Audio Conduit Test Objects
   mozilla::RefPtr<mozilla::AudioSessionConduit> mAudioSession;
   mozilla::RefPtr<mozilla::AudioSessionConduit> mAudioSession2;
   mozilla::RefPtr<mozilla::TransportInterface> mAudioTransport;
   AudioSendAndReceive audioTester;
--- a/media/webrtc/trunk/webrtc/modules/video_coding/codecs/vp8/vp8_impl.cc
+++ b/media/webrtc/trunk/webrtc/modules/video_coding/codecs/vp8/vp8_impl.cc
@@ -166,17 +166,19 @@ int VP8EncoderImpl::InitEncode(const Vid
                          .Create(num_temporal_layers, rand());
   // random start 16 bits is enough.
   picture_id_ = static_cast<uint16_t>(rand()) & 0x7FFF;
 
   // allocate memory for encoded image
   if (encoded_image_._buffer != NULL) {
     delete [] encoded_image_._buffer;
   }
-  encoded_image_._size = CalcBufferSize(kI420, codec_.width, codec_.height);
+  // Reserve 100 extra bytes for overhead at small resolutions.
+  encoded_image_._size = CalcBufferSize(kI420, codec_.width, codec_.height)
+                         + 100;
   encoded_image_._buffer = new uint8_t[encoded_image_._size];
   encoded_image_._completeFrame = true;
 
   // Creating a wrapper to the image - setting image data to NULL. Actual
   // pointer will be set in encode. Setting align to 1, as it is meaningless
   // (actual memory is not allocated).
   raw_ = vpx_img_wrap(NULL, IMG_FMT_I420, codec_.width, codec_.height,
                       1, NULL);