summaryrefslogtreecommitdiffstats
path: root/chrome
diff options
context:
space:
mode:
authorstuartmorgan@chromium.org <stuartmorgan@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98>2010-05-13 19:54:57 +0000
committerstuartmorgan@chromium.org <stuartmorgan@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98>2010-05-13 19:54:57 +0000
commit270b9088890d22620d7f8791687fa3ddabe5d1a6 (patch)
treef78448a4d7b23c7ae64a9b99038215ce5f5c7db0 /chrome
parent28ed3b4d95b376634e1ef88a9299f5d2a2a9153a (diff)
downloadchromium_src-270b9088890d22620d7f8791687fa3ddabe5d1a6.zip
chromium_src-270b9088890d22620d7f8791687fa3ddabe5d1a6.tar.gz
chromium_src-270b9088890d22620d7f8791687fa3ddabe5d1a6.tar.bz2
Switch plugin backing store to local memory on non-Windows platforms
TransportDIB has non-trivial overhead on the Mac, and the backing store is never shared with any other process, so it's better to use local memory. Windows is excluded because PlatformCanvas requires a DIB on Windows. BUG=42858 TEST=Windowless plugins should continue to draw. Review URL: http://codereview.chromium.org/1873001 git-svn-id: svn://svn.chromium.org/chrome/trunk/src@47180 0039d316-1c4b-4281-b951-d872f2087c98
Diffstat (limited to 'chrome')
-rw-r--r--chrome/renderer/webplugin_delegate_proxy.cc61
-rw-r--r--chrome/renderer/webplugin_delegate_proxy.h15
2 files changed, 56 insertions, 20 deletions
diff --git a/chrome/renderer/webplugin_delegate_proxy.cc b/chrome/renderer/webplugin_delegate_proxy.cc
index fe5291e..a545b03 100644
--- a/chrome/renderer/webplugin_delegate_proxy.cc
+++ b/chrome/renderer/webplugin_delegate_proxy.cc
@@ -191,8 +191,7 @@ WebPluginDelegateProxy::~WebPluginDelegateProxy() {
ReleaseTransportDIB(iterator->second.get());
}
- // Ask the browser to release the "live" TransportDIB objects.
- ReleaseTransportDIB(backing_store_.get());
+ // Ask the browser to release the "live" TransportDIB object.
ReleaseTransportDIB(transport_store_.get());
DCHECK(!background_store_.get());
#endif
@@ -569,10 +568,15 @@ void WebPluginDelegateProxy::UpdateGeometry(const gfx::Rect& window_rect,
// asynchronously.
ResetWindowlessBitmaps();
if (!window_rect.IsEmpty()) {
- if (!CreateBitmap(&backing_store_, &backing_store_canvas_) ||
- !CreateBitmap(&transport_store_, &transport_store_canvas_) ||
+ if (!CreateSharedBitmap(&transport_store_, &transport_store_canvas_) ||
+#if defined(OS_WIN)
+ !CreateSharedBitmap(&backing_store_, &backing_store_canvas_) ||
+#else
+ !CreateLocalBitmap(&backing_store_, &backing_store_canvas_) ||
+#endif
(needs_background_store &&
- !CreateBitmap(&background_store_, &background_store_canvas_))) {
+ !CreateSharedBitmap(&background_store_,
+ &background_store_canvas_))) {
DCHECK(false);
ResetWindowlessBitmaps();
return;
@@ -617,7 +621,6 @@ void WebPluginDelegateProxy::UpdateGeometry(const gfx::Rect& window_rect,
void WebPluginDelegateProxy::ResetWindowlessBitmaps() {
#if defined(OS_MACOSX)
- ReleaseTransportDIB(backing_store_.get());
DCHECK(!background_store_.get());
// The Mac TransportDIB implementation uses base::SharedMemory, which
// cannot be disposed of if an in-flight UpdateGeometry message refers to
@@ -642,7 +645,11 @@ void WebPluginDelegateProxy::ResetWindowlessBitmaps() {
transport_store_.reset();
background_store_.reset();
#endif
+#if defined(OS_WIN)
backing_store_.reset();
+#else
+ backing_store_.resize(0);
+#endif
backing_store_canvas_.reset();
transport_store_canvas_.reset();
@@ -650,13 +657,30 @@ void WebPluginDelegateProxy::ResetWindowlessBitmaps() {
backing_store_painted_ = gfx::Rect();
}
-bool WebPluginDelegateProxy::CreateBitmap(
+static size_t BitmapSizeForPluginRect(const gfx::Rect& plugin_rect) {
+ const size_t stride =
+ skia::PlatformCanvas::StrideForWidth(plugin_rect.width());
+ return stride * plugin_rect.height();
+}
+
+#if !defined(OS_WIN)
+bool WebPluginDelegateProxy::CreateLocalBitmap(
+ std::vector<uint8>* memory,
+ scoped_ptr<skia::PlatformCanvas>* canvas) {
+ const size_t size = BitmapSizeForPluginRect(plugin_rect_);
+ memory->resize(size);
+ if (memory->size() != size)
+ return false;
+ canvas->reset(new skia::PlatformCanvas(
+ plugin_rect_.width(), plugin_rect_.height(), true, &((*memory)[0])));
+ return true;
+}
+#endif
+
+bool WebPluginDelegateProxy::CreateSharedBitmap(
scoped_ptr<TransportDIB>* memory,
scoped_ptr<skia::PlatformCanvas>* canvas) {
- int width = plugin_rect_.width();
- int height = plugin_rect_.height();
- const size_t stride = skia::PlatformCanvas::StrideForWidth(width);
- const size_t size = stride * height;
+ const size_t size = BitmapSizeForPluginRect(plugin_rect_);
#if defined(OS_POSIX) && !defined(OS_MACOSX)
memory->reset(TransportDIB::Create(size, 0));
if (!memory->get())
@@ -674,7 +698,8 @@ bool WebPluginDelegateProxy::CreateBitmap(
static uint32 sequence_number = 0;
memory->reset(TransportDIB::Create(size, sequence_number++));
#endif
- canvas->reset((*memory)->GetPlatformCanvas(width, height));
+ canvas->reset((*memory)->GetPlatformCanvas(plugin_rect_.width(),
+ plugin_rect_.height()));
return true;
}
@@ -1299,12 +1324,13 @@ void WebPluginDelegateProxy::CopyFromTransportToBacking(const gfx::Rect& rect) {
const size_t stride =
skia::PlatformCanvas::StrideForWidth(plugin_rect_.width());
const size_t chunk_size = 4 * rect.width();
- char* source_data = static_cast<char*>(transport_store_->memory()) +
- rect.y() * stride + 4 * rect.x();
+ uint8* source_data = static_cast<uint8*>(transport_store_->memory()) +
+ rect.y() * stride + 4 * rect.x();
// The two bitmaps are flipped relative to each other.
int dest_starting_row = plugin_rect_.height() - rect.y() - 1;
- char* target_data = static_cast<char*>(backing_store_->memory()) +
- dest_starting_row * stride + 4 * rect.x();
+ DCHECK(backing_store_.size() > 0);
+ uint8* target_data = &(backing_store_[0]) + dest_starting_row * stride +
+ 4 * rect.x();
for (int row = 0; row < rect.height(); ++row) {
memcpy(target_data, source_data, chunk_size);
source_data += stride;
@@ -1464,8 +1490,7 @@ void WebPluginDelegateProxy::OnUpdateGeometry_ACK(int ack_key) {
// Now that the ACK has been received, the TransportDIB that was used
// prior to the UpdateGeometry message now being acknowledged is known to
- // be no longer needed. Release it, and take the stale entry out of the
- // map.;
+ // be no longer needed. Release it, and take the stale entry out of the map.
ReleaseTransportDIB(iterator->second.get());
old_transport_dibs_.erase(iterator);
diff --git a/chrome/renderer/webplugin_delegate_proxy.h b/chrome/renderer/webplugin_delegate_proxy.h
index b12183b..59bfce2 100644
--- a/chrome/renderer/webplugin_delegate_proxy.h
+++ b/chrome/renderer/webplugin_delegate_proxy.h
@@ -183,9 +183,16 @@ class WebPluginDelegateProxy
// Clears the shared memory section and canvases used for windowless plugins.
void ResetWindowlessBitmaps();
+#if !defined(OS_WIN)
+ // Creates a process-local memory section and canvas. PlatformCanvas on
+ // Windows only works with a DIB, not arbitrary memory.
+ bool CreateLocalBitmap(std::vector<uint8>* memory,
+ scoped_ptr<skia::PlatformCanvas>* canvas);
+#endif
+
// Creates a shared memory section and canvas.
- bool CreateBitmap(scoped_ptr<TransportDIB>* memory,
- scoped_ptr<skia::PlatformCanvas>* canvas);
+ bool CreateSharedBitmap(scoped_ptr<TransportDIB>* memory,
+ scoped_ptr<skia::PlatformCanvas>* canvas);
// Called for cleanup during plugin destruction. Normally right before the
// plugin window gets destroyed, or when the plugin has crashed (at which
@@ -240,7 +247,11 @@ class WebPluginDelegateProxy
// store when we get an invalidate from it. The background bitmap is used
// for transparent plugins, as they need the backgroud data during painting.
bool transparent_;
+#if defined(OS_WIN)
scoped_ptr<TransportDIB> backing_store_;
+#else
+ std::vector<uint8> backing_store_;
+#endif
scoped_ptr<skia::PlatformCanvas> backing_store_canvas_;
scoped_ptr<TransportDIB> transport_store_;
scoped_ptr<skia::PlatformCanvas> transport_store_canvas_;