summaryrefslogtreecommitdiffstats
path: root/webkit/glue/plugins
diff options
context:
space:
mode:
authorIain Merrick <husky@google.com>2010-11-01 12:19:54 +0000
committerIain Merrick <husky@google.com>2010-11-03 10:21:10 +0000
commit731df977c0511bca2206b5f333555b1205ff1f43 (patch)
tree0e750b949b3f00a1ac11fda25d3c2de512f2b465 /webkit/glue/plugins
parent5add15e10e7bb80512f2c597ca57221314abe577 (diff)
downloadexternal_chromium-731df977c0511bca2206b5f333555b1205ff1f43.zip
external_chromium-731df977c0511bca2206b5f333555b1205ff1f43.tar.gz
external_chromium-731df977c0511bca2206b5f333555b1205ff1f43.tar.bz2
Merge Chromium at r63472 : Initial merge by git.
Change-Id: Ifb9ee821af006a5f2211e81471be93ae440a1f5a
Diffstat (limited to 'webkit/glue/plugins')
-rw-r--r--webkit/glue/plugins/gtk_plugin_container_manager.cc4
-rw-r--r--webkit/glue/plugins/gtk_plugin_container_manager.h3
-rw-r--r--webkit/glue/plugins/pepper_audio.cc105
-rw-r--r--webkit/glue/plugins/pepper_audio.h13
-rw-r--r--webkit/glue/plugins/pepper_buffer.cc2
-rw-r--r--webkit/glue/plugins/pepper_char_set.cc4
-rw-r--r--webkit/glue/plugins/pepper_cursor_control.cc10
-rw-r--r--webkit/glue/plugins/pepper_dir_contents.h18
-rw-r--r--webkit/glue/plugins/pepper_error_util.cc1
-rw-r--r--webkit/glue/plugins/pepper_event_conversion.cc13
-rw-r--r--webkit/glue/plugins/pepper_file_callbacks.cc88
-rw-r--r--webkit/glue/plugins/pepper_file_callbacks.h53
-rw-r--r--webkit/glue/plugins/pepper_file_chooser.cc5
-rw-r--r--webkit/glue/plugins/pepper_file_io.cc13
-rw-r--r--webkit/glue/plugins/pepper_file_io.h1
-rw-r--r--webkit/glue/plugins/pepper_file_ref.cc249
-rw-r--r--webkit/glue/plugins/pepper_file_ref.h31
-rw-r--r--webkit/glue/plugins/pepper_file_system.cc251
-rw-r--r--webkit/glue/plugins/pepper_file_system.h22
-rw-r--r--webkit/glue/plugins/pepper_font.cc7
-rw-r--r--webkit/glue/plugins/pepper_graphics_2d.cc187
-rw-r--r--webkit/glue/plugins/pepper_graphics_2d.h6
-rw-r--r--webkit/glue/plugins/pepper_graphics_3d.cc6
-rw-r--r--webkit/glue/plugins/pepper_image_data.cc33
-rw-r--r--webkit/glue/plugins/pepper_image_data.h16
-rw-r--r--webkit/glue/plugins/pepper_plugin_delegate.h57
-rw-r--r--webkit/glue/plugins/pepper_plugin_instance.cc182
-rw-r--r--webkit/glue/plugins/pepper_plugin_instance.h26
-rw-r--r--webkit/glue/plugins/pepper_plugin_module.cc54
-rw-r--r--webkit/glue/plugins/pepper_plugin_module.h19
-rw-r--r--webkit/glue/plugins/pepper_plugin_object.cc26
-rw-r--r--webkit/glue/plugins/pepper_plugin_object.h12
-rw-r--r--webkit/glue/plugins/pepper_private.cc127
-rw-r--r--webkit/glue/plugins/pepper_private2.cc205
-rw-r--r--webkit/glue/plugins/pepper_private2.h19
-rw-r--r--webkit/glue/plugins/pepper_private2_linux.cc110
-rw-r--r--webkit/glue/plugins/pepper_resource.h106
-rw-r--r--webkit/glue/plugins/pepper_resource_tracker.cc75
-rw-r--r--webkit/glue/plugins/pepper_resource_tracker.h44
-rw-r--r--webkit/glue/plugins/pepper_scrollbar.cc8
-rw-r--r--webkit/glue/plugins/pepper_string.cc13
-rw-r--r--webkit/glue/plugins/pepper_string.h4
-rw-r--r--webkit/glue/plugins/pepper_url_loader.cc19
-rw-r--r--webkit/glue/plugins/pepper_url_loader.h5
-rw-r--r--webkit/glue/plugins/pepper_url_request_info.cc38
-rw-r--r--webkit/glue/plugins/pepper_url_request_info.h26
-rw-r--r--webkit/glue/plugins/pepper_url_response_info.cc4
-rw-r--r--webkit/glue/plugins/pepper_url_util.cc4
-rw-r--r--webkit/glue/plugins/pepper_var.cc98
-rw-r--r--webkit/glue/plugins/pepper_var.h6
-rw-r--r--webkit/glue/plugins/pepper_video_decoder.cc4
-rw-r--r--webkit/glue/plugins/pepper_webplugin_impl.cc28
-rw-r--r--webkit/glue/plugins/pepper_webplugin_impl.h10
-rw-r--r--webkit/glue/plugins/pepper_widget.cc2
-rw-r--r--webkit/glue/plugins/plugin_group.cc419
-rw-r--r--webkit/glue/plugins/plugin_group.h184
-rw-r--r--webkit/glue/plugins/plugin_group_unittest.cc181
-rw-r--r--webkit/glue/plugins/plugin_host.cc45
-rw-r--r--webkit/glue/plugins/plugin_lib.cc10
-rw-r--r--webkit/glue/plugins/plugin_lib_mac.mm19
-rw-r--r--webkit/glue/plugins/plugin_lib_posix.cc2
-rw-r--r--webkit/glue/plugins/plugin_list.cc311
-rw-r--r--webkit/glue/plugins/plugin_list.h84
-rw-r--r--webkit/glue/plugins/plugin_list_posix.cc2
-rw-r--r--webkit/glue/plugins/plugin_list_win.cc26
-rw-r--r--webkit/glue/plugins/plugin_web_event_converter_mac.h6
-rw-r--r--webkit/glue/plugins/plugin_web_event_converter_mac.mm28
-rw-r--r--webkit/glue/plugins/ppb_private.h56
-rw-r--r--webkit/glue/plugins/ppb_private2.h91
-rw-r--r--webkit/glue/plugins/ppp_private.h20
-rw-r--r--webkit/glue/plugins/webplugin.h20
-rw-r--r--webkit/glue/plugins/webplugin_accelerated_surface_mac.h43
-rw-r--r--webkit/glue/plugins/webplugin_delegate_impl.cc3
-rw-r--r--webkit/glue/plugins/webplugin_delegate_impl.h27
-rw-r--r--webkit/glue/plugins/webplugin_delegate_impl_gtk.cc10
-rw-r--r--webkit/glue/plugins/webplugin_delegate_impl_mac.mm87
-rw-r--r--webkit/glue/plugins/webplugin_delegate_impl_win.cc27
-rw-r--r--webkit/glue/plugins/webplugin_impl.cc9
-rw-r--r--webkit/glue/plugins/webplugin_impl.h9
-rw-r--r--webkit/glue/plugins/webplugininfo.cc44
-rw-r--r--webkit/glue/plugins/webplugininfo.h13
-rw-r--r--webkit/glue/plugins/webview_plugin.cc22
-rw-r--r--webkit/glue/plugins/webview_plugin.h10
83 files changed, 3244 insertions, 1036 deletions
diff --git a/webkit/glue/plugins/gtk_plugin_container_manager.cc b/webkit/glue/plugins/gtk_plugin_container_manager.cc
index f26b44c..2f82b24 100644
--- a/webkit/glue/plugins/gtk_plugin_container_manager.cc
+++ b/webkit/glue/plugins/gtk_plugin_container_manager.cc
@@ -11,6 +11,10 @@
#include "webkit/glue/plugins/gtk_plugin_container.h"
#include "webkit/glue/plugins/webplugin.h"
+GtkPluginContainerManager::GtkPluginContainerManager() : host_widget_(NULL) {}
+
+GtkPluginContainerManager::~GtkPluginContainerManager() {}
+
GtkWidget* GtkPluginContainerManager::CreatePluginContainer(
gfx::PluginWindowHandle id) {
DCHECK(host_widget_);
diff --git a/webkit/glue/plugins/gtk_plugin_container_manager.h b/webkit/glue/plugins/gtk_plugin_container_manager.h
index c33099d..7f7db8d 100644
--- a/webkit/glue/plugins/gtk_plugin_container_manager.h
+++ b/webkit/glue/plugins/gtk_plugin_container_manager.h
@@ -19,7 +19,8 @@ struct WebPluginGeometry;
// Helper class that creates and manages plugin containers (GtkSocket).
class GtkPluginContainerManager {
public:
- GtkPluginContainerManager() : host_widget_(NULL) { }
+ GtkPluginContainerManager();
+ ~GtkPluginContainerManager();
// Sets the widget that will host the plugin containers. Must be a GtkFixed.
void set_host_widget(GtkWidget *widget) { host_widget_ = widget; }
diff --git a/webkit/glue/plugins/pepper_audio.cc b/webkit/glue/plugins/pepper_audio.cc
index 3babc2f..5a76670 100644
--- a/webkit/glue/plugins/pepper_audio.cc
+++ b/webkit/glue/plugins/pepper_audio.cc
@@ -12,22 +12,52 @@ namespace pepper {
namespace {
-// PPB_AudioConfig functions
+// PPB_AudioConfig -------------------------------------------------------------
-PP_Resource CreateStereo16bit(PP_Module module_id, uint32_t sample_rate,
+uint32_t RecommendSampleFrameCount(uint32_t requested_sample_frame_count);
+
+PP_Resource CreateStereo16bit(PP_Module module_id,
+ PP_AudioSampleRate_Dev sample_rate,
uint32_t sample_frame_count) {
- PluginModule* module = PluginModule::FromPPModule(module_id);
+ PluginModule* module = ResourceTracker::Get()->GetModule(module_id);
if (!module)
return 0;
- scoped_refptr<AudioConfig> config(new AudioConfig(module, sample_rate,
+ // TODO(brettw): Currently we don't actually check what the hardware
+ // supports, so just allow sample rates of the "guaranteed working" ones.
+ if (sample_rate != PP_AUDIOSAMPLERATE_44100 &&
+ sample_rate != PP_AUDIOSAMPLERATE_48000)
+ return 0;
+
+ // TODO(brettw): Currently we don't actually query to get a value from the
+ // hardware, so just validate the range.
+ if (RecommendSampleFrameCount(sample_frame_count) != sample_frame_count)
+ return 0;
+
+ scoped_refptr<AudioConfig> config(new AudioConfig(module,
+ sample_rate,
sample_frame_count));
return config->GetReference();
}
-uint32_t GetSampleRate(PP_Resource config_id) {
+uint32_t RecommendSampleFrameCount(uint32_t requested_sample_frame_count) {
+ // TODO(brettw) Currently we don't actually query to get a value from the
+ // hardware, so we always return the input for in-range values.
+ if (requested_sample_frame_count < PP_AUDIOMINSAMPLEFRAMECOUNT)
+ return PP_AUDIOMINSAMPLEFRAMECOUNT;
+ if (requested_sample_frame_count > PP_AUDIOMAXSAMPLEFRAMECOUNT)
+ return PP_AUDIOMAXSAMPLEFRAMECOUNT;
+ return requested_sample_frame_count;
+}
+
+bool IsAudioConfig(PP_Resource resource) {
+ scoped_refptr<AudioConfig> config = Resource::GetAs<AudioConfig>(resource);
+ return !!config;
+}
+
+PP_AudioSampleRate_Dev GetSampleRate(PP_Resource config_id) {
scoped_refptr<AudioConfig> config = Resource::GetAs<AudioConfig>(config_id);
- return config ? config->sample_rate() : 0;
+ return config ? config->sample_rate() : PP_AUDIOSAMPLERATE_NONE;
}
uint32_t GetSampleFrameCount(PP_Resource config_id) {
@@ -35,11 +65,19 @@ uint32_t GetSampleFrameCount(PP_Resource config_id) {
return config ? config->sample_frame_count() : 0;
}
-// PPB_Audio functions
+const PPB_AudioConfig_Dev ppb_audioconfig = {
+ &CreateStereo16bit,
+ &RecommendSampleFrameCount,
+ &IsAudioConfig,
+ &GetSampleRate,
+ &GetSampleFrameCount
+};
+
+// PPB_Audio -------------------------------------------------------------------
PP_Resource Create(PP_Instance instance_id, PP_Resource config_id,
PPB_Audio_Callback callback, void* user_data) {
- PluginInstance* instance = PluginInstance::FromPPInstance(instance_id);
+ PluginInstance* instance = ResourceTracker::Get()->GetInstance(instance_id);
if (!instance)
return 0;
// TODO(neb): Require callback to be present for untrusted plugins.
@@ -49,6 +87,11 @@ PP_Resource Create(PP_Instance instance_id, PP_Resource config_id,
return audio->GetReference();
}
+bool IsAudio(PP_Resource resource) {
+ scoped_refptr<Audio> audio = Resource::GetAs<Audio>(resource);
+ return !!audio;
+}
+
PP_Resource GetCurrentConfiguration(PP_Resource audio_id) {
scoped_refptr<Audio> audio = Resource::GetAs<Audio>(audio_id);
return audio ? audio->GetCurrentConfiguration() : 0;
@@ -64,7 +107,15 @@ bool StopPlayback(PP_Resource audio_id) {
return audio ? audio->StopPlayback() : false;
}
-// PPB_AudioTrusted functions
+const PPB_Audio_Dev ppb_audio = {
+ &Create,
+ &IsAudio,
+ &GetCurrentConfiguration,
+ &StartPlayback,
+ &StopPlayback,
+};
+
+// PPB_AudioTrusted ------------------------------------------------------------
PP_Resource GetBuffer(PP_Resource audio_id) {
// TODO(neb): Implement me!
@@ -76,19 +127,6 @@ int GetOSDescriptor(PP_Resource audio_id) {
return -1;
}
-const PPB_AudioConfig_Dev ppb_audioconfig = {
- &CreateStereo16bit,
- &GetSampleRate,
- &GetSampleFrameCount
-};
-
-const PPB_Audio_Dev ppb_audio = {
- &Create,
- &GetCurrentConfiguration,
- &StartPlayback,
- &StopPlayback,
-};
-
const PPB_AudioTrusted_Dev ppb_audiotrusted = {
&GetBuffer,
&GetOSDescriptor
@@ -96,8 +134,11 @@ const PPB_AudioTrusted_Dev ppb_audiotrusted = {
} // namespace
-AudioConfig::AudioConfig(PluginModule* module, int32_t sample_rate,
- int32_t sample_frame_count)
+// AudioConfig -----------------------------------------------------------------
+
+AudioConfig::AudioConfig(PluginModule* module,
+ PP_AudioSampleRate_Dev sample_rate,
+ uint32_t sample_frame_count)
: Resource(module),
sample_rate_(sample_rate),
sample_frame_count_(sample_frame_count) {
@@ -107,10 +148,22 @@ const PPB_AudioConfig_Dev* AudioConfig::GetInterface() {
return &ppb_audioconfig;
}
+size_t AudioConfig::BufferSize() {
+ // TODO(audio): as more options become available, we'll need to
+ // have additional code here to correctly calculate the size in
+ // bytes of an audio buffer. For now, only support two channel
+ // int16_t sample buffers.
+ const int kChannels = 2;
+ const int kSizeOfSample = sizeof(int16_t);
+ return static_cast<size_t>(sample_frame_count_ * kSizeOfSample * kChannels);
+}
+
AudioConfig* AudioConfig::AsAudioConfig() {
return this;
}
+// Audio -----------------------------------------------------------------------
+
Audio::Audio(PluginModule* module)
: Resource(module),
playing_(false),
@@ -133,7 +186,6 @@ Audio::~Audio() {
// Shared memory destructor will unmap the memory automatically.
}
-
const PPB_Audio_Dev* Audio::GetInterface() {
return &ppb_audio;
}
@@ -211,6 +263,7 @@ void Audio::StreamCreated(base::SharedMemoryHandle shared_memory_handle,
void Audio::Run() {
int pending_data;
void* buffer = shared_memory_->memory();
+ size_t buffer_size_in_bytes = config_->BufferSize();
while (sizeof(pending_data) ==
socket_->Receive(&pending_data, sizeof(pending_data)) &&
@@ -218,7 +271,7 @@ void Audio::Run() {
// Exit the thread on pause.
if (pending_data < 0)
return;
- callback_(buffer, user_data_);
+ callback_(buffer, buffer_size_in_bytes, user_data_);
}
}
diff --git a/webkit/glue/plugins/pepper_audio.h b/webkit/glue/plugins/pepper_audio.h
index d9a9e86..196eac4 100644
--- a/webkit/glue/plugins/pepper_audio.h
+++ b/webkit/glue/plugins/pepper_audio.h
@@ -25,20 +25,21 @@ class PluginModule;
class AudioConfig : public Resource {
public:
- AudioConfig(PluginModule* module, int32_t sample_rate,
- int32_t sample_frame_count);
-
+ AudioConfig(PluginModule* module,
+ PP_AudioSampleRate_Dev sample_rate,
+ uint32_t sample_frame_count);
+ size_t BufferSize();
static const PPB_AudioConfig_Dev* GetInterface();
- uint32_t sample_rate() { return sample_rate_; }
+ PP_AudioSampleRate_Dev sample_rate() { return sample_rate_; }
uint32_t sample_frame_count() { return sample_frame_count_; }
private:
// Resource override.
virtual AudioConfig* AsAudioConfig();
- int sample_rate_;
- int sample_frame_count_;
+ PP_AudioSampleRate_Dev sample_rate_;
+ uint32_t sample_frame_count_;
};
class Audio : public Resource,
diff --git a/webkit/glue/plugins/pepper_buffer.cc b/webkit/glue/plugins/pepper_buffer.cc
index c3acef8..1b9097d 100644
--- a/webkit/glue/plugins/pepper_buffer.cc
+++ b/webkit/glue/plugins/pepper_buffer.cc
@@ -20,7 +20,7 @@ namespace pepper {
namespace {
PP_Resource Create(PP_Module module_id, int32_t size) {
- PluginModule* module = PluginModule::FromPPModule(module_id);
+ PluginModule* module = ResourceTracker::Get()->GetModule(module_id);
if (!module)
return 0;
diff --git a/webkit/glue/plugins/pepper_char_set.cc b/webkit/glue/plugins/pepper_char_set.cc
index 1e5fc0a..043de41 100644
--- a/webkit/glue/plugins/pepper_char_set.cc
+++ b/webkit/glue/plugins/pepper_char_set.cc
@@ -141,9 +141,9 @@ uint16_t* CharSetToUTF16(const char* input, uint32_t input_len,
}
PP_Var GetDefaultCharSet(PP_Module pp_module) {
- PluginModule* module = PluginModule::FromPPModule(pp_module);
+ PluginModule* module = ResourceTracker::Get()->GetModule(pp_module);
if (!module)
- return PP_MakeVoid();
+ return PP_MakeUndefined();
std::string encoding =
module->GetSomeInstance()->delegate()->GetDefaultEncoding();
diff --git a/webkit/glue/plugins/pepper_cursor_control.cc b/webkit/glue/plugins/pepper_cursor_control.cc
index de3c166..687aa76 100644
--- a/webkit/glue/plugins/pepper_cursor_control.cc
+++ b/webkit/glue/plugins/pepper_cursor_control.cc
@@ -22,7 +22,7 @@ bool SetCursor(PP_Instance instance_id,
PP_CursorType_Dev type,
PP_Resource custom_image_id,
const PP_Point* hot_spot) {
- PluginInstance* instance = PluginInstance::FromPPInstance(instance_id);
+ PluginInstance* instance = ResourceTracker::Get()->GetInstance(instance_id);
if (!instance)
return false;
@@ -38,7 +38,7 @@ bool SetCursor(PP_Instance instance_id,
}
bool LockCursor(PP_Instance instance_id) {
- PluginInstance* instance = PluginInstance::FromPPInstance(instance_id);
+ PluginInstance* instance = ResourceTracker::Get()->GetInstance(instance_id);
if (!instance)
return false;
@@ -47,7 +47,7 @@ bool LockCursor(PP_Instance instance_id) {
}
bool UnlockCursor(PP_Instance instance_id) {
- PluginInstance* instance = PluginInstance::FromPPInstance(instance_id);
+ PluginInstance* instance = ResourceTracker::Get()->GetInstance(instance_id);
if (!instance)
return false;
@@ -56,7 +56,7 @@ bool UnlockCursor(PP_Instance instance_id) {
}
bool HasCursorLock(PP_Instance instance_id) {
- PluginInstance* instance = PluginInstance::FromPPInstance(instance_id);
+ PluginInstance* instance = ResourceTracker::Get()->GetInstance(instance_id);
if (!instance)
return false;
@@ -65,7 +65,7 @@ bool HasCursorLock(PP_Instance instance_id) {
}
bool CanLockCursor(PP_Instance instance_id) {
- PluginInstance* instance = PluginInstance::FromPPInstance(instance_id);
+ PluginInstance* instance = ResourceTracker::Get()->GetInstance(instance_id);
if (!instance)
return false;
diff --git a/webkit/glue/plugins/pepper_dir_contents.h b/webkit/glue/plugins/pepper_dir_contents.h
new file mode 100644
index 0000000..661c577
--- /dev/null
+++ b/webkit/glue/plugins/pepper_dir_contents.h
@@ -0,0 +1,18 @@
+// Copyright (c) 2010 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef WEBKIT_GLUE_PLUGINS_PEPPER_DIR_CONTENTS_H_
+#define WEBKIT_GLUE_PLUGINS_PEPPER_DIR_CONTENTS_H_
+
+#include <vector>
+#include "base/file_path.h"
+
+struct PepperDirEntry {
+ FilePath name;
+ bool is_dir;
+};
+
+typedef std::vector<PepperDirEntry> PepperDirContents;
+
+#endif // WEBKIT_GLUE_PLUGINS_PEPPER_DIR_CONTENTS_H_
diff --git a/webkit/glue/plugins/pepper_error_util.cc b/webkit/glue/plugins/pepper_error_util.cc
index a1b5c06..895626a 100644
--- a/webkit/glue/plugins/pepper_error_util.cc
+++ b/webkit/glue/plugins/pepper_error_util.cc
@@ -17,6 +17,7 @@ int PlatformFileErrorToPepperError(base::PlatformFileError error_code) {
case base::PLATFORM_FILE_ERROR_NOT_FOUND:
return PP_ERROR_FILENOTFOUND;
case base::PLATFORM_FILE_ERROR_ACCESS_DENIED:
+ case base::PLATFORM_FILE_ERROR_SECURITY:
return PP_ERROR_NOACCESS;
case base::PLATFORM_FILE_ERROR_NO_MEMORY:
return PP_ERROR_NOMEMORY;
diff --git a/webkit/glue/plugins/pepper_event_conversion.cc b/webkit/glue/plugins/pepper_event_conversion.cc
index b88041e..5375f67 100644
--- a/webkit/glue/plugins/pepper_event_conversion.cc
+++ b/webkit/glue/plugins/pepper_event_conversion.cc
@@ -56,7 +56,10 @@ PP_InputEvent GetPPEventWithCommonFieldsAndType(
PP_InputEvent result;
memset(&result, 0, sizeof(PP_InputEvent));
result.type = ConvertEventTypes(web_event.type);
- result.time_stamp_seconds = web_event.timeStampSeconds;
+ // TODO(brettw) http://code.google.com/p/chromium/issues/detail?id=57448
+ // This should use a tick count rather than the wall clock time that WebKit
+ // uses.
+ result.time_stamp = web_event.timeStampSeconds;
return result;
}
@@ -159,7 +162,7 @@ WebKeyboardEvent* BuildKeyEvent(const PP_InputEvent& event) {
default:
NOTREACHED();
}
- key_event->timeStampSeconds = event.time_stamp_seconds;
+ key_event->timeStampSeconds = event.time_stamp;
key_event->modifiers = event.u.key.modifier;
key_event->windowsKeyCode = event.u.key.key_code;
return key_event;
@@ -168,7 +171,7 @@ WebKeyboardEvent* BuildKeyEvent(const PP_InputEvent& event) {
WebKeyboardEvent* BuildCharEvent(const PP_InputEvent& event) {
WebKeyboardEvent* key_event = new WebKeyboardEvent();
key_event->type = WebInputEvent::Char;
- key_event->timeStampSeconds = event.time_stamp_seconds;
+ key_event->timeStampSeconds = event.time_stamp;
key_event->modifiers = event.u.character.modifier;
// Make sure to not read beyond the buffer in case some bad code doesn't
@@ -209,7 +212,7 @@ WebMouseEvent* BuildMouseEvent(const PP_InputEvent& event) {
default:
NOTREACHED();
}
- mouse_event->timeStampSeconds = event.time_stamp_seconds;
+ mouse_event->timeStampSeconds = event.time_stamp;
mouse_event->modifiers = event.u.mouse.modifier;
mouse_event->button =
static_cast<WebMouseEvent::Button>(event.u.mouse.button);
@@ -222,7 +225,7 @@ WebMouseEvent* BuildMouseEvent(const PP_InputEvent& event) {
WebMouseWheelEvent* BuildMouseWheelEvent(const PP_InputEvent& event) {
WebMouseWheelEvent* mouse_wheel_event = new WebMouseWheelEvent();
mouse_wheel_event->type = WebInputEvent::MouseWheel;
- mouse_wheel_event->timeStampSeconds = event.time_stamp_seconds;
+ mouse_wheel_event->timeStampSeconds = event.time_stamp;
mouse_wheel_event->modifiers = event.u.wheel.modifier;
mouse_wheel_event->deltaX = event.u.wheel.delta_x;
mouse_wheel_event->deltaY = event.u.wheel.delta_y;
diff --git a/webkit/glue/plugins/pepper_file_callbacks.cc b/webkit/glue/plugins/pepper_file_callbacks.cc
new file mode 100644
index 0000000..3c52a0f
--- /dev/null
+++ b/webkit/glue/plugins/pepper_file_callbacks.cc
@@ -0,0 +1,88 @@
+// Copyright (c) 2010 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "webkit/glue/plugins/pepper_file_callbacks.h"
+
+#include "base/file_path.h"
+#include "base/logging.h"
+#include "third_party/ppapi/c/dev/ppb_file_system_dev.h"
+#include "third_party/ppapi/c/dev/pp_file_info_dev.h"
+#include "third_party/ppapi/c/pp_errors.h"
+#include "webkit/glue/plugins/pepper_error_util.h"
+#include "webkit/glue/plugins/pepper_file_system.h"
+#include "webkit/fileapi/file_system_types.h"
+
+namespace pepper {
+
+FileCallbacks::FileCallbacks(const base::WeakPtr<PluginModule>& module,
+ PP_CompletionCallback callback,
+ PP_FileInfo_Dev* info,
+ scoped_refptr<FileSystem> file_system)
+ : module_(module),
+ callback_(callback),
+ info_(info),
+ file_system_(file_system) {
+}
+
+void FileCallbacks::DidSucceed() {
+ if (!module_.get() || !callback_.func)
+ return;
+
+ PP_RunCompletionCallback(&callback_, PP_OK);
+}
+
+void FileCallbacks::DidReadMetadata(
+ const base::PlatformFileInfo& file_info) {
+ if (!module_.get() || !callback_.func)
+ return;
+
+ DCHECK(info_);
+ DCHECK(file_system_);
+ info_->size = file_info.size;
+ info_->creation_time = file_info.creation_time.ToDoubleT();
+ info_->last_access_time = file_info.last_accessed.ToDoubleT();
+ info_->last_modified_time = file_info.last_modified.ToDoubleT();
+ info_->system_type = file_system_->type();
+ if (file_info.is_directory)
+ info_->type = PP_FILETYPE_DIRECTORY;
+ else
+ info_->type = PP_FILETYPE_REGULAR;
+
+ PP_RunCompletionCallback(&callback_, PP_OK);
+}
+
+void FileCallbacks::DidReadDirectory(
+ const std::vector<base::file_util_proxy::Entry>&, bool) {
+ NOTREACHED();
+}
+
+void FileCallbacks::DidOpenFileSystem(const std::string&,
+ const FilePath& root_path) {
+ if (!module_.get() || !callback_.func)
+ return;
+
+ DCHECK(file_system_);
+ file_system_->set_root_path(root_path);
+ file_system_->set_opened(true);
+
+ PP_RunCompletionCallback(&callback_, PP_OK);
+}
+
+void FileCallbacks::DidFail(base::PlatformFileError error_code) {
+ RunCallback(error_code);
+}
+
+void FileCallbacks::DidWrite(int64 bytes, bool complete) {
+ NOTREACHED();
+}
+
+void FileCallbacks::RunCallback(base::PlatformFileError error_code) {
+ if (!module_.get() || !callback_.func)
+ return;
+
+ PP_RunCompletionCallback(
+ &callback_, pepper::PlatformFileErrorToPepperError(error_code));
+}
+
+} // namespace pepper
diff --git a/webkit/glue/plugins/pepper_file_callbacks.h b/webkit/glue/plugins/pepper_file_callbacks.h
new file mode 100644
index 0000000..407672e
--- /dev/null
+++ b/webkit/glue/plugins/pepper_file_callbacks.h
@@ -0,0 +1,53 @@
+// Copyright (c) 2010 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef WEBKIT_GLUE_PLUGINS_PEPPER_FILE_CALLBACKS_H_
+#define WEBKIT_GLUE_PLUGINS_PEPPER_FILE_CALLBACKS_H_
+
+#include "base/platform_file.h"
+#include "base/weak_ptr.h"
+#include "third_party/ppapi/c/pp_completion_callback.h"
+#include "webkit/fileapi/file_system_callback_dispatcher.h"
+
+struct PP_FileInfo_Dev;
+
+namespace base {
+class FilePath;
+}
+
+namespace pepper {
+
+class FileSystem;
+class PluginModule;
+
+// Instances of this class are deleted by FileSystemDispatcher.
+class FileCallbacks : public fileapi::FileSystemCallbackDispatcher {
+ public:
+ FileCallbacks(const base::WeakPtr<PluginModule>& module,
+ PP_CompletionCallback callback,
+ PP_FileInfo_Dev* info,
+ scoped_refptr<FileSystem> file_system);
+
+ // FileSystemCallbackDispatcher implementation.
+ virtual void DidSucceed();
+ virtual void DidReadMetadata(const base::PlatformFileInfo& file_info);
+ virtual void DidReadDirectory(
+ const std::vector<base::file_util_proxy::Entry>&, bool);
+ virtual void DidOpenFileSystem(const std::string&,
+ const FilePath& root_path);
+ virtual void DidFail(base::PlatformFileError error_code);
+ virtual void DidWrite(int64 bytes, bool complete);
+
+ private:
+ void RunCallback(base::PlatformFileError error_code);
+
+ base::WeakPtr<pepper::PluginModule> module_;
+ PP_CompletionCallback callback_;
+ PP_FileInfo_Dev* info_;
+ scoped_refptr<FileSystem> file_system_;
+};
+
+} // namespace pepper
+
+#endif // WEBKIT_GLUE_PLUGINS_PEPPER_FILE_CALLBACKS_H_
diff --git a/webkit/glue/plugins/pepper_file_chooser.cc b/webkit/glue/plugins/pepper_file_chooser.cc
index 138efd7..07524e9 100644
--- a/webkit/glue/plugins/pepper_file_chooser.cc
+++ b/webkit/glue/plugins/pepper_file_chooser.cc
@@ -33,7 +33,7 @@ namespace {
PP_Resource Create(PP_Instance instance_id,
const PP_FileChooserOptions_Dev* options) {
- PluginInstance* instance = PluginInstance::FromPPInstance(instance_id);
+ PluginInstance* instance = ResourceTracker::Get()->GetInstance(instance_id);
if (!instance)
return 0;
@@ -119,8 +119,7 @@ void FileChooser::StoreChosenFiles(const std::vector<std::string>& files) {
std::vector<std::string>::const_iterator end_it = files.end();
for (std::vector<std::string>::const_iterator it = files.begin();
it != end_it; it++)
- chosen_files_.push_back(
- new FileRef(module(), PP_FILESYSTEMTYPE_LOCALPERSISTENT, *it, ""));
+ chosen_files_.push_back(new FileRef(module(), FilePath().AppendASCII(*it)));
if (!completion_callback_.func)
return;
diff --git a/webkit/glue/plugins/pepper_file_io.cc b/webkit/glue/plugins/pepper_file_io.cc
index 9090f88..b979ac2 100644
--- a/webkit/glue/plugins/pepper_file_io.cc
+++ b/webkit/glue/plugins/pepper_file_io.cc
@@ -25,7 +25,7 @@ namespace pepper {
namespace {
PP_Resource Create(PP_Module module_id) {
- PluginModule* module = PluginModule::FromPPModule(module_id);
+ PluginModule* module = ResourceTracker::Get()->GetModule(module_id);
if (!module)
return 0;
@@ -225,12 +225,11 @@ int32_t FileIO::Open(FileRef* file_ref,
flags |= base::PLATFORM_FILE_WRITE;
flags |= base::PLATFORM_FILE_WRITE_ATTRIBUTES;
}
+
if (open_flags & PP_FILEOPENFLAG_TRUNCATE) {
- DCHECK(flags & PP_FILEOPENFLAG_WRITE);
+ DCHECK(open_flags & PP_FILEOPENFLAG_WRITE);
flags |= base::PLATFORM_FILE_TRUNCATE;
- }
-
- if (open_flags & PP_FILEOPENFLAG_CREATE) {
+ } else if (open_flags & PP_FILEOPENFLAG_CREATE) {
if (open_flags & PP_FILEOPENFLAG_EXCLUSIVE)
flags |= base::PLATFORM_FILE_CREATE;
else
@@ -238,9 +237,9 @@ int32_t FileIO::Open(FileRef* file_ref,
} else
flags |= base::PLATFORM_FILE_OPEN;
- file_system_type_ = file_ref->file_system_type();
+ file_system_type_ = file_ref->GetFileSystemType();
if (!delegate_->AsyncOpenFile(
- file_ref->system_path(), flags,
+ file_ref->GetSystemPath(), flags,
callback_factory_.NewCallback(&FileIO::AsyncOpenFileCallback)))
return PP_ERROR_FAILED;
diff --git a/webkit/glue/plugins/pepper_file_io.h b/webkit/glue/plugins/pepper_file_io.h
index bda8ed6..9fa24ba 100644
--- a/webkit/glue/plugins/pepper_file_io.h
+++ b/webkit/glue/plugins/pepper_file_io.h
@@ -16,7 +16,6 @@
#include "webkit/glue/plugins/pepper_resource.h"
struct PP_CompletionCallback;
-struct PP_FileInfo_Dev;
struct PPB_FileIO_Dev;
struct PPB_FileIOTrusted_Dev;
diff --git a/webkit/glue/plugins/pepper_file_ref.cc b/webkit/glue/plugins/pepper_file_ref.cc
index 7cb65a4..0a64678 100644
--- a/webkit/glue/plugins/pepper_file_ref.cc
+++ b/webkit/glue/plugins/pepper_file_ref.cc
@@ -4,12 +4,14 @@
#include "webkit/glue/plugins/pepper_file_ref.h"
-#include "base/base_paths.h"
-#include "base/path_service.h"
#include "base/string_util.h"
+#include "third_party/ppapi/c/pp_errors.h"
+#include "webkit/glue/plugins/pepper_file_callbacks.h"
+#include "webkit/glue/plugins/pepper_file_system.h"
+#include "webkit/glue/plugins/pepper_plugin_delegate.h"
#include "webkit/glue/plugins/pepper_plugin_instance.h"
+#include "webkit/glue/plugins/pepper_plugin_module.h"
#include "webkit/glue/plugins/pepper_var.h"
-#include "webkit/glue/plugins/pepper_resource_tracker.h"
namespace pepper {
@@ -34,35 +36,26 @@ void TrimTrailingSlash(std::string* path) {
path->erase(path->size() - 1, 1);
}
-PP_Resource CreateFileRef(PP_Instance instance_id,
- PP_FileSystemType_Dev fs_type,
- const char* path) {
- PluginInstance* instance = PluginInstance::FromPPInstance(instance_id);
- if (!instance)
+PP_Resource Create(PP_Resource file_system_id, const char* path) {
+ scoped_refptr<FileSystem> file_system(
+ Resource::GetAs<FileSystem>(file_system_id));
+ if (!file_system)
return 0;
- std::string origin; // TODO(darin): Extract from PluginInstance.
+ if (!file_system->instance())
+ return 0;
std::string validated_path(path);
if (!IsValidLocalPath(validated_path))
return 0;
TrimTrailingSlash(&validated_path);
- FileRef* file_ref = new FileRef(instance->module(),
- fs_type,
- validated_path,
- origin);
+ FileRef* file_ref = new FileRef(file_system->instance()->module(),
+ file_system,
+ validated_path);
return file_ref->GetReference();
}
-PP_Resource CreatePersistentFileRef(PP_Instance instance_id, const char* path) {
- return CreateFileRef(instance_id, PP_FILESYSTEMTYPE_LOCALPERSISTENT, path);
-}
-
-PP_Resource CreateTemporaryFileRef(PP_Instance instance_id, const char* path) {
- return CreateFileRef(instance_id, PP_FILESYSTEMTYPE_LOCALTEMPORARY, path);
-}
-
bool IsFileRef(PP_Resource resource) {
return !!Resource::GetAs<FileRef>(resource);
}
@@ -71,25 +64,25 @@ PP_FileSystemType_Dev GetFileSystemType(PP_Resource file_ref_id) {
scoped_refptr<FileRef> file_ref(Resource::GetAs<FileRef>(file_ref_id));
if (!file_ref)
return PP_FILESYSTEMTYPE_EXTERNAL;
- return file_ref->file_system_type();
+ return file_ref->GetFileSystemType();
}
PP_Var GetName(PP_Resource file_ref_id) {
scoped_refptr<FileRef> file_ref(Resource::GetAs<FileRef>(file_ref_id));
if (!file_ref)
- return PP_MakeVoid();
+ return PP_MakeUndefined();
return StringVar::StringToPPVar(file_ref->module(), file_ref->GetName());
}
PP_Var GetPath(PP_Resource file_ref_id) {
scoped_refptr<FileRef> file_ref(Resource::GetAs<FileRef>(file_ref_id));
if (!file_ref)
- return PP_MakeVoid();
+ return PP_MakeUndefined();
- if (file_ref->file_system_type() == PP_FILESYSTEMTYPE_EXTERNAL)
- return PP_MakeVoid();
+ if (file_ref->GetFileSystemType() == PP_FILESYSTEMTYPE_EXTERNAL)
+ return PP_MakeUndefined();
- return StringVar::StringToPPVar(file_ref->module(), file_ref->path());
+ return StringVar::StringToPPVar(file_ref->module(), file_ref->GetPath());
}
PP_Resource GetParent(PP_Resource file_ref_id) {
@@ -97,7 +90,7 @@ PP_Resource GetParent(PP_Resource file_ref_id) {
if (!file_ref)
return 0;
- if (file_ref->file_system_type() == PP_FILESYSTEMTYPE_EXTERNAL)
+ if (file_ref->GetFileSystemType() == PP_FILESYSTEMTYPE_EXTERNAL)
return 0;
scoped_refptr<FileRef> parent_ref(file_ref->GetParent());
@@ -107,34 +100,158 @@ PP_Resource GetParent(PP_Resource file_ref_id) {
return parent_ref->GetReference();
}
+int32_t MakeDirectory(PP_Resource directory_ref_id,
+ bool make_ancestors,
+ PP_CompletionCallback callback) {
+ scoped_refptr<FileRef> directory_ref(
+ Resource::GetAs<FileRef>(directory_ref_id));
+ if (!directory_ref)
+ return PP_ERROR_BADRESOURCE;
+
+ scoped_refptr<FileSystem> file_system = directory_ref->GetFileSystem();
+ if (!file_system || !file_system->opened() ||
+ (file_system->type() == PP_FILESYSTEMTYPE_EXTERNAL))
+ return PP_ERROR_NOACCESS;
+
+ PluginInstance* instance = file_system->instance();
+ if (!instance->delegate()->MakeDirectory(
+ directory_ref->GetSystemPath(), make_ancestors,
+ new FileCallbacks(instance->module()->AsWeakPtr(),
+ callback, NULL, NULL)))
+ return PP_ERROR_FAILED;
+
+ return PP_ERROR_WOULDBLOCK;
+}
+
+int32_t Query(PP_Resource file_ref_id,
+ PP_FileInfo_Dev* info,
+ PP_CompletionCallback callback) {
+ scoped_refptr<FileRef> file_ref(Resource::GetAs<FileRef>(file_ref_id));
+ if (!file_ref)
+ return PP_ERROR_BADRESOURCE;
+
+ scoped_refptr<FileSystem> file_system = file_ref->GetFileSystem();
+ if (!file_system || !file_system->opened() ||
+ (file_system->type() == PP_FILESYSTEMTYPE_EXTERNAL))
+ return PP_ERROR_NOACCESS;
+
+ PluginInstance* instance = file_system->instance();
+ if (!instance->delegate()->Query(
+ file_ref->GetSystemPath(),
+ new FileCallbacks(instance->module()->AsWeakPtr(),
+ callback, info, file_system)))
+ return PP_ERROR_FAILED;
+
+ return PP_ERROR_WOULDBLOCK;
+}
+
+int32_t Touch(PP_Resource file_ref_id,
+ PP_Time last_access_time,
+ PP_Time last_modified_time,
+ PP_CompletionCallback callback) {
+ scoped_refptr<FileRef> file_ref(Resource::GetAs<FileRef>(file_ref_id));
+ if (!file_ref)
+ return PP_ERROR_BADRESOURCE;
+
+ scoped_refptr<FileSystem> file_system = file_ref->GetFileSystem();
+ if (!file_system || !file_system->opened() ||
+ (file_system->type() == PP_FILESYSTEMTYPE_EXTERNAL))
+ return PP_ERROR_NOACCESS;
+
+ PluginInstance* instance = file_system->instance();
+ if (!instance->delegate()->Touch(
+ file_ref->GetSystemPath(), base::Time::FromDoubleT(last_access_time),
+ base::Time::FromDoubleT(last_modified_time),
+ new FileCallbacks(instance->module()->AsWeakPtr(),
+ callback, NULL, NULL)))
+ return PP_ERROR_FAILED;
+
+ return PP_ERROR_WOULDBLOCK;
+}
+
+int32_t Delete(PP_Resource file_ref_id,
+ PP_CompletionCallback callback) {
+ scoped_refptr<FileRef> file_ref(Resource::GetAs<FileRef>(file_ref_id));
+ if (!file_ref)
+ return PP_ERROR_BADRESOURCE;
+
+ scoped_refptr<FileSystem> file_system = file_ref->GetFileSystem();
+ if (!file_system || !file_system->opened() ||
+ (file_system->type() == PP_FILESYSTEMTYPE_EXTERNAL))
+ return PP_ERROR_NOACCESS;
+
+ PluginInstance* instance = file_system->instance();
+ if (!instance->delegate()->Delete(
+ file_ref->GetSystemPath(),
+ new FileCallbacks(instance->module()->AsWeakPtr(),
+ callback, NULL, NULL)))
+ return PP_ERROR_FAILED;
+
+ return PP_ERROR_WOULDBLOCK;
+}
+
+int32_t Rename(PP_Resource file_ref_id,
+ PP_Resource new_file_ref_id,
+ PP_CompletionCallback callback) {
+ scoped_refptr<FileRef> file_ref(Resource::GetAs<FileRef>(file_ref_id));
+ if (!file_ref)
+ return PP_ERROR_BADRESOURCE;
+
+ scoped_refptr<FileRef> new_file_ref(
+ Resource::GetAs<FileRef>(new_file_ref_id));
+ if (!new_file_ref)
+ return PP_ERROR_BADRESOURCE;
+
+ scoped_refptr<FileSystem> file_system = file_ref->GetFileSystem();
+ if (!file_system || !file_system->opened() ||
+ (file_system != new_file_ref->GetFileSystem()) ||
+ (file_system->type() == PP_FILESYSTEMTYPE_EXTERNAL))
+ return PP_ERROR_NOACCESS;
+
+ PluginInstance* instance = file_system->instance();
+ if (!instance->delegate()->Rename(
+ file_ref->GetSystemPath(), new_file_ref->GetSystemPath(),
+ new FileCallbacks(instance->module()->AsWeakPtr(),
+ callback, NULL, NULL)))
+ return PP_ERROR_FAILED;
+
+ return PP_ERROR_WOULDBLOCK;
+}
+
const PPB_FileRef_Dev ppb_fileref = {
- &CreatePersistentFileRef,
- &CreateTemporaryFileRef,
+ &Create,
&IsFileRef,
&GetFileSystemType,
&GetName,
&GetPath,
- &GetParent
+ &GetParent,
+ &MakeDirectory,
+ &Query,
+ &Touch,
+ &Delete,
+ &Rename
};
} // namespace
+FileRef::FileRef()
+ : Resource(NULL),
+ file_system_(NULL) {
+}
+
FileRef::FileRef(PluginModule* module,
- PP_FileSystemType_Dev file_system_type,
- const std::string& validated_path,
- const std::string& origin)
+ scoped_refptr<FileSystem> file_system,
+ const std::string& validated_path)
: Resource(module),
- fs_type_(file_system_type),
- path_(validated_path),
- origin_(origin) {
- // TODO(darin): Need to initialize system_path_.
+ file_system_(file_system),
+ virtual_path_(validated_path) {
}
FileRef::FileRef(PluginModule* module,
const FilePath& external_file_path)
: Resource(module),
- system_path_(external_file_path),
- fs_type_(PP_FILESYSTEMTYPE_EXTERNAL) {
+ file_system_(NULL),
+ system_path_(external_file_path) {
}
FileRef::~FileRef() {
@@ -146,48 +263,56 @@ const PPB_FileRef_Dev* FileRef::GetInterface() {
}
std::string FileRef::GetName() const {
- if (path_.size() == 1 && path_[0] == '/')
- return path_;
+ if (GetFileSystemType() == PP_FILESYSTEMTYPE_EXTERNAL)
+ return std::string();
+
+ if (virtual_path_.size() == 1 && virtual_path_[0] == '/')
+ return virtual_path_;
// There should always be a leading slash at least!
- size_t pos = path_.rfind('/');
+ size_t pos = virtual_path_.rfind('/');
DCHECK(pos != std::string::npos);
- return path_.substr(pos + 1);
+ return virtual_path_.substr(pos + 1);
}
scoped_refptr<FileRef> FileRef::GetParent() {
- if (path_.size() == 1 && path_[0] == '/')
- return this;
+ if (GetFileSystemType() == PP_FILESYSTEMTYPE_EXTERNAL)
+ return new FileRef();
// There should always be a leading slash at least!
- size_t pos = path_.rfind('/');
+ size_t pos = virtual_path_.rfind('/');
DCHECK(pos != std::string::npos);
// If the path is "/foo", then we want to include the slash.
if (pos == 0)
pos++;
- std::string parent_path = path_.substr(0, pos);
+ std::string parent_path = virtual_path_.substr(0, pos);
- FileRef* parent_ref = new FileRef(module(), fs_type_, parent_path, origin_);
+ FileRef* parent_ref = new FileRef(module(), file_system_, parent_path);
return parent_ref;
}
-// static
-FileRef* FileRef::GetInaccessibleFileRef(PluginModule* module) {
- FilePath inaccessible_path;
- if (!PathService::Get(base::FILE_MODULE, &inaccessible_path))
- return NULL;
- return new FileRef(module, inaccessible_path);
+scoped_refptr<FileSystem> FileRef::GetFileSystem() const {
+ return file_system_;
}
-// static
-FileRef* FileRef::GetNonexistentFileRef(PluginModule* module) {
- FilePath dir_module_path;
- if (!PathService::Get(base::DIR_MODULE, &dir_module_path))
- return NULL;
- return new FileRef(module, dir_module_path.Append(
- FILE_PATH_LITERAL("nonexistent_file")));
+PP_FileSystemType_Dev FileRef::GetFileSystemType() const {
+ if (!file_system_)
+ return PP_FILESYSTEMTYPE_EXTERNAL;
+
+ return file_system_->type();
+}
+
+std::string FileRef::GetPath() const {
+ return virtual_path_;
+}
+
+FilePath FileRef::GetSystemPath() const {
+ if (GetFileSystemType() == PP_FILESYSTEMTYPE_EXTERNAL)
+ return system_path_;
+
+ return file_system_->root_path().AppendASCII(virtual_path_);
}
} // namespace pepper
diff --git a/webkit/glue/plugins/pepper_file_ref.h b/webkit/glue/plugins/pepper_file_ref.h
index 0ab0e65..4dd8826 100644
--- a/webkit/glue/plugins/pepper_file_ref.h
+++ b/webkit/glue/plugins/pepper_file_ref.h
@@ -13,14 +13,16 @@
namespace pepper {
+class FileSystem;
+class PluginInstance;
class PluginModule;
class FileRef : public Resource {
public:
+ FileRef();
FileRef(PluginModule* module,
- PP_FileSystemType_Dev file_system_type,
- const std::string& validated_path,
- const std::string& origin);
+ scoped_refptr<FileSystem> file_system,
+ const std::string& validated_path);
FileRef(PluginModule* module,
const FilePath& external_file_path);
virtual ~FileRef();
@@ -36,28 +38,23 @@ class FileRef : public Resource {
std::string GetName() const;
scoped_refptr<FileRef> GetParent();
- PP_FileSystemType_Dev file_system_type() const { return fs_type_; }
+ // Returns the file system to which this FileRef belongs.
+ scoped_refptr<FileSystem> GetFileSystem() const;
+
+ // Returns the type of the file system to which this FileRef belongs.
+ PP_FileSystemType_Dev GetFileSystemType() const;
// Returns the virtual path (i.e., the path that the pepper plugin sees)
// corresponding to this file.
- const std::string& path() const { return path_; }
+ std::string GetPath() const;
// Returns the system path corresponding to this file.
- const FilePath& system_path() const { return system_path_; }
-
- // Returns a FileRef instance pointing to a file that should not be
- // accessible by the plugin. Should be used for testing only.
- static FileRef* GetInaccessibleFileRef(PluginModule* module);
-
- // Returns a FileRef instance pointing to a nonexistent file.
- // Should be used for testing only.
- static FileRef* GetNonexistentFileRef(PluginModule* module);
+ FilePath GetSystemPath() const;
private:
+ scoped_refptr<FileSystem> file_system_;
+ std::string virtual_path_; // UTF-8 encoded
FilePath system_path_;
- PP_FileSystemType_Dev fs_type_;
- std::string path_; // UTF-8 encoded.
- std::string origin_;
};
} // namespace pepper
diff --git a/webkit/glue/plugins/pepper_file_system.cc b/webkit/glue/plugins/pepper_file_system.cc
index 82a2fc8..21321a5 100644
--- a/webkit/glue/plugins/pepper_file_system.cc
+++ b/webkit/glue/plugins/pepper_file_system.cc
@@ -4,244 +4,79 @@
#include "webkit/glue/plugins/pepper_file_system.h"
-#include "base/logging.h"
#include "base/ref_counted.h"
-#include "base/weak_ptr.h"
#include "third_party/ppapi/c/dev/ppb_file_system_dev.h"
#include "third_party/ppapi/c/pp_completion_callback.h"
-#include "third_party/ppapi/c/pp_time.h"
-#include "webkit/fileapi/file_system_callback_dispatcher.h"
-#include "webkit/glue/plugins/pepper_resource.h"
-#include "webkit/glue/plugins/pepper_error_util.h"
-#include "webkit/glue/plugins/pepper_file_ref.h"
+#include "third_party/WebKit/WebKit/chromium/public/WebDocument.h"
+#include "third_party/WebKit/WebKit/chromium/public/WebElement.h"
+#include "third_party/WebKit/WebKit/chromium/public/WebFrame.h"
+#include "third_party/WebKit/WebKit/chromium/public/WebPluginContainer.h"
+#include "webkit/fileapi/file_system_types.h"
+#include "webkit/glue/plugins/pepper_file_callbacks.h"
#include "webkit/glue/plugins/pepper_plugin_delegate.h"
#include "webkit/glue/plugins/pepper_plugin_instance.h"
#include "webkit/glue/plugins/pepper_plugin_module.h"
#include "webkit/glue/plugins/pepper_resource.h"
+#include "webkit/glue/plugins/pepper_resource_tracker.h"
namespace pepper {
namespace {
-// Instances of this class are deleted when RunCallback() is called.
-class StatusCallback : public fileapi::FileSystemCallbackDispatcher {
- public:
- StatusCallback(base::WeakPtr<pepper::PluginModule> module,
- PP_CompletionCallback callback)
- : module_(module),
- callback_(callback) {
- }
-
- // FileSystemCallbackDispatcher implementation.
- virtual void DidSucceed() {
- RunCallback(base::PLATFORM_FILE_OK);
- }
-
- virtual void DidReadMetadata(const base::PlatformFileInfo&) {
- NOTREACHED();
- }
-
- virtual void DidReadDirectory(
- const std::vector<base::file_util_proxy::Entry>&, bool) {
- NOTREACHED();
- }
-
- virtual void DidOpenFileSystem(const std::string&, const FilePath&) {
- NOTREACHED();
- }
-
- virtual void DidFail(base::PlatformFileError error_code) {
- RunCallback(error_code);
- }
-
- private:
- void RunCallback(base::PlatformFileError error_code) {
- if (!module_.get() || !callback_.func)
- return;
-
- PP_RunCompletionCallback(
- &callback_, pepper::PlatformFileErrorToPepperError(error_code));
-
- delete this;
- }
-
- base::WeakPtr<pepper::PluginModule> module_;
- PP_CompletionCallback callback_;
-};
-
-// Instances of this class are deleted when RunCallback() is called.
-class QueryInfoCallback : public fileapi::FileSystemCallbackDispatcher {
- public:
- QueryInfoCallback(base::WeakPtr<pepper::PluginModule> module,
- PP_CompletionCallback callback,
- PP_FileInfo_Dev* info,
- PP_FileSystemType_Dev file_system_type)
- : module_(module),
- callback_(callback),
- info_(info),
- file_system_type_(file_system_type) {
- DCHECK(info_);
- }
-
- // FileSystemCallbackDispatcher implementation.
- virtual void DidSucceed() {
- NOTREACHED();
- }
-
- virtual void DidReadMetadata(const base::PlatformFileInfo& file_info) {
- RunCallback(base::PLATFORM_FILE_OK, file_info);
- }
-
- virtual void DidReadDirectory(
- const std::vector<base::file_util_proxy::Entry>&, bool) {
- NOTREACHED();
- }
-
- virtual void DidOpenFileSystem(const std::string&, const FilePath&) {
- NOTREACHED();
- }
-
- virtual void DidFail(base::PlatformFileError error_code) {
- RunCallback(error_code, base::PlatformFileInfo());
- }
-
- private:
- void RunCallback(base::PlatformFileError error_code,
- const base::PlatformFileInfo& file_info) {
- if (!module_.get() || !callback_.func)
- return;
-
- if (error_code == base::PLATFORM_FILE_OK) {
- info_->size = file_info.size;
- info_->creation_time = file_info.creation_time.ToDoubleT();
- info_->last_access_time = file_info.last_accessed.ToDoubleT();
- info_->last_modified_time = file_info.last_modified.ToDoubleT();
- info_->system_type = file_system_type_;
- if (file_info.is_directory)
- info_->type = PP_FILETYPE_DIRECTORY;
- else
- info_->type = PP_FILETYPE_REGULAR;
- }
- PP_RunCompletionCallback(
- &callback_, pepper::PlatformFileErrorToPepperError(error_code));
-
- delete this;
- }
-
- base::WeakPtr<pepper::PluginModule> module_;
- PP_CompletionCallback callback_;
- PP_FileInfo_Dev* info_;
- PP_FileSystemType_Dev file_system_type_;
-};
-
-int32_t MakeDirectory(PP_Resource directory_ref_id,
- bool make_ancestors,
- PP_CompletionCallback callback) {
- scoped_refptr<FileRef> directory_ref(
- Resource::GetAs<FileRef>(directory_ref_id));
- if (!directory_ref)
- return PP_ERROR_BADRESOURCE;
-
- if (directory_ref->file_system_type() == PP_FILESYSTEMTYPE_EXTERNAL)
- return PP_ERROR_FAILED;
-
- PluginModule* module = directory_ref->module();
- if (!module->GetSomeInstance()->delegate()->MakeDirectory(
- directory_ref->system_path(), make_ancestors,
- new StatusCallback(module->AsWeakPtr(), callback)))
- return PP_ERROR_FAILED;
+PP_Resource Create(PP_Instance instance, PP_FileSystemType_Dev type) {
+ PluginInstance* plugin_instance =
+ ResourceTracker::Get()->GetInstance(instance);
+ if (!plugin_instance)
+ return 0;
- return PP_ERROR_WOULDBLOCK;
+ FileSystem* file_system = new FileSystem(plugin_instance, type);
+ return file_system->GetReference();
}
-int32_t Query(PP_Resource file_ref_id,
- PP_FileInfo_Dev* info,
- PP_CompletionCallback callback) {
- scoped_refptr<FileRef> file_ref(Resource::GetAs<FileRef>(file_ref_id));
- if (!file_ref)
+int32_t Open(PP_Resource file_system_id,
+ int64 expected_size,
+ PP_CompletionCallback callback) {
+ scoped_refptr<FileSystem> file_system(
+ Resource::GetAs<FileSystem>(file_system_id));
+ if (!file_system)
return PP_ERROR_BADRESOURCE;
- PluginModule* module = file_ref->module();
- if (!module->GetSomeInstance()->delegate()->Query(
- file_ref->system_path(),
- new QueryInfoCallback(module->AsWeakPtr(), callback,
- info, file_ref->file_system_type())))
- return PP_ERROR_FAILED;
-
- return PP_ERROR_WOULDBLOCK;
-}
+ if (file_system->opened())
+ return PP_OK;
-int32_t Touch(PP_Resource file_ref_id,
- PP_Time last_access_time,
- PP_Time last_modified_time,
- PP_CompletionCallback callback) {
- scoped_refptr<FileRef> file_ref(Resource::GetAs<FileRef>(file_ref_id));
- if (!file_ref)
- return PP_ERROR_BADRESOURCE;
-
- PluginModule* module = file_ref->module();
- if (!module->GetSomeInstance()->delegate()->Touch(
- file_ref->system_path(), base::Time::FromDoubleT(last_access_time),
- base::Time::FromDoubleT(last_modified_time),
- new StatusCallback(module->AsWeakPtr(), callback)))
+ if ((file_system->type() != PP_FILESYSTEMTYPE_LOCALPERSISTENT) &&
+ (file_system->type() != PP_FILESYSTEMTYPE_LOCALTEMPORARY))
return PP_ERROR_FAILED;
- return PP_ERROR_WOULDBLOCK;
-}
-
-int32_t Delete(PP_Resource file_ref_id,
- PP_CompletionCallback callback) {
- scoped_refptr<FileRef> file_ref(Resource::GetAs<FileRef>(file_ref_id));
- if (!file_ref)
- return PP_ERROR_BADRESOURCE;
-
- if (file_ref->file_system_type() == PP_FILESYSTEMTYPE_EXTERNAL)
- return PP_ERROR_FAILED;
-
- PluginModule* module = file_ref->module();
- if (!module->GetSomeInstance()->delegate()->Delete(
- file_ref->system_path(),
- new StatusCallback(module->AsWeakPtr(), callback)))
- return PP_ERROR_FAILED;
-
- return PP_ERROR_WOULDBLOCK;
-}
-
-int32_t Rename(PP_Resource file_ref_id,
- PP_Resource new_file_ref_id,
- PP_CompletionCallback callback) {
- scoped_refptr<FileRef> file_ref(Resource::GetAs<FileRef>(file_ref_id));
- if (!file_ref)
- return PP_ERROR_BADRESOURCE;
-
- scoped_refptr<FileRef> new_file_ref(
- Resource::GetAs<FileRef>(new_file_ref_id));
- if (!new_file_ref)
- return PP_ERROR_BADRESOURCE;
-
- if ((file_ref->file_system_type() == PP_FILESYSTEMTYPE_EXTERNAL) ||
- (file_ref->file_system_type() != new_file_ref->file_system_type()))
- return PP_ERROR_FAILED;
-
- PluginModule* module = file_ref->module();
- if (!module->GetSomeInstance()->delegate()->Rename(
- file_ref->system_path(), new_file_ref->system_path(),
- new StatusCallback(module->AsWeakPtr(), callback)))
+ PluginInstance* instance = file_system->instance();
+ fileapi::FileSystemType file_system_type =
+ (file_system->type() == PP_FILESYSTEMTYPE_LOCALTEMPORARY ?
+ fileapi::kFileSystemTypeTemporary :
+ fileapi::kFileSystemTypePersistent);
+ if (!instance->delegate()->OpenFileSystem(
+ instance->container()->element().document().frame()->url(),
+ file_system_type, expected_size,
+ new FileCallbacks(instance->module()->AsWeakPtr(),
+ callback, NULL, file_system)))
return PP_ERROR_FAILED;
return PP_ERROR_WOULDBLOCK;
}
const PPB_FileSystem_Dev ppb_filesystem = {
- &MakeDirectory,
- &Query,
- &Touch,
- &Delete,
- &Rename
+ &Create,
+ &Open
};
} // namespace
+FileSystem::FileSystem(PluginInstance* instance, PP_FileSystemType_Dev type)
+ : Resource(instance->module()),
+ instance_(instance),
+ type_(type),
+ opened_(false) {
+}
+
const PPB_FileSystem_Dev* FileSystem::GetInterface() {
return &ppb_filesystem;
}
diff --git a/webkit/glue/plugins/pepper_file_system.h b/webkit/glue/plugins/pepper_file_system.h
index 1abfc52..f883299 100644
--- a/webkit/glue/plugins/pepper_file_system.h
+++ b/webkit/glue/plugins/pepper_file_system.h
@@ -6,19 +6,37 @@
#define WEBKIT_GLUE_PLUGINS_PEPPER_FILE_SYSTEM_H_
#include "base/basictypes.h"
+#include "base/file_path.h"
+#include "third_party/ppapi/c/dev/pp_file_info_dev.h"
+#include "webkit/glue/plugins/pepper_resource.h"
struct PPB_FileSystem_Dev;
namespace pepper {
-class FileSystem {
+class PluginInstance;
+
+class FileSystem : public Resource {
public:
// Returns a pointer to the interface implementing PPB_FileSystem that is
// exposed to the plugin.
static const PPB_FileSystem_Dev* GetInterface();
+ FileSystem(PluginInstance* instance, PP_FileSystemType_Dev type);
+ FileSystem* AsFileSystem() { return this; }
+
+ PluginInstance* instance() { return instance_; }
+ PP_FileSystemType_Dev type() { return type_; }
+ const FilePath& root_path() const { return root_path_; }
+ void set_root_path(const FilePath& root_path) { root_path_ = root_path; }
+ bool opened() const { return opened_; }
+ void set_opened(bool opened) { opened_ = opened; }
+
private:
- DISALLOW_IMPLICIT_CONSTRUCTORS(FileSystem);
+ PluginInstance* instance_;
+ PP_FileSystemType_Dev type_;
+ FilePath root_path_;
+ bool opened_;
};
} // namespace pepper
diff --git a/webkit/glue/plugins/pepper_font.cc b/webkit/glue/plugins/pepper_font.cc
index 82bf369..cad39f5 100644
--- a/webkit/glue/plugins/pepper_font.cc
+++ b/webkit/glue/plugins/pepper_font.cc
@@ -33,7 +33,8 @@ namespace {
bool IsPPFontDescriptionValid(const PP_FontDescription_Dev& desc) {
// Check validity of UTF-8.
- if (desc.face.type != PP_VARTYPE_STRING && desc.face.type != PP_VARTYPE_VOID)
+ if (desc.face.type != PP_VARTYPE_STRING &&
+ desc.face.type != PP_VARTYPE_UNDEFINED)
return false;
// Check enum ranges.
@@ -107,7 +108,7 @@ bool PPTextRunToWebTextRun(const PP_TextRun_Dev* run, WebTextRun* output) {
PP_Resource Create(PP_Module module_id,
const PP_FontDescription_Dev* description) {
- PluginModule* module = PluginModule::FromPPModule(module_id);
+ PluginModule* module = ResourceTracker::Get()->GetModule(module_id);
if (!module)
return 0;
@@ -198,7 +199,7 @@ const PPB_Font_Dev* Font::GetInterface() {
bool Font::Describe(PP_FontDescription_Dev* description,
PP_FontMetrics_Dev* metrics) {
- if (description->face.type != PP_VARTYPE_VOID)
+ if (description->face.type != PP_VARTYPE_UNDEFINED)
return false;
WebFontDescription web_desc = font_->fontDescription();
diff --git a/webkit/glue/plugins/pepper_graphics_2d.cc b/webkit/glue/plugins/pepper_graphics_2d.cc
index 5011f87..a75da85 100644
--- a/webkit/glue/plugins/pepper_graphics_2d.cc
+++ b/webkit/glue/plugins/pepper_graphics_2d.cc
@@ -25,7 +25,7 @@
#if defined(OS_MACOSX)
#include "base/mac_util.h"
-#include "base/scoped_cftyperef.h"
+#include "base/mac/scoped_cftyperef.h"
#endif
namespace pepper {
@@ -63,10 +63,57 @@ bool ValidateAndConvertRect(const PP_Rect* rect,
return true;
}
+// Converts BGRA <-> RGBA.
+void ConvertBetweenBGRAandRGBA(const uint32_t* input,
+ int pixel_length,
+ uint32_t* output) {
+ for (int i = 0; i < pixel_length; i++) {
+ const unsigned char* pixel_in =
+ reinterpret_cast<const unsigned char*>(&input[i]);
+ unsigned char* pixel_out = reinterpret_cast<unsigned char*>(&output[i]);
+ pixel_out[0] = pixel_in[2];
+ pixel_out[1] = pixel_in[1];
+ pixel_out[2] = pixel_in[0];
+ pixel_out[3] = pixel_in[3];
+ }
+}
+
+// Converts ImageData from PP_IMAGEDATAFORMAT_BGRA_PREMUL to
+// PP_IMAGEDATAFORMAT_RGBA_PREMUL, or reverse.
+void ConvertImageData(ImageData* src_image, const SkIRect& src_rect,
+ ImageData* dest_image, const SkRect& dest_rect) {
+ DCHECK(src_image->format() != dest_image->format());
+ DCHECK(ImageData::IsImageDataFormatSupported(src_image->format()));
+ DCHECK(ImageData::IsImageDataFormatSupported(dest_image->format()));
+
+ const SkBitmap* src_bitmap = src_image->GetMappedBitmap();
+ const SkBitmap* dest_bitmap = dest_image->GetMappedBitmap();
+ if (src_rect.width() == src_image->width() &&
+ dest_rect.width() == dest_image->width()) {
+ // Fast path if the full line needs to be converted.
+ ConvertBetweenBGRAandRGBA(
+ src_bitmap->getAddr32(static_cast<int>(src_rect.fLeft),
+ static_cast<int>(src_rect.fTop)),
+ src_rect.width() * src_rect.height(),
+ dest_bitmap->getAddr32(static_cast<int>(dest_rect.fLeft),
+ static_cast<int>(dest_rect.fTop)));
+ } else {
+ // Slow path where we convert line by line.
+ for (int y = 0; y < src_rect.height(); y++) {
+ ConvertBetweenBGRAandRGBA(
+ src_bitmap->getAddr32(static_cast<int>(src_rect.fLeft),
+ static_cast<int>(src_rect.fTop + y)),
+ src_rect.width(),
+ dest_bitmap->getAddr32(static_cast<int>(dest_rect.fLeft),
+ static_cast<int>(dest_rect.fTop + y)));
+ }
+ }
+}
+
PP_Resource Create(PP_Module module_id,
const PP_Size* size,
bool is_always_opaque) {
- PluginModule* module = PluginModule::FromPPModule(module_id);
+ PluginModule* module = ResourceTracker::Get()->GetModule(module_id);
if (!module)
return 0;
@@ -80,49 +127,46 @@ bool IsGraphics2D(PP_Resource resource) {
return !!Resource::GetAs<Graphics2D>(resource);
}
-bool Describe(PP_Resource device_context,
+bool Describe(PP_Resource graphics_2d,
PP_Size* size,
bool* is_always_opaque) {
scoped_refptr<Graphics2D> context(
- Resource::GetAs<Graphics2D>(device_context));
+ Resource::GetAs<Graphics2D>(graphics_2d));
if (!context)
return false;
return context->Describe(size, is_always_opaque);
}
-bool PaintImageData(PP_Resource device_context,
- PP_Resource image,
+void PaintImageData(PP_Resource graphics_2d,
+ PP_Resource image_data,
const PP_Point* top_left,
const PP_Rect* src_rect) {
scoped_refptr<Graphics2D> context(
- Resource::GetAs<Graphics2D>(device_context));
- if (!context)
- return false;
- return context->PaintImageData(image, top_left, src_rect);
+ Resource::GetAs<Graphics2D>(graphics_2d));
+ if (context)
+ context->PaintImageData(image_data, top_left, src_rect);
}
-bool Scroll(PP_Resource device_context,
+void Scroll(PP_Resource graphics_2d,
const PP_Rect* clip_rect,
const PP_Point* amount) {
scoped_refptr<Graphics2D> context(
- Resource::GetAs<Graphics2D>(device_context));
- if (!context)
- return false;
- return context->Scroll(clip_rect, amount);
+ Resource::GetAs<Graphics2D>(graphics_2d));
+ if (context)
+ context->Scroll(clip_rect, amount);
}
-bool ReplaceContents(PP_Resource device_context, PP_Resource image) {
+void ReplaceContents(PP_Resource graphics_2d, PP_Resource image_data) {
scoped_refptr<Graphics2D> context(
- Resource::GetAs<Graphics2D>(device_context));
- if (!context)
- return false;
- return context->ReplaceContents(image);
+ Resource::GetAs<Graphics2D>(graphics_2d));
+ if (context)
+ context->ReplaceContents(image_data);
}
-int32_t Flush(PP_Resource device_context,
+int32_t Flush(PP_Resource graphics_2d,
PP_CompletionCallback callback) {
scoped_refptr<Graphics2D> context(
- Resource::GetAs<Graphics2D>(device_context));
+ Resource::GetAs<Graphics2D>(graphics_2d));
if (!context)
return PP_ERROR_BADRESOURCE;
return context->Flush(callback);
@@ -189,8 +233,8 @@ const PPB_Graphics2D* Graphics2D::GetInterface() {
bool Graphics2D::Init(int width, int height, bool is_always_opaque) {
// The underlying ImageData will validate the dimensions.
image_data_ = new ImageData(module());
- if (!image_data_->Init(PP_IMAGEDATAFORMAT_BGRA_PREMUL, width, height, true) ||
- !image_data_->Map()) {
+ if (!image_data_->Init(ImageData::GetNativeImageDataFormat(), width, height,
+ true) || !image_data_->Map()) {
image_data_ = NULL;
return false;
}
@@ -205,22 +249,23 @@ bool Graphics2D::Describe(PP_Size* size, bool* is_always_opaque) {
return true;
}
-bool Graphics2D::PaintImageData(PP_Resource image,
+void Graphics2D::PaintImageData(PP_Resource image_data,
const PP_Point* top_left,
const PP_Rect* src_rect) {
if (!top_left)
- return false;
+ return;
- scoped_refptr<ImageData> image_resource(Resource::GetAs<ImageData>(image));
+ scoped_refptr<ImageData> image_resource(
+ Resource::GetAs<ImageData>(image_data));
if (!image_resource)
- return false;
+ return;
QueuedOperation operation(QueuedOperation::PAINT);
operation.paint_image = image_resource;
if (!ValidateAndConvertRect(src_rect, image_resource->width(),
image_resource->height(),
&operation.paint_src_rect))
- return false;
+ return;
// Validate the bitmap position using the previously-validated rect, there
// should be no painted area outside of the image.
@@ -229,25 +274,24 @@ bool Graphics2D::PaintImageData(PP_Resource image,
if (x64 + static_cast<int64>(operation.paint_src_rect.x()) < 0 ||
x64 + static_cast<int64>(operation.paint_src_rect.right()) >
image_data_->width())
- return false;
+ return;
if (y64 + static_cast<int64>(operation.paint_src_rect.y()) < 0 ||
y64 + static_cast<int64>(operation.paint_src_rect.bottom()) >
image_data_->height())
- return false;
+ return;
operation.paint_x = top_left->x;
operation.paint_y = top_left->y;
queued_operations_.push_back(operation);
- return true;
}
-bool Graphics2D::Scroll(const PP_Rect* clip_rect, const PP_Point* amount) {
+void Graphics2D::Scroll(const PP_Rect* clip_rect, const PP_Point* amount) {
QueuedOperation operation(QueuedOperation::SCROLL);
if (!ValidateAndConvertRect(clip_rect,
image_data_->width(),
image_data_->height(),
&operation.scroll_clip_rect))
- return false;
+ return;
// If we're being asked to scroll by more than the clip rect size, just
// ignore this scroll command and say it worked.
@@ -255,31 +299,29 @@ bool Graphics2D::Scroll(const PP_Rect* clip_rect, const PP_Point* amount) {
int32 dy = amount->y;
if (dx <= -image_data_->width() || dx >= image_data_->width() ||
dx <= -image_data_->height() || dy >= image_data_->height())
- return true;
+ return;
operation.scroll_dx = dx;
operation.scroll_dy = dy;
queued_operations_.push_back(operation);
- return false;
}
-bool Graphics2D::ReplaceContents(PP_Resource image) {
- scoped_refptr<ImageData> image_resource(Resource::GetAs<ImageData>(image));
+void Graphics2D::ReplaceContents(PP_Resource image_data) {
+ scoped_refptr<ImageData> image_resource(
+ Resource::GetAs<ImageData>(image_data));
if (!image_resource)
- return false;
- if (image_resource->format() != PP_IMAGEDATAFORMAT_BGRA_PREMUL)
- return false;
+ return;
+ if (!ImageData::IsImageDataFormatSupported(image_resource->format()))
+ return;
if (image_resource->width() != image_data_->width() ||
image_resource->height() != image_data_->height())
- return false;
+ return;
QueuedOperation operation(QueuedOperation::REPLACE);
operation.replace_image = image_resource;
queued_operations_.push_back(operation);
-
- return true;
}
int32_t Graphics2D::Flush(const PP_CompletionCallback& callback) {
@@ -342,7 +384,7 @@ bool Graphics2D::ReadImageData(PP_Resource image,
scoped_refptr<ImageData> image_resource(Resource::GetAs<ImageData>(image));
if (!image_resource)
return false;
- if (image_resource->format() != PP_IMAGEDATAFORMAT_BGRA_PREMUL)
+ if (!ImageData::IsImageDataFormatSupported(image_resource->format()))
return false; // Must be in the right format.
// Validate the bitmap position.
@@ -360,7 +402,6 @@ bool Graphics2D::ReadImageData(PP_Resource image,
ImageDataAutoMapper auto_mapper(image_resource);
if (!auto_mapper.is_valid())
return false;
- skia::PlatformCanvas* dest_canvas = image_resource->mapped_canvas();
SkIRect src_irect = { x, y,
x + image_resource->width(),
@@ -370,11 +411,18 @@ bool Graphics2D::ReadImageData(PP_Resource image,
SkIntToScalar(image_resource->width()),
SkIntToScalar(image_resource->height()) };
- // We want to replace the contents of the bitmap rather than blend.
- SkPaint paint;
- paint.setXfermodeMode(SkXfermode::kSrc_Mode);
- dest_canvas->drawBitmapRect(*image_data_->GetMappedBitmap(),
- &src_irect, dest_rect, &paint);
+ if (image_resource->format() != image_data_->format()) {
+ // Convert the image data if the format does not match.
+ ConvertImageData(image_data_, src_irect, image_resource.get(), dest_rect);
+ } else {
+ skia::PlatformCanvas* dest_canvas = image_resource->mapped_canvas();
+
+ // We want to replace the contents of the bitmap rather than blend.
+ SkPaint paint;
+ paint.setXfermodeMode(SkXfermode::kSrc_Mode);
+ dest_canvas->drawBitmapRect(*image_data_->GetMappedBitmap(),
+ &src_irect, dest_rect, &paint);
+ }
return true;
}
@@ -421,11 +469,11 @@ void Graphics2D::Paint(WebKit::WebCanvas* canvas,
#if defined(OS_MACOSX)
SkAutoLockPixels lock(backing_bitmap);
- scoped_cftyperef<CGDataProviderRef> data_provider(
+ base::mac::ScopedCFTypeRef<CGDataProviderRef> data_provider(
CGDataProviderCreateWithData(
NULL, backing_bitmap.getAddr32(0, 0),
backing_bitmap.rowBytes() * backing_bitmap.height(), NULL));
- scoped_cftyperef<CGImageRef> image(
+ base::mac::ScopedCFTypeRef<CGImageRef> image(
CGImageCreate(
backing_bitmap.width(), backing_bitmap.height(),
8, 32, backing_bitmap.rowBytes(),
@@ -510,14 +558,19 @@ void Graphics2D::ExecutePaintImageData(ImageData* image,
SkIntToScalar(invalidated_rect->right()),
SkIntToScalar(invalidated_rect->bottom()) };
- // We're guaranteed to have a mapped canvas since we mapped it in Init().
- skia::PlatformCanvas* backing_canvas = image_data_->mapped_canvas();
+ if (image->format() != image_data_->format()) {
+ // Convert the image data if the format does not match.
+ ConvertImageData(image, src_irect, image_data_, dest_rect);
+ } else {
+ // We're guaranteed to have a mapped canvas since we mapped it in Init().
+ skia::PlatformCanvas* backing_canvas = image_data_->mapped_canvas();
- // We want to replace the contents of the bitmap rather than blend.
- SkPaint paint;
- paint.setXfermodeMode(SkXfermode::kSrc_Mode);
- backing_canvas->drawBitmapRect(*image->GetMappedBitmap(),
- &src_irect, dest_rect, &paint);
+ // We want to replace the contents of the bitmap rather than blend.
+ SkPaint paint;
+ paint.setXfermodeMode(SkXfermode::kSrc_Mode);
+ backing_canvas->drawBitmapRect(*image->GetMappedBitmap(),
+ &src_irect, dest_rect, &paint);
+ }
}
void Graphics2D::ExecuteScroll(const gfx::Rect& clip, int dx, int dy,
@@ -529,7 +582,19 @@ void Graphics2D::ExecuteScroll(const gfx::Rect& clip, int dx, int dy,
void Graphics2D::ExecuteReplaceContents(ImageData* image,
gfx::Rect* invalidated_rect) {
- image_data_->Swap(image);
+ if (image->format() != image_data_->format()) {
+ DCHECK(image->width() == image_data_->width() &&
+ image->height() == image_data_->height());
+ // Convert the image data if the format does not match.
+ SkIRect src_irect = { 0, 0, image->width(), image->height() };
+ SkRect dest_rect = { SkIntToScalar(0),
+ SkIntToScalar(0),
+ SkIntToScalar(image_data_->width()),
+ SkIntToScalar(image_data_->height()) };
+ ConvertImageData(image, src_irect, image_data_, dest_rect);
+ } else {
+ image_data_->Swap(image);
+ }
*invalidated_rect = gfx::Rect(0, 0,
image_data_->width(), image_data_->height());
}
diff --git a/webkit/glue/plugins/pepper_graphics_2d.h b/webkit/glue/plugins/pepper_graphics_2d.h
index 3af84de..ff4cd16 100644
--- a/webkit/glue/plugins/pepper_graphics_2d.h
+++ b/webkit/glue/plugins/pepper_graphics_2d.h
@@ -43,11 +43,11 @@ class Graphics2D : public Resource {
// PPB_Graphics2D functions.
bool Describe(PP_Size* size, bool* is_always_opaque);
- bool PaintImageData(PP_Resource image,
+ void PaintImageData(PP_Resource image_data,
const PP_Point* top_left,
const PP_Rect* src_rect);
- bool Scroll(const PP_Rect* clip_rect, const PP_Point* amount);
- bool ReplaceContents(PP_Resource image);
+ void Scroll(const PP_Rect* clip_rect, const PP_Point* amount);
+ void ReplaceContents(PP_Resource image_data);
int32_t Flush(const PP_CompletionCallback& callback);
bool ReadImageData(PP_Resource image, const PP_Point* top_left);
diff --git a/webkit/glue/plugins/pepper_graphics_3d.cc b/webkit/glue/plugins/pepper_graphics_3d.cc
index 18e5cd1..1ebc3ea 100644
--- a/webkit/glue/plugins/pepper_graphics_3d.cc
+++ b/webkit/glue/plugins/pepper_graphics_3d.cc
@@ -62,7 +62,7 @@ PP_Resource CreateContext(PP_Instance instance_id, int32_t config,
const int32_t* attrib_list) {
DCHECK_EQ(0, share_context);
- PluginInstance* instance = PluginInstance::FromPPInstance(instance_id);
+ PluginInstance* instance = ResourceTracker::Get()->GetInstance(instance_id);
if (!instance) {
return 0;
}
@@ -146,7 +146,7 @@ Graphics3D::~Graphics3D() {
bool Graphics3D::Init(PP_Instance instance_id, int32_t config,
const int32_t* attrib_list) {
- PluginInstance* instance = PluginInstance::FromPPInstance(instance_id);
+ PluginInstance* instance = ResourceTracker::Get()->GetInstance(instance_id);
if (!instance) {
return false;
}
@@ -241,7 +241,7 @@ void Graphics3D::Destroy() {
}
void Graphics3D::HandleRepaint(PP_Instance instance_id) {
- PluginInstance* instance = PluginInstance::FromPPInstance(instance_id);
+ PluginInstance* instance = ResourceTracker::Get()->GetInstance(instance_id);
if (instance) {
instance->Graphics3DContextLost();
if (platform_context_.get()) {
diff --git a/webkit/glue/plugins/pepper_image_data.cc b/webkit/glue/plugins/pepper_image_data.cc
index aeb2c88..2ee8b21 100644
--- a/webkit/glue/plugins/pepper_image_data.cc
+++ b/webkit/glue/plugins/pepper_image_data.cc
@@ -15,6 +15,7 @@
#include "third_party/ppapi/c/pp_resource.h"
#include "third_party/ppapi/c/ppb_image_data.h"
#include "third_party/ppapi/c/trusted/ppb_image_data_trusted.h"
+#include "third_party/skia/include/core/SkColorPriv.h"
#include "webkit/glue/plugins/pepper_plugin_instance.h"
#include "webkit/glue/plugins/pepper_plugin_module.h"
@@ -23,14 +24,18 @@ namespace pepper {
namespace {
PP_ImageDataFormat GetNativeImageDataFormat() {
- return PP_IMAGEDATAFORMAT_BGRA_PREMUL;
+ return ImageData::GetNativeImageDataFormat();
+}
+
+bool IsImageDataFormatSupported(PP_ImageDataFormat format) {
+ return ImageData::IsImageDataFormatSupported(format);
}
PP_Resource Create(PP_Module module_id,
PP_ImageDataFormat format,
const PP_Size* size,
bool init_to_zero) {
- PluginModule* module = PluginModule::FromPPModule(module_id);
+ PluginModule* module = ResourceTracker::Get()->GetModule(module_id);
if (!module)
return 0;
@@ -78,6 +83,7 @@ uint64_t GetNativeMemoryHandle2(PP_Resource resource) {
const PPB_ImageData ppb_imagedata = {
&GetNativeImageDataFormat,
+ &IsImageDataFormatSupported,
&Create,
&IsImageData,
&Describe,
@@ -93,6 +99,7 @@ const PPB_ImageDataTrusted ppb_imagedata_trusted = {
ImageData::ImageData(PluginModule* module)
: Resource(module),
+ format_(PP_IMAGEDATAFORMAT_BGRA_PREMUL),
width_(0),
height_(0) {
}
@@ -110,12 +117,28 @@ const PPB_ImageDataTrusted* ImageData::GetTrustedInterface() {
return &ppb_imagedata_trusted;
}
+// static
+PP_ImageDataFormat ImageData::GetNativeImageDataFormat() {
+ if (SK_B32_SHIFT == 0)
+ return PP_IMAGEDATAFORMAT_BGRA_PREMUL;
+ else if (SK_R32_SHIFT == 0)
+ return PP_IMAGEDATAFORMAT_RGBA_PREMUL;
+ else
+ return PP_IMAGEDATAFORMAT_BGRA_PREMUL; // Default to something on failure.
+}
+
+// static
+bool ImageData::IsImageDataFormatSupported(PP_ImageDataFormat format) {
+ return format == PP_IMAGEDATAFORMAT_BGRA_PREMUL ||
+ format == PP_IMAGEDATAFORMAT_RGBA_PREMUL;
+}
+
bool ImageData::Init(PP_ImageDataFormat format,
int width, int height,
bool init_to_zero) {
// TODO(brettw) this should be called only on the main thread!
// TODO(brettw) use init_to_zero when we implement caching.
- if (format != PP_IMAGEDATAFORMAT_BGRA_PREMUL)
+ if (!IsImageDataFormatSupported(format))
return false; // Only support this one format for now.
if (width <= 0 || height <= 0)
return false;
@@ -125,13 +148,14 @@ bool ImageData::Init(PP_ImageDataFormat format,
platform_image_.reset(
module()->GetSomeInstance()->delegate()->CreateImage2D(width, height));
+ format_ = format;
width_ = width;
height_ = height;
return !!platform_image_.get();
}
void ImageData::Describe(PP_ImageDataDesc* desc) const {
- desc->format = PP_IMAGEDATAFORMAT_BGRA_PREMUL;
+ desc->format = format_;
desc->size.width = width_;
desc->size.height = height_;
desc->stride = width_ * 4;
@@ -173,6 +197,7 @@ const SkBitmap* ImageData::GetMappedBitmap() const {
void ImageData::Swap(ImageData* other) {
swap(other->platform_image_, platform_image_);
swap(other->mapped_canvas_, mapped_canvas_);
+ std::swap(other->format_, format_);
std::swap(other->width_, width_);
std::swap(other->height_, height_);
}
diff --git a/webkit/glue/plugins/pepper_image_data.h b/webkit/glue/plugins/pepper_image_data.h
index f2a110b..f8c713a 100644
--- a/webkit/glue/plugins/pepper_image_data.h
+++ b/webkit/glue/plugins/pepper_image_data.h
@@ -28,11 +28,8 @@ class ImageData : public Resource {
int width() const { return width_; }
int height() const { return height_; }
- // Returns the image format. Currently there is only one format so this
- // always returns the same thing. But if you care about the formation, you
- // should probably check this so when we support multiple formats, we can't
- // forget to update your code.
- PP_ImageDataFormat format() const { return PP_IMAGEDATAFORMAT_BGRA_PREMUL; }
+ // Returns the image format.
+ PP_ImageDataFormat format() const { return format_; }
// Returns true if this image is mapped. False means that the image is either
// invalid or not mapped. See ImageDataAutoMapper below.
@@ -47,6 +44,14 @@ class ImageData : public Resource {
static const PPB_ImageData* GetInterface();
static const PPB_ImageDataTrusted* GetTrustedInterface();
+ // Returns the image data format used by the browser. If the plugin uses the
+ // same format, there is no conversion. Otherwise the browser will be in
+ // charge of converting from a supported format to its native format.
+ static PP_ImageDataFormat GetNativeImageDataFormat();
+
+ // Returns true if the format is supported by the browser.
+ static bool IsImageDataFormatSupported(PP_ImageDataFormat format);
+
// Resource overrides.
virtual ImageData* AsImageData() { return this; }
@@ -76,6 +81,7 @@ class ImageData : public Resource {
// When the device is mapped, this is the image. Null when umapped.
scoped_ptr<skia::PlatformCanvas> mapped_canvas_;
+ PP_ImageDataFormat format_;
int width_;
int height_;
diff --git a/webkit/glue/plugins/pepper_plugin_delegate.h b/webkit/glue/plugins/pepper_plugin_delegate.h
index 1bb4bed..7738fbf 100644
--- a/webkit/glue/plugins/pepper_plugin_delegate.h
+++ b/webkit/glue/plugins/pepper_plugin_delegate.h
@@ -13,11 +13,15 @@
#include "base/shared_memory.h"
#include "base/sync_socket.h"
#include "base/task.h"
+#include "googleurl/src/gurl.h"
#include "third_party/ppapi/c/pp_completion_callback.h"
#include "third_party/ppapi/c/pp_errors.h"
#include "third_party/ppapi/c/pp_stdint.h"
+#include "webkit/fileapi/file_system_types.h"
+#include "webkit/glue/plugins/pepper_dir_contents.h"
class AudioMessageFilter;
+class GURL;
namespace base {
class MessageLoopProxy;
@@ -156,12 +160,12 @@ class PluginDelegate {
PlatformAudio::Client* client) = 0;
// Notifies that the number of find results has changed.
- virtual void DidChangeNumberOfFindResults(int identifier,
- int total,
- bool final_result) = 0;
+ virtual void NumberOfFindResultsChanged(int identifier,
+ int total,
+ bool final_result) = 0;
// Notifies that the index of the currently selected item has been updated.
- virtual void DidChangeSelectedFindResult(int identifier, int index) = 0;
+ virtual void SelectedFindResultChanged(int identifier, int index) = 0;
// Runs a file chooser.
virtual bool RunFileChooser(
@@ -174,6 +178,11 @@ class PluginDelegate {
virtual bool AsyncOpenFile(const FilePath& path,
int flags,
AsyncOpenFileCallback* callback) = 0;
+ virtual bool OpenFileSystem(
+ const GURL& url,
+ fileapi::FileSystemType type,
+ long long size,
+ fileapi::FileSystemCallbackDispatcher* dispatcher) = 0;
virtual bool MakeDirectory(
const FilePath& path,
bool recursive,
@@ -190,6 +199,31 @@ class PluginDelegate {
const FilePath& new_file_path,
fileapi::FileSystemCallbackDispatcher* dispatcher) = 0;
+ virtual base::PlatformFileError OpenModuleLocalFile(
+ const std::string& module_name,
+ const FilePath& path,
+ int flags,
+ base::PlatformFile* file) = 0;
+ virtual base::PlatformFileError RenameModuleLocalFile(
+ const std::string& module_name,
+ const FilePath& path_from,
+ const FilePath& path_to) = 0;
+ virtual base::PlatformFileError DeleteModuleLocalFileOrDir(
+ const std::string& module_name,
+ const FilePath& path,
+ bool recursive) = 0;
+ virtual base::PlatformFileError CreateModuleLocalDir(
+ const std::string& module_name,
+ const FilePath& path) = 0;
+ virtual base::PlatformFileError QueryModuleLocalFile(
+ const std::string& module_name,
+ const FilePath& path,
+ base::PlatformFileInfo* info) = 0;
+ virtual base::PlatformFileError GetModuleLocalDirContents(
+ const std::string& module_name,
+ const FilePath& path,
+ PepperDirContents* contents) = 0;
+
// Returns a MessageLoopProxy instance associated with the message loop
// of the file thread in this renderer.
virtual scoped_refptr<base::MessageLoopProxy>
@@ -202,6 +236,21 @@ class PluginDelegate {
// Returns a string with the name of the default 8-bit char encoding.
virtual std::string GetDefaultEncoding() = 0;
+
+ // Sets the mininum and maximium zoom factors.
+ virtual void ZoomLimitsChanged(double minimum_factor,
+ double maximum_factor) = 0;
+
+ // Retrieves the proxy information for the given URL in PAC format. On error,
+ // this will return an empty string.
+ virtual std::string ResolveProxy(const GURL& url) = 0;
+
+ // Tell the browser when resource loading starts/ends.
+ virtual void DidStartLoading() = 0;
+ virtual void DidStopLoading() = 0;
+
+ // Sets restrictions on how the content can be used (i.e. no print/copy).
+ virtual void SetContentRestriction(int restrictions) = 0;
};
} // namespace pepper
diff --git a/webkit/glue/plugins/pepper_plugin_instance.cc b/webkit/glue/plugins/pepper_plugin_instance.cc
index b4ccd89..54a1f42 100644
--- a/webkit/glue/plugins/pepper_plugin_instance.cc
+++ b/webkit/glue/plugins/pepper_plugin_instance.cc
@@ -5,10 +5,10 @@
#include "webkit/glue/plugins/pepper_plugin_instance.h"
#include "base/logging.h"
-#include "base/histogram.h"
+#include "base/metrics/histogram.h"
#if defined(OS_MACOSX)
#include "base/mac_util.h"
-#include "base/scoped_cftyperef.h"
+#include "base/mac/scoped_cftyperef.h"
#endif
#include "base/scoped_ptr.h"
#include "base/utf_string_conversions.h"
@@ -24,7 +24,9 @@
#include "skia/ext/platform_canvas.h"
#include "third_party/ppapi/c/dev/ppb_find_dev.h"
#include "third_party/ppapi/c/dev/ppb_fullscreen_dev.h"
+#include "third_party/ppapi/c/dev/ppb_zoom_dev.h"
#include "third_party/ppapi/c/dev/ppp_find_dev.h"
+#include "third_party/ppapi/c/dev/ppp_selection_dev.h"
#include "third_party/ppapi/c/dev/ppp_zoom_dev.h"
#include "third_party/ppapi/c/pp_input_event.h"
#include "third_party/ppapi/c/pp_instance.h"
@@ -42,6 +44,7 @@
#include "third_party/WebKit/WebKit/chromium/public/WebInputEvent.h"
#include "third_party/WebKit/WebKit/chromium/public/WebPluginContainer.h"
#include "third_party/WebKit/WebKit/chromium/public/WebRect.h"
+#include "third_party/WebKit/WebKit/chromium/public/WebView.h"
#include "webkit/glue/plugins/pepper_buffer.h"
#include "webkit/glue/plugins/pepper_graphics_2d.h"
#include "webkit/glue/plugins/pepper_event_conversion.h"
@@ -52,6 +55,7 @@
#include "webkit/glue/plugins/pepper_string.h"
#include "webkit/glue/plugins/pepper_url_loader.h"
#include "webkit/glue/plugins/pepper_var.h"
+#include "webkit/glue/plugins/ppp_private.h"
using WebKit::WebBindings;
using WebKit::WebCanvas;
@@ -59,6 +63,7 @@ using WebKit::WebCursorInfo;
using WebKit::WebFrame;
using WebKit::WebInputEvent;
using WebKit::WebPluginContainer;
+using WebKit::WebView;
namespace pepper {
@@ -137,28 +142,28 @@ void RectToPPRect(const gfx::Rect& input, PP_Rect* output) {
}
PP_Var GetWindowObject(PP_Instance instance_id) {
- PluginInstance* instance = PluginInstance::FromPPInstance(instance_id);
+ PluginInstance* instance = ResourceTracker::Get()->GetInstance(instance_id);
if (!instance)
- return PP_MakeVoid();
+ return PP_MakeUndefined();
return instance->GetWindowObject();
}
PP_Var GetOwnerElementObject(PP_Instance instance_id) {
- PluginInstance* instance = PluginInstance::FromPPInstance(instance_id);
+ PluginInstance* instance = ResourceTracker::Get()->GetInstance(instance_id);
if (!instance)
- return PP_MakeVoid();
+ return PP_MakeUndefined();
return instance->GetOwnerElementObject();
}
bool BindGraphics(PP_Instance instance_id, PP_Resource device_id) {
- PluginInstance* instance = PluginInstance::FromPPInstance(instance_id);
+ PluginInstance* instance = ResourceTracker::Get()->GetInstance(instance_id);
if (!instance)
return false;
return instance->BindGraphics(device_id);
}
bool IsFullFrame(PP_Instance instance_id) {
- PluginInstance* instance = PluginInstance::FromPPInstance(instance_id);
+ PluginInstance* instance = ResourceTracker::Get()->GetInstance(instance_id);
if (!instance)
return false;
return instance->full_frame();
@@ -167,9 +172,9 @@ bool IsFullFrame(PP_Instance instance_id) {
PP_Var ExecuteScript(PP_Instance instance_id,
PP_Var script,
PP_Var* exception) {
- PluginInstance* instance = PluginInstance::FromPPInstance(instance_id);
+ PluginInstance* instance = ResourceTracker::Get()->GetInstance(instance_id);
if (!instance)
- return PP_MakeVoid();
+ return PP_MakeUndefined();
return instance->ExecuteScript(script, exception);
}
@@ -184,23 +189,23 @@ const PPB_Instance ppb_instance = {
void NumberOfFindResultsChanged(PP_Instance instance_id,
int32_t total,
bool final_result) {
- PluginInstance* instance = PluginInstance::FromPPInstance(instance_id);
+ PluginInstance* instance = ResourceTracker::Get()->GetInstance(instance_id);
if (!instance)
return;
DCHECK_NE(instance->find_identifier(), -1);
- instance->delegate()->DidChangeNumberOfFindResults(
+ instance->delegate()->NumberOfFindResultsChanged(
instance->find_identifier(), total, final_result);
}
void SelectedFindResultChanged(PP_Instance instance_id,
int32_t index) {
- PluginInstance* instance = PluginInstance::FromPPInstance(instance_id);
+ PluginInstance* instance = ResourceTracker::Get()->GetInstance(instance_id);
if (!instance)
return;
DCHECK_NE(instance->find_identifier(), -1);
- instance->delegate()->DidChangeSelectedFindResult(
+ instance->delegate()->SelectedFindResultChanged(
instance->find_identifier(), index);
}
@@ -210,14 +215,14 @@ const PPB_Find_Dev ppb_find = {
};
bool IsFullscreen(PP_Instance instance_id) {
- PluginInstance* instance = PluginInstance::FromPPInstance(instance_id);
+ PluginInstance* instance = ResourceTracker::Get()->GetInstance(instance_id);
if (!instance)
return false;
return instance->IsFullscreen();
}
bool SetFullscreen(PP_Instance instance_id, bool fullscreen) {
- PluginInstance* instance = PluginInstance::FromPPInstance(instance_id);
+ PluginInstance* instance = ResourceTracker::Get()->GetInstance(instance_id);
if (!instance)
return false;
return instance->SetFullscreen(fullscreen);
@@ -228,6 +233,33 @@ const PPB_Fullscreen_Dev ppb_fullscreen = {
&SetFullscreen,
};
+void ZoomChanged(PP_Instance instance_id, double factor) {
+ PluginInstance* instance = ResourceTracker::Get()->GetInstance(instance_id);
+ if (!instance)
+ return;
+ double zoom_level = WebView::zoomFactorToZoomLevel(factor);
+ instance->container()->zoomLevelChanged(zoom_level);
+}
+
+void ZoomLimitsChanged(PP_Instance instance_id,
+ double minimum_factor,
+ double maximium_factor) {
+ if (minimum_factor > maximium_factor) {
+ NOTREACHED();
+ return;
+ }
+
+ PluginInstance* instance = ResourceTracker::Get()->GetInstance(instance_id);
+ if (!instance)
+ return;
+ instance->delegate()->ZoomLimitsChanged(minimum_factor, maximium_factor);
+}
+
+const PPB_Zoom_Dev ppb_zoom = {
+ &ZoomChanged,
+ &ZoomLimitsChanged
+};
+
} // namespace
PluginInstance::PluginInstance(PluginDelegate* delegate,
@@ -236,12 +268,15 @@ PluginInstance::PluginInstance(PluginDelegate* delegate,
: delegate_(delegate),
module_(module),
instance_interface_(instance_interface),
+ pp_instance_(0),
container_(NULL),
full_frame_(false),
has_webkit_focus_(false),
has_content_area_focus_(false),
find_identifier_(-1),
plugin_find_interface_(NULL),
+ plugin_private_interface_(NULL),
+ plugin_selection_interface_(NULL),
plugin_zoom_interface_(NULL),
#if defined (OS_LINUX)
num_pages_(0),
@@ -251,6 +286,8 @@ PluginInstance::PluginInstance(PluginDelegate* delegate,
plugin_graphics_3d_interface_(NULL),
always_on_top_(false),
fullscreen_container_(NULL) {
+ pp_instance_ = ResourceTracker::Get()->AddInstance(this);
+
memset(&current_print_settings_, 0, sizeof(current_print_settings_));
DCHECK(delegate);
module_->InstanceCreated(this);
@@ -260,6 +297,8 @@ PluginInstance::PluginInstance(PluginDelegate* delegate,
PluginInstance::~PluginInstance() {
delegate_->InstanceDeleted(this);
module_->InstanceDeleted(this);
+
+ ResourceTracker::Get()->InstanceDeleted(pp_instance_);
}
// static
@@ -268,11 +307,6 @@ const PPB_Instance* PluginInstance::GetInterface() {
}
// static
-PluginInstance* PluginInstance::FromPPInstance(PP_Instance instance) {
- return reinterpret_cast<PluginInstance*>(instance);
-}
-
-// static
const PPB_Find_Dev* PluginInstance::GetFindInterface() {
return &ppb_find;
}
@@ -282,8 +316,9 @@ const PPB_Fullscreen_Dev* PluginInstance::GetFullscreenInterface() {
return &ppb_fullscreen;
}
-PP_Instance PluginInstance::GetPPInstance() {
- return reinterpret_cast<intptr_t>(this);
+// static
+const PPB_Zoom_Dev* PluginInstance::GetZoomInterface() {
+ return &ppb_zoom;
}
void PluginInstance::Paint(WebCanvas* canvas,
@@ -311,18 +346,18 @@ void PluginInstance::InvalidateRect(const gfx::Rect& rect) {
PP_Var PluginInstance::GetWindowObject() {
if (!container_)
- return PP_MakeVoid();
+ return PP_MakeUndefined();
WebFrame* frame = container_->element().document().frame();
if (!frame)
- return PP_MakeVoid();
+ return PP_MakeUndefined();
return ObjectVar::NPObjectToPPVar(module(), frame->windowObject());
}
PP_Var PluginInstance::GetOwnerElementObject() {
if (!container_)
- return PP_MakeVoid();
+ return PP_MakeUndefined();
return ObjectVar::NPObjectToPPVar(module(),
container_->scriptableObjectForElement());
}
@@ -378,13 +413,13 @@ bool PluginInstance::SetCursor(PP_CursorType_Dev type) {
PP_Var PluginInstance::ExecuteScript(PP_Var script, PP_Var* exception) {
TryCatch try_catch(module(), exception);
if (try_catch.has_exception())
- return PP_MakeVoid();
+ return PP_MakeUndefined();
// Convert the script into an inconvenient NPString object.
scoped_refptr<StringVar> script_string(StringVar::FromPPVar(script));
if (!script_string) {
try_catch.SetException("Script param to ExecuteScript must be a string.");
- return PP_MakeVoid();
+ return PP_MakeUndefined();
}
NPString np_script;
np_script.UTF8Characters = script_string->value().c_str();
@@ -394,7 +429,7 @@ PP_Var PluginInstance::ExecuteScript(PP_Var script, PP_Var* exception) {
WebFrame* frame = container_->element().document().frame();
if (!frame) {
try_catch.SetException("No frame to execute script in.");
- return PP_MakeVoid();
+ return PP_MakeUndefined();
}
NPVariant result;
@@ -405,7 +440,7 @@ PP_Var PluginInstance::ExecuteScript(PP_Var script, PP_Var* exception) {
// doesn't actually catch this exception.
try_catch.SetException("Exception caught");
WebBindings::releaseVariantValue(&result);
- return PP_MakeVoid();
+ return PP_MakeUndefined();
}
PP_Var ret = Var::NPVariantToPPVar(module_, &result);
@@ -414,7 +449,7 @@ PP_Var PluginInstance::ExecuteScript(PP_Var script, PP_Var* exception) {
}
void PluginInstance::Delete() {
- instance_interface_->Delete(GetPPInstance());
+ instance_interface_->DidDestroy(pp_instance());
if (fullscreen_container_) {
fullscreen_container_->Destroy();
@@ -430,9 +465,6 @@ bool PluginInstance::Initialize(WebPluginContainer* container,
container_ = container;
full_frame_ = full_frame;
- if (!instance_interface_->New(GetPPInstance()))
- return false;
-
size_t argc = 0;
scoped_array<const char*> argn(new const char*[arg_names.size()]);
scoped_array<const char*> argv(new const char*[arg_names.size()]);
@@ -442,13 +474,13 @@ bool PluginInstance::Initialize(WebPluginContainer* container,
argc++;
}
- return instance_interface_->Initialize(GetPPInstance(),
- argc, argn.get(), argv.get());
+ return instance_interface_->DidCreate(pp_instance(),
+ argc, argn.get(), argv.get());
}
bool PluginInstance::HandleDocumentLoad(URLLoader* loader) {
Resource::ScopedResourceId resource(loader);
- return instance_interface_->HandleDocumentLoad(GetPPInstance(), resource.id);
+ return instance_interface_->HandleDocumentLoad(pp_instance(), resource.id);
}
bool PluginInstance::HandleInputEvent(const WebKit::WebInputEvent& event,
@@ -459,7 +491,7 @@ bool PluginInstance::HandleInputEvent(const WebKit::WebInputEvent& event,
// Each input event may generate more than one PP_InputEvent.
bool rv = false;
for (size_t i = 0; i < pp_events.size(); i++)
- rv |= instance_interface_->HandleInputEvent(GetPPInstance(), &pp_events[i]);
+ rv |= instance_interface_->HandleInputEvent(pp_instance(), &pp_events[i]);
if (cursor_.get())
*cursor_info = *cursor_;
@@ -467,7 +499,7 @@ bool PluginInstance::HandleInputEvent(const WebKit::WebInputEvent& event,
}
PP_Var PluginInstance::GetInstanceObject() {
- return instance_interface_->GetInstanceObject(GetPPInstance());
+ return instance_interface_->GetInstanceObject(pp_instance());
}
void PluginInstance::ViewChanged(const gfx::Rect& position,
@@ -486,7 +518,7 @@ void PluginInstance::ViewChanged(const gfx::Rect& position,
PP_Rect pp_position, pp_clip;
RectToPPRect(position_, &pp_position);
RectToPPRect(clip_, &pp_clip);
- instance_interface_->ViewChanged(GetPPInstance(), &pp_position, &pp_clip);
+ instance_interface_->DidChangeView(pp_instance(), &pp_position, &pp_clip);
}
void PluginInstance::SetWebKitFocus(bool has_focus) {
@@ -496,7 +528,7 @@ void PluginInstance::SetWebKitFocus(bool has_focus) {
bool old_plugin_focus = PluginHasFocus();
has_webkit_focus_ = has_focus;
if (PluginHasFocus() != old_plugin_focus)
- instance_interface_->FocusChanged(GetPPInstance(), PluginHasFocus());
+ instance_interface_->DidChangeFocus(pp_instance(), PluginHasFocus());
}
void PluginInstance::SetContentAreaFocus(bool has_focus) {
@@ -506,7 +538,7 @@ void PluginInstance::SetContentAreaFocus(bool has_focus) {
bool old_plugin_focus = PluginHasFocus();
has_content_area_focus_ = has_focus;
if (PluginHasFocus() != old_plugin_focus)
- instance_interface_->FocusChanged(GetPPInstance(), PluginHasFocus());
+ instance_interface_->DidChangeFocus(pp_instance(), PluginHasFocus());
}
void PluginInstance::ViewInitiatedPaint() {
@@ -547,7 +579,25 @@ bool PluginInstance::GetBitmapForOptimizedPluginPaint(
}
string16 PluginInstance::GetSelectedText(bool html) {
- PP_Var rv = instance_interface_->GetSelectedText(GetPPInstance(), html);
+ if (!LoadSelectionInterface())
+ return string16();
+
+ PP_Var rv = plugin_selection_interface_->GetSelectedText(pp_instance(), html);
+ scoped_refptr<StringVar> string(StringVar::FromPPVar(rv));
+ Var::PluginReleasePPVar(rv); // Release the ref the plugin transfered to us.
+ if (!string)
+ return string16();
+ return UTF8ToUTF16(string->value());
+}
+
+string16 PluginInstance::GetLinkAtPosition(const gfx::Point& point) {
+ if (!LoadPrivateInterface())
+ return string16();
+
+ PP_Point p;
+ p.x = point.x();
+ p.y = point.y();
+ PP_Var rv = plugin_private_interface_->GetLinkAtPosition(pp_instance(), p);
scoped_refptr<StringVar> string(StringVar::FromPPVar(rv));
Var::PluginReleasePPVar(rv); // Release the ref the plugin transfered to us.
if (!string)
@@ -555,10 +605,10 @@ string16 PluginInstance::GetSelectedText(bool html) {
return UTF8ToUTF16(string->value());
}
-void PluginInstance::Zoom(float factor, bool text_only) {
+void PluginInstance::Zoom(double factor, bool text_only) {
if (!LoadZoomInterface())
return;
- plugin_zoom_interface_->Zoom(GetPPInstance(), factor, text_only);
+ plugin_zoom_interface_->Zoom(pp_instance(), factor, text_only);
}
bool PluginInstance::StartFind(const string16& search_text,
@@ -568,21 +618,21 @@ bool PluginInstance::StartFind(const string16& search_text,
return false;
find_identifier_ = identifier;
return plugin_find_interface_->StartFind(
- GetPPInstance(),
+ pp_instance(),
UTF16ToUTF8(search_text.c_str()).c_str(),
case_sensitive);
}
void PluginInstance::SelectFindResult(bool forward) {
if (LoadFindInterface())
- plugin_find_interface_->SelectFindResult(GetPPInstance(), forward);
+ plugin_find_interface_->SelectFindResult(pp_instance(), forward);
}
void PluginInstance::StopFind() {
if (!LoadFindInterface())
return;
find_identifier_ = -1;
- plugin_find_interface_->StopFind(GetPPInstance());
+ plugin_find_interface_->StopFind(pp_instance());
}
bool PluginInstance::LoadFindInterface() {
@@ -595,6 +645,26 @@ bool PluginInstance::LoadFindInterface() {
return !!plugin_find_interface_;
}
+bool PluginInstance::LoadPrivateInterface() {
+ if (!plugin_private_interface_) {
+ plugin_private_interface_ =
+ reinterpret_cast<const PPP_Private*>(module_->GetPluginInterface(
+ PPP_PRIVATE_INTERFACE));
+ }
+
+ return !!plugin_private_interface_;
+}
+
+bool PluginInstance::LoadSelectionInterface() {
+ if (!plugin_selection_interface_) {
+ plugin_selection_interface_ =
+ reinterpret_cast<const PPP_Selection_Dev*>(module_->GetPluginInterface(
+ PPP_SELECTION_DEV_INTERFACE));
+ }
+
+ return !!plugin_selection_interface_;
+}
+
bool PluginInstance::LoadZoomInterface() {
if (!plugin_zoom_interface_) {
plugin_zoom_interface_ =
@@ -620,7 +690,7 @@ bool PluginInstance::GetPreferredPrintOutputFormat(
return false;
uint32_t format_count = 0;
PP_PrintOutputFormat_Dev* supported_formats =
- plugin_print_interface_->QuerySupportedFormats(GetPPInstance(),
+ plugin_print_interface_->QuerySupportedFormats(pp_instance(),
&format_count);
if (!supported_formats)
return false;
@@ -663,7 +733,7 @@ int PluginInstance::PrintBegin(const gfx::Rect& printable_area,
print_settings.orientation = PP_PRINTORIENTATION_NORMAL;
print_settings.grayscale = false;
print_settings.format = format;
- int num_pages = plugin_print_interface_->Begin(GetPPInstance(),
+ int num_pages = plugin_print_interface_->Begin(pp_instance(),
&print_settings);
if (!num_pages)
return 0;
@@ -694,7 +764,7 @@ bool PluginInstance::PrintPage(int page_number, WebKit::WebCanvas* canvas) {
#endif // defined(OS_LINUX)
PP_Resource print_output =
- plugin_print_interface_->PrintPages(GetPPInstance(), &page_range, 1);
+ plugin_print_interface_->PrintPages(pp_instance(), &page_range, 1);
if (!print_output)
return false;
@@ -715,7 +785,7 @@ bool PluginInstance::PrintPage(int page_number, WebKit::WebCanvas* canvas) {
void PluginInstance::PrintEnd() {
DCHECK(plugin_print_interface_);
if (plugin_print_interface_)
- plugin_print_interface_->End(GetPPInstance());
+ plugin_print_interface_->End(pp_instance());
memset(&current_print_settings_, 0, sizeof(current_print_settings_));
#if defined(OS_MACOSX)
last_printed_page_ = NULL;
@@ -732,7 +802,7 @@ void PluginInstance::Graphics3DContextLost() {
PPP_GRAPHICS_3D_DEV_INTERFACE));
}
if (plugin_graphics_3d_interface_)
- plugin_graphics_3d_interface_->Graphics3DContextLost(GetPPInstance());
+ plugin_graphics_3d_interface_->Graphics3DContextLost(pp_instance());
}
bool PluginInstance::IsFullscreen() {
@@ -743,7 +813,7 @@ bool PluginInstance::SetFullscreen(bool fullscreen) {
bool is_fullscreen = (fullscreen_container_ != NULL);
if (fullscreen == is_fullscreen)
return true;
- LOG(INFO) << "Setting fullscreen to " << (fullscreen ? "on" : "off");
+ VLOG(1) << "Setting fullscreen to " << (fullscreen ? "on" : "off");
if (fullscreen) {
fullscreen_container_ = delegate_->CreateFullscreenContainer(this);
} else {
@@ -957,11 +1027,11 @@ void PluginInstance::DrawSkBitmapToCanvas(
int canvas_height) {
SkAutoLockPixels lock(bitmap);
DCHECK(bitmap.getConfig() == SkBitmap::kARGB_8888_Config);
- scoped_cftyperef<CGDataProviderRef> data_provider(
+ base::mac::ScopedCFTypeRef<CGDataProviderRef> data_provider(
CGDataProviderCreateWithData(
NULL, bitmap.getAddr32(0, 0),
bitmap.rowBytes() * bitmap.height(), NULL));
- scoped_cftyperef<CGImageRef> image(
+ base::mac::ScopedCFTypeRef<CGImageRef> image(
CGImageCreate(
bitmap.width(), bitmap.height(),
8, 32, bitmap.rowBytes(),
diff --git a/webkit/glue/plugins/pepper_plugin_instance.h b/webkit/glue/plugins/pepper_plugin_instance.h
index 4eb956f..e0cc25d 100644
--- a/webkit/glue/plugins/pepper_plugin_instance.h
+++ b/webkit/glue/plugins/pepper_plugin_instance.h
@@ -25,8 +25,11 @@ struct PP_Var;
struct PPB_Instance;
struct PPB_Find_Dev;
struct PPB_Fullscreen_Dev;
+struct PPB_Zoom_Dev;
struct PPP_Find_Dev;
struct PPP_Instance;
+struct PPP_Private;
+struct PPP_Selection_Dev;
struct PPP_Zoom_Dev;
class SkBitmap;
@@ -51,6 +54,10 @@ class PluginModule;
class URLLoader;
class FullscreenContainer;
+// Represents one time a plugin appears on one web page.
+//
+// Note: to get from a PP_Instance to a PluginInstance*, use the
+// ResourceTracker.
class PluginInstance : public base::RefCounted<PluginInstance> {
public:
PluginInstance(PluginDelegate* delegate,
@@ -60,13 +67,11 @@ class PluginInstance : public base::RefCounted<PluginInstance> {
static const PPB_Instance* GetInterface();
- // Converts the given instance ID to an actual instance object.
- static PluginInstance* FromPPInstance(PP_Instance instance);
-
// Returns a pointer to the interface implementing PPB_Find that is
// exposed to the plugin.
static const PPB_Find_Dev* GetFindInterface();
static const PPB_Fullscreen_Dev* GetFullscreenInterface();
+ static const PPB_Zoom_Dev* GetZoomInterface();
PluginDelegate* delegate() const { return delegate_; }
PluginModule* module() const { return module_.get(); }
@@ -80,7 +85,9 @@ class PluginInstance : public base::RefCounted<PluginInstance> {
void set_always_on_top(bool on_top) { always_on_top_ = on_top; }
- PP_Instance GetPPInstance();
+ // Returns the PP_Instance uniquely identifying this instance. Guaranteed
+ // nonzero.
+ PP_Instance pp_instance() const { return pp_instance_; }
// Paints the current backing store to the web page.
void Paint(WebKit::WebCanvas* canvas,
@@ -134,7 +141,8 @@ class PluginInstance : public base::RefCounted<PluginInstance> {
gfx::Rect* clip);
string16 GetSelectedText(bool html);
- void Zoom(float factor, bool text_only);
+ string16 GetLinkAtPosition(const gfx::Point& point);
+ void Zoom(double factor, bool text_only);
bool StartFind(const string16& search_text,
bool case_sensitive,
int identifier);
@@ -154,6 +162,8 @@ class PluginInstance : public base::RefCounted<PluginInstance> {
private:
bool LoadFindInterface();
+ bool LoadPrivateInterface();
+ bool LoadSelectionInterface();
bool LoadZoomInterface();
// Determines if we think the plugin has focus, both content area and webkit
@@ -181,6 +191,8 @@ class PluginInstance : public base::RefCounted<PluginInstance> {
scoped_refptr<PluginModule> module_;
const PPP_Instance* instance_interface_;
+ PP_Instance pp_instance_;
+
// NULL until we have been initialized.
WebKit::WebPluginContainer* container_;
@@ -211,8 +223,10 @@ class PluginInstance : public base::RefCounted<PluginInstance> {
// The id of the current find operation, or -1 if none is in process.
int find_identifier_;
- // The plugin find and zoom interfaces.
+ // The plugin-provided interfaces.
const PPP_Find_Dev* plugin_find_interface_;
+ const PPP_Private* plugin_private_interface_;
+ const PPP_Selection_Dev* plugin_selection_interface_;
const PPP_Zoom_Dev* plugin_zoom_interface_;
// This is only valid between a successful PrintBegin call and a PrintEnd
diff --git a/webkit/glue/plugins/pepper_plugin_module.cc b/webkit/glue/plugins/pepper_plugin_module.cc
index 251023f..13390d5 100644
--- a/webkit/glue/plugins/pepper_plugin_module.cc
+++ b/webkit/glue/plugins/pepper_plugin_module.cc
@@ -32,8 +32,10 @@
#include "third_party/ppapi/c/dev/ppb_url_request_info_dev.h"
#include "third_party/ppapi/c/dev/ppb_url_response_info_dev.h"
#include "third_party/ppapi/c/dev/ppb_url_util_dev.h"
+#include "third_party/ppapi/c/dev/ppb_var_deprecated.h"
#include "third_party/ppapi/c/dev/ppb_video_decoder_dev.h"
#include "third_party/ppapi/c/dev/ppb_widget_dev.h"
+#include "third_party/ppapi/c/dev/ppb_zoom_dev.h"
#include "third_party/ppapi/c/trusted/ppb_image_data_trusted.h"
#include "third_party/ppapi/c/pp_module.h"
#include "third_party/ppapi/c/pp_resource.h"
@@ -42,7 +44,6 @@
#include "third_party/ppapi/c/ppb_graphics_2d.h"
#include "third_party/ppapi/c/ppb_image_data.h"
#include "third_party/ppapi/c/ppb_instance.h"
-#include "third_party/ppapi/c/ppb_var.h"
#include "third_party/ppapi/c/ppp.h"
#include "third_party/ppapi/c/ppp_instance.h"
#include "webkit/glue/plugins/pepper_audio.h"
@@ -123,6 +124,13 @@ double GetTime() {
return base::Time::Now().ToDoubleT();
}
+double GetTickTime() {
+ // TODO(brettw) http://code.google.com/p/chromium/issues/detail?id=57448
+ // This should be a tick timer rather than wall clock time, but needs to
+ // match message times, which also currently use wall clock time.
+ return GetTime();
+}
+
void CallOnMainThread(int delay_in_msec,
PP_CompletionCallback callback,
int32_t result) {
@@ -142,6 +150,7 @@ const PPB_Core core_interface = {
&MemAlloc,
&MemFree,
&GetTime,
+ &GetTickTime,
&CallOnMainThread,
&IsMainThread
};
@@ -170,33 +179,17 @@ void QuitMessageLoop() {
}
uint32_t GetLiveObjectCount(PP_Module module_id) {
- PluginModule* module = PluginModule::FromPPModule(module_id);
+ PluginModule* module = ResourceTracker::Get()->GetModule(module_id);
if (!module)
return static_cast<uint32_t>(-1);
return ResourceTracker::Get()->GetLiveObjectsForModule(module);
}
-PP_Resource GetInaccessibleFileRef(PP_Module module_id) {
- PluginModule* module = PluginModule::FromPPModule(module_id);
- if (!module)
- return static_cast<uint32_t>(-1);
- return FileRef::GetInaccessibleFileRef(module)->GetReference();
-}
-
-PP_Resource GetNonexistentFileRef(PP_Module module_id) {
- PluginModule* module = PluginModule::FromPPModule(module_id);
- if (!module)
- return static_cast<uint32_t>(-1);
- return FileRef::GetNonexistentFileRef(module)->GetReference();
-}
-
const PPB_Testing_Dev testing_interface = {
&ReadImageData,
&RunMessageLoop,
&QuitMessageLoop,
- &GetLiveObjectCount,
- &GetInaccessibleFileRef,
- &GetNonexistentFileRef
+ &GetLiveObjectCount
};
// GetInterface ----------------------------------------------------------------
@@ -204,8 +197,8 @@ const PPB_Testing_Dev testing_interface = {
const void* GetInterface(const char* name) {
if (strcmp(name, PPB_CORE_INTERFACE) == 0)
return &core_interface;
- if (strcmp(name, PPB_VAR_INTERFACE) == 0)
- return Var::GetInterface();
+ if (strcmp(name, PPB_VAR_DEPRECATED_INTERFACE) == 0)
+ return Var::GetDeprecatedInterface();
if (strcmp(name, PPB_INSTANCE_INTERFACE) == 0)
return PluginInstance::GetInterface();
if (strcmp(name, PPB_IMAGEDATA_INTERFACE) == 0)
@@ -272,6 +265,8 @@ const void* GetInterface(const char* name) {
return CharSet::GetInterface();
if (strcmp(name, PPB_CURSOR_CONTROL_DEV_INTERFACE) == 0)
return GetCursorControlInterface();
+ if (strcmp(name, PPB_ZOOM_DEV_INTERFACE) == 0)
+ return PluginInstance::GetZoomInterface();
// Only support the testing interface when the command line switch is
// specified. This allows us to prevent people from (ab)using this interface
@@ -288,6 +283,7 @@ const void* GetInterface(const char* name) {
PluginModule::PluginModule()
: initialized_(false),
library_(NULL) {
+ pp_module_ = ResourceTracker::Get()->AddModule(this);
GetMainThreadMessageLoop(); // Initialize the main thread message loop.
GetLivePluginSet()->insert(this);
}
@@ -315,6 +311,8 @@ PluginModule::~PluginModule() {
if (library_)
base::UnloadNativeLibrary(library_);
+
+ ResourceTracker::Get()->ModuleDeleted(pp_module_);
}
// static
@@ -339,14 +337,6 @@ scoped_refptr<PluginModule> PluginModule::CreateInternalModule(
}
// static
-PluginModule* PluginModule::FromPPModule(PP_Module module) {
- PluginModule* lib = reinterpret_cast<PluginModule*>(module);
- if (GetLivePluginSet()->find(lib) == GetLivePluginSet()->end())
- return NULL; // Invalid plugin.
- return lib;
-}
-
-// static
const PPB_Core* PluginModule::GetCore() {
return &core_interface;
}
@@ -356,7 +346,7 @@ bool PluginModule::InitFromEntryPoints(const EntryPoints& entry_points) {
return true;
// Attempt to run the initialization funciton.
- int retval = entry_points.initialize_module(GetPPModule(), &GetInterface);
+ int retval = entry_points.initialize_module(pp_module(), &GetInterface);
if (retval != 0) {
LOG(WARNING) << "PPP_InitializeModule returned failure " << retval;
return false;
@@ -420,10 +410,6 @@ bool PluginModule::LoadEntryPoints(const base::NativeLibrary& library,
return true;
}
-PP_Module PluginModule::GetPPModule() const {
- return reinterpret_cast<intptr_t>(this);
-}
-
PluginInstance* PluginModule::CreateInstance(PluginDelegate* delegate) {
const PPP_Instance* plugin_instance_interface =
reinterpret_cast<const PPP_Instance*>(GetPluginInterface(
diff --git a/webkit/glue/plugins/pepper_plugin_module.h b/webkit/glue/plugins/pepper_plugin_module.h
index a560c56..4ac13c3 100644
--- a/webkit/glue/plugins/pepper_plugin_module.h
+++ b/webkit/glue/plugins/pepper_plugin_module.h
@@ -27,6 +27,11 @@ class PluginDelegate;
class PluginInstance;
class PluginObject;
+// Represents one plugin library loaded into one renderer. This library may
+// have multiple instances.
+//
+// Note: to get from a PP_Instance to a PluginInstance*, use the
+// ResourceTracker.
class PluginModule : public base::RefCounted<PluginModule>,
public base::SupportsWeakPtr<PluginModule> {
public:
@@ -52,13 +57,12 @@ class PluginModule : public base::RefCounted<PluginModule>,
static scoped_refptr<PluginModule> CreateInternalModule(
EntryPoints entry_points);
- // Converts the given module ID to an actual module object. Will return NULL
- // if the module is invalid.
- static PluginModule* FromPPModule(PP_Module module);
-
static const PPB_Core* GetCore();
- PP_Module GetPPModule() const;
+ PP_Module pp_module() const { return pp_module_; }
+
+ void set_name(const std::string& name) { name_ = name; }
+ const std::string& name() const { return name_; }
PluginInstance* CreateInstance(PluginDelegate* delegate);
@@ -100,6 +104,8 @@ class PluginModule : public base::RefCounted<PluginModule>,
static bool LoadEntryPoints(const base::NativeLibrary& library,
EntryPoints* entry_points);
+ PP_Module pp_module_;
+
bool initialized_;
// Holds a reference to the base::NativeLibrary handle if this PluginModule
@@ -112,6 +118,9 @@ class PluginModule : public base::RefCounted<PluginModule>,
// implementation.
EntryPoints entry_points_;
+ // The name of the module.
+ std::string name_;
+
// Non-owning pointers to all instances associated with this module. When
// there are no more instances, this object should be deleted.
typedef std::set<PluginInstance*> PluginInstanceSet;
diff --git a/webkit/glue/plugins/pepper_plugin_object.cc b/webkit/glue/plugins/pepper_plugin_object.cc
index c0a7cd6..b655f83 100644
--- a/webkit/glue/plugins/pepper_plugin_object.cc
+++ b/webkit/glue/plugins/pepper_plugin_object.cc
@@ -10,9 +10,9 @@
#include "base/string_util.h"
#include "third_party/npapi/bindings/npapi.h"
#include "third_party/npapi/bindings/npruntime.h"
+#include "third_party/ppapi/c/dev/ppb_var_deprecated.h"
+#include "third_party/ppapi/c/dev/ppp_class_deprecated.h"
#include "third_party/ppapi/c/pp_var.h"
-#include "third_party/ppapi/c/ppb_var.h"
-#include "third_party/ppapi/c/ppp_class.h"
#include "third_party/WebKit/WebKit/chromium/public/WebBindings.h"
#include "webkit/glue/plugins/pepper_plugin_module.h"
#include "webkit/glue/plugins/pepper_string.h"
@@ -38,7 +38,7 @@ const char kInvalidPluginValue[] = "Error: Plugin returned invalid value.";
// an object.
bool PPVarToNPVariant(PP_Var var, NPVariant* result) {
switch (var.type) {
- case PP_VARTYPE_VOID:
+ case PP_VARTYPE_UNDEFINED:
VOID_TO_NPVARIANT(*result);
break;
case PP_VARTYPE_NULL:
@@ -139,7 +139,7 @@ class PPResultAndExceptionToNPResult {
NPVariant* np_result)
: object_var_(object_var),
np_result_(np_result),
- exception_(PP_MakeVoid()),
+ exception_(PP_MakeUndefined()),
success_(false),
checked_exception_(false) {
}
@@ -154,7 +154,7 @@ class PPResultAndExceptionToNPResult {
}
// Returns true if an exception has been set.
- bool has_exception() const { return exception_.type != PP_VARTYPE_VOID; }
+ bool has_exception() const { return exception_.type != PP_VARTYPE_UNDEFINED; }
// Returns a pointer to the exception. You would pass this to the PPAPI
// function as the exception parameter. If it is set to non-void, this object
@@ -267,11 +267,11 @@ class NPObjectAccessorWithIdentifier {
NPIdentifier identifier,
bool allow_integer_identifier)
: object_(PluginObject::FromNPObject(object)),
- identifier_(PP_MakeVoid()) {
+ identifier_(PP_MakeUndefined()) {
if (object_) {
identifier_ = Var::NPIdentifierToPPVar(object_->module(), identifier);
if (identifier_.type == PP_VARTYPE_INT32 && !allow_integer_identifier)
- identifier_.type = PP_VARTYPE_VOID; // Make the identifier invalid.
+ identifier_.type = PP_VARTYPE_UNDEFINED; // Mark it invalid.
}
}
@@ -281,7 +281,7 @@ class NPObjectAccessorWithIdentifier {
// Returns true if both the object and identifier are valid.
bool is_valid() const {
- return object_ && identifier_.type != PP_VARTYPE_VOID;
+ return object_ && identifier_.type != PP_VARTYPE_UNDEFINED;
}
PluginObject* object() { return object_; }
@@ -294,7 +294,7 @@ class NPObjectAccessorWithIdentifier {
DISALLOW_COPY_AND_ASSIGN(NPObjectAccessorWithIdentifier);
};
-// NPObject implementation in terms of PPP_Class -------------------------------
+// NPObject implementation in terms of PPP_Class_Deprecated --------------------
NPObject* WrapperClass_Allocate(NPP npp, NPClass* unused) {
return PluginObject::AllocateObjectWrapper();
@@ -349,7 +349,7 @@ bool WrapperClass_InvokeDefault(NPObject* np_object, const NPVariant* argv,
PPResultAndExceptionToNPResult result_converter(obj, result);
result_converter.SetResult(obj->ppp_class()->Call(
- obj->ppp_class_data(), PP_MakeVoid(), argc, args.array(),
+ obj->ppp_class_data(), PP_MakeUndefined(), argc, args.array(),
result_converter.exception()));
return result_converter.success();
}
@@ -518,7 +518,7 @@ struct PluginObject::NPObjectWrapper : public NPObject {
PluginObject::PluginObject(PluginModule* module,
NPObjectWrapper* object_wrapper,
- const PPP_Class* ppp_class,
+ const PPP_Class_Deprecated* ppp_class,
void* ppp_class_data)
: module_(module),
object_wrapper_(object_wrapper),
@@ -542,7 +542,7 @@ PluginObject::~PluginObject() {
}
PP_Var PluginObject::Create(PluginModule* module,
- const PPP_Class* ppp_class,
+ const PPP_Class_Deprecated* ppp_class,
void* ppp_class_data) {
// This will internally end up calling our AllocateObjectWrapper via the
// WrapperClass_Allocated function which will have created an object wrapper
@@ -568,7 +568,7 @@ NPObject* PluginObject::GetNPObject() const {
// static
bool PluginObject::IsInstanceOf(NPObject* np_object,
- const PPP_Class* ppp_class,
+ const PPP_Class_Deprecated* ppp_class,
void** ppp_class_data) {
// Validate that this object is implemented by our wrapper class before
// trying to get the PluginObject.
diff --git a/webkit/glue/plugins/pepper_plugin_object.h b/webkit/glue/plugins/pepper_plugin_object.h
index 7715a81..e31c1b1 100644
--- a/webkit/glue/plugins/pepper_plugin_object.h
+++ b/webkit/glue/plugins/pepper_plugin_object.h
@@ -10,7 +10,7 @@
#include "base/basictypes.h"
struct PP_Var;
-struct PPP_Class;
+struct PPP_Class_Deprecated;
typedef struct NPObject NPObject;
typedef struct _NPVariant NPVariant;
@@ -25,12 +25,12 @@ class PluginObject {
// Allocates a new PluginObject and returns it as a PP_Var with a
// refcount of 1.
static PP_Var Create(PluginModule* module,
- const PPP_Class* ppp_class,
+ const PPP_Class_Deprecated* ppp_class,
void* ppp_class_data);
PluginModule* module() const { return module_; }
- const PPP_Class* ppp_class() { return ppp_class_; }
+ const PPP_Class_Deprecated* ppp_class() { return ppp_class_; }
void* ppp_class_data() { return ppp_class_data_; };
NPObject* GetNPObject() const;
@@ -40,7 +40,7 @@ class PluginObject {
// returns true and places the class data into |*ppp_class_data| (which can
// optionally be NULL if no class data is desired).
static bool IsInstanceOf(NPObject* np_object,
- const PPP_Class* ppp_class,
+ const PPP_Class_Deprecated* ppp_class,
void** ppp_class_data);
// Converts the given NPObject to the corresponding ObjectVar.
@@ -65,7 +65,7 @@ class PluginObject {
// incremented on it, and this class will take ownership of that reference.
PluginObject(PluginModule* module,
NPObjectWrapper* object_wrapper,
- const PPP_Class* ppp_class,
+ const PPP_Class_Deprecated* ppp_class,
void* ppp_class_data);
PluginModule* module_;
@@ -78,7 +78,7 @@ class PluginObject {
// owns us.
NPObjectWrapper* object_wrapper_;
- const PPP_Class* ppp_class_;
+ const PPP_Class_Deprecated* ppp_class_;
void* ppp_class_data_;
DISALLOW_COPY_AND_ASSIGN(PluginObject);
diff --git a/webkit/glue/plugins/pepper_private.cc b/webkit/glue/plugins/pepper_private.cc
index e35006b..0bf5328 100644
--- a/webkit/glue/plugins/pepper_private.cc
+++ b/webkit/glue/plugins/pepper_private.cc
@@ -7,24 +7,34 @@
#include "webkit/glue/plugins/pepper_private.h"
#include "app/resource_bundle.h"
+#include "base/metrics/histogram.h"
#include "base/utf_string_conversions.h"
#include "grit/webkit_resources.h"
#include "grit/webkit_strings.h"
#include "skia/ext/platform_canvas.h"
+#include "third_party/ppapi/c/pp_resource.h"
#include "third_party/skia/include/core/SkBitmap.h"
+#include "third_party/icu/public/i18n/unicode/usearch.h"
#include "webkit/glue/webkit_glue.h"
#include "webkit/glue/plugins/pepper_image_data.h"
+#include "webkit/glue/plugins/pepper_plugin_delegate.h"
+#include "webkit/glue/plugins/pepper_plugin_instance.h"
#include "webkit/glue/plugins/pepper_plugin_module.h"
#include "webkit/glue/plugins/pepper_var.h"
#include "webkit/glue/plugins/ppb_private.h"
+#include "webkit/glue/plugins/pepper_var.h"
namespace pepper {
#if defined(OS_LINUX)
class PrivateFontFile : public Resource {
public:
- PrivateFontFile(PluginModule* module, int fd) : Resource(module), fd_(fd) {}
- virtual ~PrivateFontFile() {}
+ PrivateFontFile(PluginModule* module, int fd)
+ : Resource(module),
+ fd_(fd) {
+ }
+ virtual ~PrivateFontFile() {
+ }
// Resource overrides.
PrivateFontFile* AsPrivateFontFile() { return this; }
@@ -74,13 +84,18 @@ static const ResourceImageInfo kResourceImageMap[] = {
};
PP_Var GetLocalizedString(PP_Module module_id, PP_ResourceString string_id) {
- PluginModule* module = PluginModule::FromPPModule(module_id);
+ PluginModule* module = ResourceTracker::Get()->GetModule(module_id);
if (!module)
- return PP_MakeVoid();
+ return PP_MakeUndefined();
std::string rv;
- if (string_id == PP_RESOURCESTRING_PDFGETPASSWORD)
+ if (string_id == PP_RESOURCESTRING_PDFGETPASSWORD) {
rv = UTF16ToUTF8(webkit_glue::GetLocalizedString(IDS_PDF_NEED_PASSWORD));
+ } else if (string_id == PP_RESOURCESTRING_PDFLOADING) {
+ rv = UTF16ToUTF8(webkit_glue::GetLocalizedString(IDS_PDF_PAGE_LOADING));
+ } else {
+ NOTREACHED();
+ }
return StringVar::StringToPPVar(module, rv);
}
@@ -99,11 +114,11 @@ PP_Resource GetResourceImage(PP_Module module_id, PP_ResourceImage image_id) {
SkBitmap* res_bitmap =
ResourceBundle::GetSharedInstance().GetBitmapNamed(res_id);
- PluginModule* module = PluginModule::FromPPModule(module_id);
+ PluginModule* module = ResourceTracker::Get()->GetModule(module_id);
if (!module)
return 0;
scoped_refptr<pepper::ImageData> image_data(new pepper::ImageData(module));
- if (!image_data->Init(PP_IMAGEDATAFORMAT_BGRA_PREMUL,
+ if (!image_data->Init(ImageData::GetNativeImageDataFormat(),
res_bitmap->width(), res_bitmap->height(), false)) {
return 0;
}
@@ -124,16 +139,22 @@ PP_Resource GetResourceImage(PP_Module module_id, PP_ResourceImage image_id) {
PP_Resource GetFontFileWithFallback(
PP_Module module_id,
- const PP_PrivateFontFileDescription* description) {
+ const PP_FontDescription_Dev* description,
+ PP_PrivateFontCharset charset) {
#if defined(OS_LINUX)
- PluginModule* module = PluginModule::FromPPModule(module_id);
+ PluginModule* module = ResourceTracker::Get()->GetModule(module_id);
if (!module)
return 0;
- int fd = webkit_glue::MatchFontWithFallback(description->face,
- description->weight >= 700,
- description->italic,
- description->charset);
+ scoped_refptr<StringVar> face_name(StringVar::FromPPVar(description->face));
+ if (!face_name)
+ return 0;
+
+ int fd = webkit_glue::MatchFontWithFallback(
+ face_name->value().c_str(),
+ description->weight >= PP_FONTWEIGHT_BOLD,
+ description->italic,
+ charset);
if (fd == -1)
return 0;
@@ -162,11 +183,91 @@ bool GetFontTableForPrivateFontFile(PP_Resource font_file,
#endif
}
+void SearchString(PP_Module module,
+ const unsigned short* input_string,
+ const unsigned short* input_term,
+ bool case_sensitive,
+ PP_PrivateFindResult** results,
+ int* count) {
+ const char16* string = reinterpret_cast<const char16*>(input_string);
+ const char16* term = reinterpret_cast<const char16*>(input_term);
+
+ UErrorCode status = U_ZERO_ERROR;
+ UStringSearch* searcher = usearch_open(
+ term, -1, string, -1, webkit_glue::GetWebKitLocale().c_str(), 0,
+ &status);
+ DCHECK(status == U_ZERO_ERROR || status == U_USING_FALLBACK_WARNING ||
+ status == U_USING_DEFAULT_WARNING);
+ UCollationStrength strength = case_sensitive ? UCOL_TERTIARY : UCOL_PRIMARY;
+
+ UCollator* collator = usearch_getCollator(searcher);
+ if (ucol_getStrength(collator) != strength) {
+ ucol_setStrength(collator, strength);
+ usearch_reset(searcher);
+ }
+
+ status = U_ZERO_ERROR;
+ int match_start = usearch_first(searcher, &status);
+ DCHECK(status == U_ZERO_ERROR);
+
+ std::vector<PP_PrivateFindResult> pp_results;
+ while (match_start != USEARCH_DONE) {
+ size_t matched_length = usearch_getMatchedLength(searcher);
+ PP_PrivateFindResult result;
+ result.start_index = match_start;
+ result.length = matched_length;
+ pp_results.push_back(result);
+ match_start = usearch_next(searcher, &status);
+ DCHECK(status == U_ZERO_ERROR);
+ }
+
+ *count = pp_results.size();
+ if (*count) {
+ *results = reinterpret_cast<PP_PrivateFindResult*>(
+ malloc(*count * sizeof(PP_PrivateFindResult)));
+ memcpy(*results, &pp_results[0], *count * sizeof(PP_PrivateFindResult));
+ } else {
+ *results = NULL;
+ }
+
+ usearch_close(searcher);
+}
+
+void DidStartLoading(PP_Instance instance_id) {
+ PluginInstance* instance = ResourceTracker::Get()->GetInstance(instance_id);
+ if (!instance)
+ return;
+ instance->delegate()->DidStartLoading();
+}
+
+void DidStopLoading(PP_Instance instance_id) {
+ PluginInstance* instance = ResourceTracker::Get()->GetInstance(instance_id);
+ if (!instance)
+ return;
+ instance->delegate()->DidStopLoading();
+}
+
+void SetContentRestriction(PP_Instance instance_id, int restrictions) {
+ PluginInstance* instance = ResourceTracker::Get()->GetInstance(instance_id);
+ if (!instance)
+ return;
+ instance->delegate()->SetContentRestriction(restrictions);
+}
+
+void HistogramPDFPageCount(int count) {
+ UMA_HISTOGRAM_COUNTS_10000("PDF.PageCount", count);
+}
+
const PPB_Private ppb_private = {
&GetLocalizedString,
&GetResourceImage,
&GetFontFileWithFallback,
&GetFontTableForPrivateFontFile,
+ &SearchString,
+ &DidStartLoading,
+ &DidStopLoading,
+ &SetContentRestriction,
+ &HistogramPDFPageCount
};
} // namespace
diff --git a/webkit/glue/plugins/pepper_private2.cc b/webkit/glue/plugins/pepper_private2.cc
index 9a740aa..a96ef30 100644
--- a/webkit/glue/plugins/pepper_private2.cc
+++ b/webkit/glue/plugins/pepper_private2.cc
@@ -4,22 +4,223 @@
#include "webkit/glue/plugins/pepper_private2.h"
+#include <string.h>
+
+#include "base/file_path.h"
+#include "base/stringprintf.h"
+#include "base/utf_string_conversions.h"
+#include "googleurl/src/gurl.h"
+#include "third_party/ppapi/c/dev/pp_file_info_dev.h"
+#include "third_party/ppapi/c/dev/ppb_file_io_dev.h"
+#include "webkit/glue/plugins/pepper_error_util.h"
+#include "webkit/glue/plugins/pepper_plugin_delegate.h"
#include "webkit/glue/plugins/pepper_plugin_instance.h"
+#include "webkit/glue/plugins/pepper_plugin_module.h"
+#include "webkit/glue/plugins/pepper_var.h"
#include "webkit/glue/plugins/ppb_private2.h"
namespace pepper {
namespace {
+PluginInstance* GetSomeInstance(PP_Module pp_module) {
+ PluginModule* module = ResourceTracker::Get()->GetModule(pp_module);
+ if (!module)
+ return NULL;
+
+ return module->GetSomeInstance();
+}
+
void SetInstanceAlwaysOnTop(PP_Instance pp_instance, bool on_top) {
- PluginInstance* instance = PluginInstance::FromPPInstance(pp_instance);
+ PluginInstance* instance = ResourceTracker::Get()->GetInstance(pp_instance);
if (!instance)
return;
instance->set_always_on_top(on_top);
}
+PP_Var GetProxyForURL(PP_Module pp_module, const char* url) {
+ PluginInstance* instance = GetSomeInstance(pp_module);
+ if (!instance)
+ return PP_MakeUndefined();
+
+ GURL gurl(url);
+ if (!gurl.is_valid())
+ return PP_MakeUndefined();
+
+ std::string proxy_host = instance->delegate()->ResolveProxy(gurl);
+ if (proxy_host.empty())
+ return PP_MakeUndefined(); // No proxy.
+ return StringVar::StringToPPVar(instance->module(), proxy_host);
+}
+
+FilePath GetFilePathFromUTF8(const char* path) {
+#if defined(OS_WIN)
+ return FilePath(UTF8ToUTF16(path));
+#else
+ return FilePath(path);
+#endif
+}
+
+int32_t OpenModuleLocalFile(PP_Module module,
+ const char* path,
+ int32_t mode,
+ PP_FileHandle* file) {
+ PluginInstance* instance = GetSomeInstance(module);
+ if (!instance)
+ return PP_ERROR_FAILED;
+
+ int flags = 0;
+ if (mode & PP_FILEOPENFLAG_READ)
+ flags |= base::PLATFORM_FILE_READ;
+ if (mode & PP_FILEOPENFLAG_WRITE) {
+ flags |= base::PLATFORM_FILE_WRITE;
+ flags |= base::PLATFORM_FILE_WRITE_ATTRIBUTES;
+ }
+ if (mode & PP_FILEOPENFLAG_TRUNCATE) {
+ DCHECK(mode & PP_FILEOPENFLAG_WRITE);
+ flags |= base::PLATFORM_FILE_TRUNCATE;
+ }
+
+ if (mode & PP_FILEOPENFLAG_CREATE) {
+ if (mode & PP_FILEOPENFLAG_EXCLUSIVE)
+ flags |= base::PLATFORM_FILE_CREATE;
+ else
+ flags |= base::PLATFORM_FILE_OPEN_ALWAYS;
+ } else {
+ flags |= base::PLATFORM_FILE_OPEN;
+ }
+
+ base::PlatformFile base_file;
+ base::PlatformFileError result = instance->delegate()->OpenModuleLocalFile(
+ instance->module()->name(),
+ GetFilePathFromUTF8(path),
+ flags,
+ &base_file);
+ *file = base_file;
+ return PlatformFileErrorToPepperError(result);
+}
+
+
+int32_t RenameModuleLocalFile(PP_Module module,
+ const char* path_from,
+ const char* path_to) {
+ PluginInstance* instance = GetSomeInstance(module);
+ if (!instance)
+ return PP_ERROR_FAILED;
+
+ base::PlatformFileError result = instance->delegate()->RenameModuleLocalFile(
+ instance->module()->name(),
+ GetFilePathFromUTF8(path_from),
+ GetFilePathFromUTF8(path_to));
+ return PlatformFileErrorToPepperError(result);
+}
+
+int32_t DeleteModuleLocalFileOrDir(PP_Module module,
+ const char* path,
+ bool recursive) {
+ PluginInstance* instance = GetSomeInstance(module);
+ if (!instance)
+ return PP_ERROR_FAILED;
+
+ base::PlatformFileError result =
+ instance->delegate()->DeleteModuleLocalFileOrDir(
+ instance->module()->name(), GetFilePathFromUTF8(path), recursive);
+ return PlatformFileErrorToPepperError(result);
+}
+
+int32_t CreateModuleLocalDir(PP_Module module, const char* path) {
+ PluginInstance* instance = GetSomeInstance(module);
+ if (!instance)
+ return PP_ERROR_FAILED;
+
+ base::PlatformFileError result = instance->delegate()->CreateModuleLocalDir(
+ instance->module()->name(), GetFilePathFromUTF8(path));
+ return PlatformFileErrorToPepperError(result);
+}
+
+int32_t QueryModuleLocalFile(PP_Module module,
+ const char* path,
+ PP_FileInfo_Dev* info) {
+ PluginInstance* instance = GetSomeInstance(module);
+ if (!instance)
+ return PP_ERROR_FAILED;
+
+ base::PlatformFileInfo file_info;
+ base::PlatformFileError result = instance->delegate()->QueryModuleLocalFile(
+ instance->module()->name(), GetFilePathFromUTF8(path), &file_info);
+ if (result == base::PLATFORM_FILE_OK) {
+ info->size = file_info.size;
+ info->creation_time = file_info.creation_time.ToDoubleT();
+ info->last_access_time = file_info.last_accessed.ToDoubleT();
+ info->last_modified_time = file_info.last_modified.ToDoubleT();
+ info->system_type = PP_FILESYSTEMTYPE_EXTERNAL;
+ if (file_info.is_directory)
+ info->type = PP_FILETYPE_DIRECTORY;
+ else
+ info->type = PP_FILETYPE_REGULAR;
+ }
+ return PlatformFileErrorToPepperError(result);
+}
+
+int32_t GetModuleLocalDirContents(PP_Module module,
+ const char* path,
+ PP_DirContents_Dev** contents) {
+ PluginInstance* instance = GetSomeInstance(module);
+ if (!instance)
+ return PP_ERROR_FAILED;
+
+ *contents = NULL;
+ PepperDirContents pepper_contents;
+ base::PlatformFileError result =
+ instance->delegate()->GetModuleLocalDirContents(
+ instance->module()->name(),
+ GetFilePathFromUTF8(path),
+ &pepper_contents);
+
+ if (result != base::PLATFORM_FILE_OK)
+ return PlatformFileErrorToPepperError(result);
+
+ *contents = new PP_DirContents_Dev;
+ size_t count = pepper_contents.size();
+ (*contents)->count = count;
+ (*contents)->entries = new PP_DirEntry_Dev[count];
+ for (size_t i = 0; i < count; ++i) {
+ PP_DirEntry_Dev& entry = (*contents)->entries[i];
+#if defined(OS_WIN)
+ const std::string& name = UTF16ToUTF8(pepper_contents[i].name.value());
+#else
+ const std::string& name = pepper_contents[i].name.value();
+#endif
+ size_t size = name.size() + 1;
+ char* name_copy = new char[size];
+ memcpy(name_copy, name.c_str(), size);
+ entry.name = name_copy;
+ entry.is_dir = pepper_contents[i].is_dir;
+ }
+ return PP_OK;
+}
+
+void FreeModuleLocalDirContents(PP_Module module,
+ PP_DirContents_Dev* contents) {
+ DCHECK(contents);
+ for (int32_t i = 0; i < contents->count; ++i) {
+ delete [] contents->entries[i].name;
+ }
+ delete [] contents->entries;
+ delete contents;
+}
+
const PPB_Private2 ppb_private2 = {
- &SetInstanceAlwaysOnTop
+ &SetInstanceAlwaysOnTop,
+ &Private2::DrawGlyphs,
+ &GetProxyForURL,
+ &OpenModuleLocalFile,
+ &RenameModuleLocalFile,
+ &DeleteModuleLocalFileOrDir,
+ &CreateModuleLocalDir,
+ &QueryModuleLocalFile,
+ &GetModuleLocalDirContents,
+ &FreeModuleLocalDirContents,
};
} // namespace
diff --git a/webkit/glue/plugins/pepper_private2.h b/webkit/glue/plugins/pepper_private2.h
index 492669a..a8a4b6e 100644
--- a/webkit/glue/plugins/pepper_private2.h
+++ b/webkit/glue/plugins/pepper_private2.h
@@ -5,8 +5,12 @@
#ifndef WEBKIT_GLUE_PLUGINS_PEPPER_PRIVATE2_H_
#define WEBKIT_GLUE_PLUGINS_PEPPER_PRIVATE2_H_
+#include "build/build_config.h"
+#include "third_party/ppapi/c/pp_point.h"
+#include "third_party/ppapi/c/pp_rect.h"
#include "webkit/glue/plugins/pepper_resource.h"
+struct PP_FontDescription_Dev;
struct PPB_Private2;
namespace pepper {
@@ -16,6 +20,21 @@ class Private2 {
// Returns a pointer to the interface implementing PPB_Private2 that is
// exposed to the plugin.
static const PPB_Private2* GetInterface();
+
+ static bool DrawGlyphs(PP_Resource pp_image_data,
+ const PP_FontDescription_Dev* font_desc,
+ uint32_t color,
+ PP_Point position,
+ PP_Rect clip,
+ float transformation[3][3],
+ uint32_t glyph_count,
+ uint16_t glyph_indices[],
+ PP_Point glyph_advances[])
+#if defined(OS_LINUX)
+ ;
+#else
+ { return false; }
+#endif
};
} // namespace pepper
diff --git a/webkit/glue/plugins/pepper_private2_linux.cc b/webkit/glue/plugins/pepper_private2_linux.cc
new file mode 100644
index 0000000..4beb6b6
--- /dev/null
+++ b/webkit/glue/plugins/pepper_private2_linux.cc
@@ -0,0 +1,110 @@
+// Copyright (c) 2010 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "webkit/glue/plugins/pepper_private2.h"
+
+#include "skia/ext/platform_canvas.h"
+#include "third_party/ppapi/c/pp_point.h"
+#include "third_party/ppapi/c/pp_rect.h"
+#include "third_party/ppapi/c/dev/ppb_font_dev.h"
+#include "third_party/skia/include/core/SkCanvas.h"
+#include "third_party/skia/include/core/SkMatrix.h"
+#include "third_party/skia/include/core/SkPaint.h"
+#include "third_party/skia/include/core/SkPoint.h"
+#include "third_party/skia/include/core/SkTemplates.h"
+#include "third_party/skia/include/core/SkTypeface.h"
+#include "webkit/glue/plugins/pepper_image_data.h"
+#include "webkit/glue/plugins/pepper_var.h"
+
+namespace pepper {
+
+bool Private2::DrawGlyphs(PP_Resource pp_image_data,
+ const PP_FontDescription_Dev* font_desc,
+ uint32_t color,
+ PP_Point position,
+ PP_Rect clip,
+ float transformation[3][3],
+ uint32_t glyph_count,
+ uint16_t glyph_indices[],
+ PP_Point glyph_advances[]) {
+ scoped_refptr<ImageData> image_resource(
+ Resource::GetAs<ImageData>(pp_image_data));
+ if (!image_resource.get())
+ return false;
+ ImageDataAutoMapper mapper(image_resource);
+ if (!mapper.is_valid())
+ return false;
+
+ // Set up the typeface.
+ scoped_refptr<StringVar> face_name(StringVar::FromPPVar(font_desc->face));
+ if (!face_name)
+ return false;
+ int style = SkTypeface::kNormal;
+ if (font_desc->weight >= PP_FONTWEIGHT_BOLD)
+ style |= SkTypeface::kBold;
+ if (font_desc->italic)
+ style |= SkTypeface::kItalic;
+ SkTypeface* typeface =
+ SkTypeface::CreateFromName(face_name->value().c_str(),
+ static_cast<SkTypeface::Style>(style));
+ if (!typeface)
+ return false;
+
+ // Set up the canvas.
+ SkCanvas* canvas = image_resource->mapped_canvas();
+ canvas->save();
+
+ // Clip is applied in pixels before the transform.
+ SkRect clip_rect = { clip.point.x, clip.point.y,
+ clip.point.x + clip.size.width,
+ clip.point.y + clip.size.height };
+ canvas->clipRect(clip_rect);
+
+ // -- Do not return early below this. The canvas needs restoring and the
+ // typeface will leak if it's not assigned to the paint (it's refcounted and
+ // the refcount is currently 0).
+
+ // Convert & set the matrix.
+ SkMatrix matrix;
+ matrix.set(SkMatrix::kMScaleX, SkFloatToScalar(transformation[0][0]));
+ matrix.set(SkMatrix::kMSkewX, SkFloatToScalar(transformation[0][1]));
+ matrix.set(SkMatrix::kMTransX, SkFloatToScalar(transformation[0][2]));
+ matrix.set(SkMatrix::kMSkewY, SkFloatToScalar(transformation[1][0]));
+ matrix.set(SkMatrix::kMScaleY, SkFloatToScalar(transformation[1][1]));
+ matrix.set(SkMatrix::kMTransY, SkFloatToScalar(transformation[1][2]));
+ matrix.set(SkMatrix::kMPersp0, SkFloatToScalar(transformation[2][0]));
+ matrix.set(SkMatrix::kMPersp1, SkFloatToScalar(transformation[2][1]));
+ matrix.set(SkMatrix::kMPersp2, SkFloatToScalar(transformation[2][2]));
+ canvas->concat(matrix);
+
+ SkPaint paint;
+ paint.setColor(color);
+ paint.setTextEncoding(SkPaint::kGlyphID_TextEncoding);
+ paint.setAntiAlias(true);
+ paint.setHinting(SkPaint::kFull_Hinting);
+ paint.setTextSize(SkIntToScalar(font_desc->size));
+ paint.setTypeface(typeface); // Takes a ref and manages lifetime.
+ paint.setSubpixelText(true);
+ paint.setLCDRenderText(true);
+
+ SkScalar x = SkIntToScalar(position.x);
+ SkScalar y = SkIntToScalar(position.y);
+
+ // Build up the skia advances.
+ SkAutoSTMalloc<32, SkPoint> storage(glyph_count);
+ SkPoint* sk_positions = storage.get();
+ for (uint32_t i = 0; i < glyph_count; i++) {
+ sk_positions[i].set(x, y);
+ x += SkFloatToScalar(glyph_advances[i].x);
+ y += SkFloatToScalar(glyph_advances[i].y);
+ }
+
+ canvas->drawPosText(glyph_indices, glyph_count * 2, sk_positions, paint);
+
+ canvas->restore();
+ return true;
+}
+
+} // namespace pepper
+
diff --git a/webkit/glue/plugins/pepper_resource.h b/webkit/glue/plugins/pepper_resource.h
index cab6f32..32dbf0b 100644
--- a/webkit/glue/plugins/pepper_resource.h
+++ b/webkit/glue/plugins/pepper_resource.h
@@ -12,29 +12,37 @@
namespace pepper {
-class Buffer;
-class Audio;
-class AudioConfig;
-class DirectoryReader;
-class FileChooser;
-class FileIO;
-class FileRef;
-class Font;
-class Graphics2D;
-class Graphics3D;
-class ImageData;
-class ObjectVar;
-class PluginModule;
-class PrivateFontFile;
-class Scrollbar;
-class StringVar;
-class Transport;
-class URLLoader;
-class URLRequestInfo;
-class URLResponseInfo;
-class Var;
-class VideoDecoder;
-class Widget;
+// If you inherit from resource, make sure you add the class name here.
+#define FOR_ALL_RESOURCES(F) \
+ F(Audio) \
+ F(AudioConfig) \
+ F(Buffer) \
+ F(DirectoryReader) \
+ F(FileChooser) \
+ F(FileIO) \
+ F(FileRef) \
+ F(FileSystem) \
+ F(Font) \
+ F(Graphics2D) \
+ F(Graphics3D) \
+ F(ImageData) \
+ F(ObjectVar) \
+ F(PluginModule) \
+ F(PrivateFontFile) \
+ F(Scrollbar) \
+ F(StringVar) \
+ F(Transport) \
+ F(URLLoader) \
+ F(URLRequestInfo) \
+ F(URLResponseInfo) \
+ F(Var) \
+ F(VideoDecoder) \
+ F(Widget)
+
+// Forward declaration of Resource classes.
+#define DECLARE_RESOURCE_CLASS(RESOURCE) class RESOURCE;
+FOR_ALL_RESOURCES(DECLARE_RESOURCE_CLASS)
+#undef DECLARE_RESOURCE_CLASS
class Resource : public base::RefCountedThreadSafe<Resource> {
public:
@@ -80,28 +88,10 @@ class Resource : public base::RefCountedThreadSafe<Resource> {
// Type-specific getters for individual resource types. These will return
// NULL if the resource does not match the specified type. Used by the Cast()
// function.
- virtual Audio* AsAudio() { return NULL; }
- virtual AudioConfig* AsAudioConfig() { return NULL; }
- virtual Buffer* AsBuffer() { return NULL; }
- virtual DirectoryReader* AsDirectoryReader() { return NULL; }
- virtual FileChooser* AsFileChooser() { return NULL; }
- virtual FileIO* AsFileIO() { return NULL; }
- virtual FileRef* AsFileRef() { return NULL; }
- virtual Font* AsFont() { return NULL; }
- virtual Graphics2D* AsGraphics2D() { return NULL; }
- virtual Graphics3D* AsGraphics3D() { return NULL; }
- virtual ImageData* AsImageData() { return NULL; }
- virtual ObjectVar* AsObjectVar() { return NULL; }
- virtual PrivateFontFile* AsPrivateFontFile() { return NULL; }
- virtual Scrollbar* AsScrollbar() { return NULL; }
- virtual StringVar* AsStringVar() { return NULL; }
- virtual Transport* AsTransport() { return NULL; }
- virtual URLLoader* AsURLLoader() { return NULL; }
- virtual URLRequestInfo* AsURLRequestInfo() { return NULL; }
- virtual URLResponseInfo* AsURLResponseInfo() { return NULL; }
- virtual Var* AsVar() { return NULL; }
- virtual VideoDecoder* AsVideoDecoder() { return NULL; }
- virtual Widget* AsWidget() { return NULL; }
+ #define DEFINE_TYPE_GETTER(RESOURCE) \
+ virtual RESOURCE* As##RESOURCE() { return NULL; }
+ FOR_ALL_RESOURCES(DEFINE_TYPE_GETTER)
+ #undef DEFINE_TYPE_GETTER
private:
// If referenced by a plugin, holds the id of this resource object. Do not
@@ -129,30 +119,10 @@ class Resource : public base::RefCountedThreadSafe<Resource> {
return As##Type(); \
}
-DEFINE_RESOURCE_CAST(Audio)
-DEFINE_RESOURCE_CAST(AudioConfig)
-DEFINE_RESOURCE_CAST(Buffer)
-DEFINE_RESOURCE_CAST(DirectoryReader)
-DEFINE_RESOURCE_CAST(FileChooser)
-DEFINE_RESOURCE_CAST(FileIO)
-DEFINE_RESOURCE_CAST(FileRef)
-DEFINE_RESOURCE_CAST(Font)
-DEFINE_RESOURCE_CAST(Graphics2D)
-DEFINE_RESOURCE_CAST(Graphics3D)
-DEFINE_RESOURCE_CAST(ImageData)
-DEFINE_RESOURCE_CAST(ObjectVar)
-DEFINE_RESOURCE_CAST(PrivateFontFile)
-DEFINE_RESOURCE_CAST(Scrollbar)
-DEFINE_RESOURCE_CAST(StringVar);
-DEFINE_RESOURCE_CAST(Transport)
-DEFINE_RESOURCE_CAST(URLLoader)
-DEFINE_RESOURCE_CAST(URLRequestInfo)
-DEFINE_RESOURCE_CAST(URLResponseInfo)
-DEFINE_RESOURCE_CAST(Var)
-DEFINE_RESOURCE_CAST(VideoDecoder)
-DEFINE_RESOURCE_CAST(Widget)
-
+FOR_ALL_RESOURCES(DEFINE_RESOURCE_CAST)
#undef DEFINE_RESOURCE_CAST
+
+#undef FOR_ALL_RESOURCES
} // namespace pepper
#endif // WEBKIT_GLUE_PLUGINS_PEPPER_RESOURCE_H_
diff --git a/webkit/glue/plugins/pepper_resource_tracker.cc b/webkit/glue/plugins/pepper_resource_tracker.cc
index 9ee54f8..2e18cd8 100644
--- a/webkit/glue/plugins/pepper_resource_tracker.cc
+++ b/webkit/glue/plugins/pepper_resource_tracker.cc
@@ -8,6 +8,7 @@
#include <set>
#include "base/logging.h"
+#include "base/rand_util.h"
#include "third_party/ppapi/c/pp_resource.h"
#include "webkit/glue/plugins/pepper_resource.h"
@@ -79,4 +80,78 @@ uint32 ResourceTracker::GetLiveObjectsForModule(PluginModule* module) const {
return count;
}
+PP_Instance ResourceTracker::AddInstance(PluginInstance* instance) {
+#ifndef NDEBUG
+ // Make sure we're not adding one more than once.
+ for (InstanceMap::const_iterator i = instance_map_.begin();
+ i != instance_map_.end(); ++i)
+ DCHECK(i->second != instance);
+#endif
+
+ // Use a random 64-bit number for the instance ID. This helps prevent some
+ // mischeif where you could misallocate resources if you gave a different
+ // instance ID.
+ //
+ // See also AddModule below.
+ //
+ // Need to make sure the random number isn't a duplicate or 0.
+ PP_Instance new_instance;
+ do {
+ new_instance = static_cast<PP_Instance>(base::RandUint64());
+ } while (!new_instance ||
+ instance_map_.find(new_instance) != instance_map_.end());
+ instance_map_[new_instance] = instance;
+ return new_instance;
+}
+
+void ResourceTracker::InstanceDeleted(PP_Instance instance) {
+ InstanceMap::iterator found = instance_map_.find(instance);
+ if (found == instance_map_.end()) {
+ NOTREACHED();
+ return;
+ }
+ instance_map_.erase(found);
+}
+
+PluginInstance* ResourceTracker::GetInstance(PP_Instance instance) {
+ InstanceMap::iterator found = instance_map_.find(instance);
+ if (found == instance_map_.end())
+ return NULL;
+ return found->second;
+}
+
+PP_Module ResourceTracker::AddModule(PluginModule* module) {
+#ifndef NDEBUG
+ // Make sure we're not adding one more than once.
+ for (ModuleMap::const_iterator i = module_map_.begin();
+ i != module_map_.end(); ++i)
+ DCHECK(i->second != module);
+#endif
+
+ // See AddInstance above.
+ PP_Module new_module;
+ do {
+ new_module = static_cast<PP_Module>(base::RandUint64());
+ } while (!new_module ||
+ module_map_.find(new_module) != module_map_.end());
+ module_map_[new_module] = module;
+ return new_module;
+}
+
+void ResourceTracker::ModuleDeleted(PP_Module module) {
+ ModuleMap::iterator found = module_map_.find(module);
+ if (found == module_map_.end()) {
+ NOTREACHED();
+ return;
+ }
+ module_map_.erase(found);
+}
+
+PluginModule* ResourceTracker::GetModule(PP_Module module) {
+ ModuleMap::iterator found = module_map_.find(module);
+ if (found == module_map_.end())
+ return NULL;
+ return found->second;
+}
+
} // namespace pepper
diff --git a/webkit/glue/plugins/pepper_resource_tracker.h b/webkit/glue/plugins/pepper_resource_tracker.h
index 59f02d2..5c27ebd 100644
--- a/webkit/glue/plugins/pepper_resource_tracker.h
+++ b/webkit/glue/plugins/pepper_resource_tracker.h
@@ -5,18 +5,22 @@
#ifndef WEBKIT_GLUE_PLUGINS_PEPPER_RESOURCE_TRACKER_H_
#define WEBKIT_GLUE_PLUGINS_PEPPER_RESOURCE_TRACKER_H_
+#include <map>
#include <utility>
#include "base/basictypes.h"
#include "base/hash_tables.h"
#include "base/ref_counted.h"
#include "base/singleton.h"
+#include "third_party/ppapi/c/pp_instance.h"
+#include "third_party/ppapi/c/pp_module.h"
#include "third_party/ppapi/c/pp_resource.h"
typedef struct NPObject NPObject;
namespace pepper {
+class PluginInstance;
class PluginModule;
class Resource;
@@ -31,6 +35,8 @@ class ResourceTracker {
return Singleton<ResourceTracker>::get();
}
+ // PP_Resources --------------------------------------------------------------
+
// The returned pointer will be NULL if there is no resource. Note that this
// return value is a scoped_refptr so that we ensure the resource is valid
// from the point of the lookup to the point that the calling code needs it.
@@ -48,6 +54,34 @@ class ResourceTracker {
// This is slow, use only for testing.
uint32 GetLiveObjectsForModule(PluginModule* module) const;
+ // PP_Modules ----------------------------------------------------------------
+
+ // Adds a new plugin module to the list of tracked module, and returns a new
+ // module handle to identify it.
+ PP_Module AddModule(PluginModule* module);
+
+ // Called when a plugin modulde was deleted and should no longer be tracked.
+ // The given handle should be one generated by AddModule.
+ void ModuleDeleted(PP_Module module);
+
+ // Returns a pointer to the plugin modulde object associated with the given
+ // modulde handle. The return value will be NULL if the handle is invalid.
+ PluginModule* GetModule(PP_Module module);
+
+ // PP_Instances --------------------------------------------------------------
+
+ // Adds a new plugin instance to the list of tracked instances, and returns a
+ // new instance handle to identify it.
+ PP_Instance AddInstance(PluginInstance* instance);
+
+ // Called when a plugin instance was deleted and should no longer be tracked.
+ // The given handle should be one generated by AddInstance.
+ void InstanceDeleted(PP_Instance instance);
+
+ // Returns a pointer to the plugin instance object associated with the given
+ // instance handle. The return value will be NULL if the handle is invalid.
+ PluginInstance* GetInstance(PP_Instance instance);
+
private:
friend struct DefaultSingletonTraits<ResourceTracker>;
friend class Resource;
@@ -74,6 +108,16 @@ class ResourceTracker {
typedef base::hash_map<PP_Resource, ResourceAndRefCount> ResourceMap;
ResourceMap live_resources_;
+ // Tracks all live instances. The pointers are non-owning, the PluginInstance
+ // destructor will notify us when the instance is deleted.
+ typedef std::map<PP_Instance, PluginInstance*> InstanceMap;
+ InstanceMap instance_map_;
+
+ // Tracks all live modules. The pointers are non-owning, the PluginModule
+ // destructor will notify us when the module is deleted.
+ typedef std::map<PP_Module, PluginModule*> ModuleMap;
+ ModuleMap module_map_;
+
DISALLOW_COPY_AND_ASSIGN(ResourceTracker);
};
diff --git a/webkit/glue/plugins/pepper_scrollbar.cc b/webkit/glue/plugins/pepper_scrollbar.cc
index a8943d2..88a3f9b 100644
--- a/webkit/glue/plugins/pepper_scrollbar.cc
+++ b/webkit/glue/plugins/pepper_scrollbar.cc
@@ -19,7 +19,7 @@
#include "webkit/glue/webkit_glue.h"
#if defined(OS_WIN)
-#include "base/win_util.h"
+#include "base/win/windows_version.h"
#endif
using WebKit::WebInputEvent;
@@ -31,7 +31,7 @@ namespace pepper {
namespace {
PP_Resource Create(PP_Instance instance_id, bool vertical) {
- PluginInstance* instance = PluginInstance::FromPPInstance(instance_id);
+ PluginInstance* instance = ResourceTracker::Get()->GetInstance(instance_id);
if (!instance)
return 0;
@@ -164,7 +164,7 @@ bool Scrollbar::Paint(const PP_Rect* rect, ImageData* image) {
scrollbar_->paint(webkit_glue::ToWebCanvas(canvas), gfx_rect);
#if defined(OS_WIN)
- if (win_util::GetWinVersion() == win_util::WINVERSION_XP) {
+ if (base::win::GetVersion() == base::win::VERSION_XP) {
canvas->getTopPlatformDevice().makeOpaque(
gfx_rect.x(), gfx_rect.y(), gfx_rect.width(), gfx_rect.height());
}
@@ -196,7 +196,7 @@ void Scrollbar::valueChanged(WebKit::WebScrollbar* scrollbar) {
return;
ScopedResourceId resource(this);
ppp_scrollbar->ValueChanged(
- instance()->GetPPInstance(), resource.id, scrollbar_->value());
+ instance()->pp_instance(), resource.id, scrollbar_->value());
}
void Scrollbar::invalidateScrollbarRect(WebKit::WebScrollbar* scrollbar,
diff --git a/webkit/glue/plugins/pepper_string.cc b/webkit/glue/plugins/pepper_string.cc
new file mode 100644
index 0000000..53c8943
--- /dev/null
+++ b/webkit/glue/plugins/pepper_string.cc
@@ -0,0 +1,13 @@
+// Copyright (c) 2010 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "webkit/glue/plugins/pepper_string.h"
+
+namespace pepper {
+
+String::String(const char* str, uint32 len) : value_(str, len) {}
+
+String::~String() {}
+
+} // namespace pepper
diff --git a/webkit/glue/plugins/pepper_string.h b/webkit/glue/plugins/pepper_string.h
index 1fc43c4..fa1ab2f 100644
--- a/webkit/glue/plugins/pepper_string.h
+++ b/webkit/glue/plugins/pepper_string.h
@@ -14,8 +14,8 @@ namespace pepper {
class String : public base::RefCountedThreadSafe<String> {
public:
- String(const char* str, uint32 len) : value_(str, len) {
- }
+ String(const char* str, uint32 len);
+ virtual ~String();
const std::string& value() const { return value_; }
diff --git a/webkit/glue/plugins/pepper_url_loader.cc b/webkit/glue/plugins/pepper_url_loader.cc
index 4169c00..62fe176 100644
--- a/webkit/glue/plugins/pepper_url_loader.cc
+++ b/webkit/glue/plugins/pepper_url_loader.cc
@@ -40,12 +40,11 @@ namespace pepper {
namespace {
PP_Resource Create(PP_Instance instance_id) {
- PluginInstance* instance = PluginInstance::FromPPInstance(instance_id);
+ PluginInstance* instance = ResourceTracker::Get()->GetInstance(instance_id);
if (!instance)
return 0;
- URLLoader* loader = new URLLoader(instance);
-
+ URLLoader* loader = new URLLoader(instance, false);
return loader->GetReference();
}
@@ -168,9 +167,10 @@ const PPB_URLLoaderTrusted_Dev ppb_urlloadertrusted = {
} // namespace
-URLLoader::URLLoader(PluginInstance* instance)
+URLLoader::URLLoader(PluginInstance* instance, bool main_document_loader)
: Resource(instance->module()),
instance_(instance),
+ main_document_loader_(main_document_loader),
pending_callback_(),
bytes_sent_(0),
total_bytes_to_be_sent_(-1),
@@ -217,10 +217,8 @@ int32_t URLLoader::Open(URLRequestInfo* request,
frame->dispatchWillSendRequest(web_request);
loader_.reset(WebKit::webKitClient()->createURLLoader());
- if (!loader_.get()) {
- loader_.reset();
+ if (!loader_.get())
return PP_ERROR_FAILED;
- }
loader_->loadAsynchronously(web_request, this);
pending_callback_ = callback;
@@ -280,7 +278,12 @@ int32_t URLLoader::FinishStreamingToFile(PP_CompletionCallback callback) {
}
void URLLoader::Close() {
- NOTIMPLEMENTED(); // TODO(darin): Implement me.
+ if (loader_.get()) {
+ loader_->cancel();
+ } else if (main_document_loader_) {
+ WebFrame* frame = instance_->container()->element().document().frame();
+ frame->stopLoading();
+ }
}
void URLLoader::GrantUniversalAccess() {
diff --git a/webkit/glue/plugins/pepper_url_loader.h b/webkit/glue/plugins/pepper_url_loader.h
index 4919de7..e613475 100644
--- a/webkit/glue/plugins/pepper_url_loader.h
+++ b/webkit/glue/plugins/pepper_url_loader.h
@@ -24,7 +24,7 @@ class URLResponseInfo;
class URLLoader : public Resource, public WebKit::WebURLLoaderClient {
public:
- explicit URLLoader(PluginInstance* instance);
+ URLLoader(PluginInstance* instance, bool main_document_loader);
virtual ~URLLoader();
// Returns a pointer to the interface implementing PPB_URLLoader that is
@@ -83,6 +83,9 @@ class URLLoader : public Resource, public WebKit::WebURLLoaderClient {
size_t FillUserBuffer();
scoped_refptr<PluginInstance> instance_;
+ // If true, then the plugin instance is a full-frame plugin and we're just
+ // wrapping the main document's loader (i.e. loader_ is null).
+ bool main_document_loader_;
scoped_ptr<WebKit::WebURLLoader> loader_;
scoped_refptr<URLResponseInfo> response_info_;
PP_CompletionCallback pending_callback_;
diff --git a/webkit/glue/plugins/pepper_url_request_info.cc b/webkit/glue/plugins/pepper_url_request_info.cc
index 4edbe83..dd8f7a6 100644
--- a/webkit/glue/plugins/pepper_url_request_info.cc
+++ b/webkit/glue/plugins/pepper_url_request_info.cc
@@ -47,7 +47,7 @@ bool IsIgnoredRequestHeader(const std::string& name) {
}
PP_Resource Create(PP_Module module_id) {
- PluginModule* module = PluginModule::FromPPModule(module_id);
+ PluginModule* module = ResourceTracker::Get()->GetModule(module_id);
if (!module)
return 0;
@@ -80,17 +80,13 @@ bool SetProperty(PP_Resource request_id,
return false;
}
-bool AppendDataToBody(PP_Resource request_id, PP_Var var) {
+bool AppendDataToBody(PP_Resource request_id, const char* data, uint32_t len) {
scoped_refptr<URLRequestInfo> request(
Resource::GetAs<URLRequestInfo>(request_id));
if (!request)
return false;
- scoped_refptr<StringVar> data(StringVar::FromPPVar(var));
- if (!data)
- return false;
-
- return request->AppendDataToBody(data->value());
+ return request->AppendDataToBody(std::string(data, len));
}
bool AppendFileToBody(PP_Resource request_id,
@@ -123,6 +119,31 @@ const PPB_URLRequestInfo_Dev ppb_urlrequestinfo = {
} // namespace
+struct URLRequestInfo::BodyItem {
+ BodyItem(const std::string& data)
+ : data(data),
+ start_offset(0),
+ number_of_bytes(-1),
+ expected_last_modified_time(0.0) {
+ }
+
+ BodyItem(FileRef* file_ref,
+ int64_t start_offset,
+ int64_t number_of_bytes,
+ PP_Time expected_last_modified_time)
+ : file_ref(file_ref),
+ start_offset(start_offset),
+ number_of_bytes(number_of_bytes),
+ expected_last_modified_time(expected_last_modified_time) {
+ }
+
+ std::string data;
+ scoped_refptr<FileRef> file_ref;
+ int64_t start_offset;
+ int64_t number_of_bytes;
+ PP_Time expected_last_modified_time;
+};
+
URLRequestInfo::URLRequestInfo(PluginModule* module)
: Resource(module),
stream_to_file_(false) {
@@ -217,7 +238,8 @@ WebURLRequest URLRequestInfo::ToWebURLRequest(WebFrame* frame) const {
for (size_t i = 0; i < body_.size(); ++i) {
if (body_[i].file_ref) {
http_body.appendFileRange(
- webkit_glue::FilePathToWebString(body_[i].file_ref->system_path()),
+ webkit_glue::FilePathToWebString(
+ body_[i].file_ref->GetSystemPath()),
body_[i].start_offset,
body_[i].number_of_bytes,
body_[i].expected_last_modified_time);
diff --git a/webkit/glue/plugins/pepper_url_request_info.h b/webkit/glue/plugins/pepper_url_request_info.h
index 7220531..2d394d5 100644
--- a/webkit/glue/plugins/pepper_url_request_info.h
+++ b/webkit/glue/plugins/pepper_url_request_info.h
@@ -45,31 +45,7 @@ class URLRequestInfo : public Resource {
WebKit::WebURLRequest ToWebURLRequest(WebKit::WebFrame* frame) const;
private:
- struct BodyItem {
- BodyItem(const std::string& data)
- : data(data),
- start_offset(0),
- number_of_bytes(-1),
- expected_last_modified_time(0.0) {
- }
-
- BodyItem(FileRef* file_ref,
- int64_t start_offset,
- int64_t number_of_bytes,
- PP_Time expected_last_modified_time)
- : file_ref(file_ref),
- start_offset(start_offset),
- number_of_bytes(number_of_bytes),
- expected_last_modified_time(expected_last_modified_time) {
- }
-
- std::string data;
- scoped_refptr<FileRef> file_ref;
- int64_t start_offset;
- int64_t number_of_bytes;
- PP_Time expected_last_modified_time;
- };
-
+ struct BodyItem;
typedef std::vector<BodyItem> Body;
std::string url_;
diff --git a/webkit/glue/plugins/pepper_url_response_info.cc b/webkit/glue/plugins/pepper_url_response_info.cc
index 79042ba..8af3385 100644
--- a/webkit/glue/plugins/pepper_url_response_info.cc
+++ b/webkit/glue/plugins/pepper_url_response_info.cc
@@ -47,7 +47,7 @@ PP_Var GetProperty(PP_Resource response_id,
scoped_refptr<URLResponseInfo> response(
Resource::GetAs<URLResponseInfo>(response_id));
if (!response)
- return PP_MakeVoid();
+ return PP_MakeUndefined();
return response->GetProperty(property);
}
@@ -97,7 +97,7 @@ PP_Var URLResponseInfo::GetProperty(PP_URLResponseProperty_Dev property) {
return StringVar::StringToPPVar(module(), headers_);
default:
NOTIMPLEMENTED(); // TODO(darin): Implement me!
- return PP_MakeVoid();
+ return PP_MakeUndefined();
}
}
diff --git a/webkit/glue/plugins/pepper_url_util.cc b/webkit/glue/plugins/pepper_url_util.cc
index 3f9a54f..a182b92 100644
--- a/webkit/glue/plugins/pepper_url_util.cc
+++ b/webkit/glue/plugins/pepper_url_util.cc
@@ -60,7 +60,7 @@ PP_Var GenerateUrlReturn(PluginModule* module, const GURL& url,
// unchanged.
bool SecurityOriginForInstance(PP_Instance instance_id,
WebKit::WebSecurityOrigin* security_origin) {
- PluginInstance* instance = PluginInstance::FromPPInstance(instance_id);
+ PluginInstance* instance = ResourceTracker::Get()->GetInstance(instance_id);
if (!instance)
return false;
@@ -100,7 +100,7 @@ PP_Var ResolveRelativeToUrl(PP_Var base_url,
PP_Var ResolveRelativeToDocument(PP_Instance instance_id,
PP_Var relative,
PP_UrlComponents_Dev* components) {
- PluginInstance* instance = PluginInstance::FromPPInstance(instance_id);
+ PluginInstance* instance = ResourceTracker::Get()->GetInstance(instance_id);
if (!instance)
return PP_MakeNull();
diff --git a/webkit/glue/plugins/pepper_var.cc b/webkit/glue/plugins/pepper_var.cc
index b4ba014..6daece9 100644
--- a/webkit/glue/plugins/pepper_var.cc
+++ b/webkit/glue/plugins/pepper_var.cc
@@ -7,8 +7,8 @@
#include "base/logging.h"
#include "base/scoped_ptr.h"
#include "base/string_util.h"
+#include "third_party/ppapi/c/dev/ppb_var_deprecated.h"
#include "third_party/ppapi/c/pp_var.h"
-#include "third_party/ppapi/c/ppb_var.h"
#include "third_party/WebKit/WebKit/chromium/public/WebBindings.h"
#include "webkit/glue/plugins/pepper_plugin_module.h"
#include "webkit/glue/plugins/pepper_plugin_object.h"
@@ -43,7 +43,7 @@ const char kUnableToConstructException[] = "Error: Unable to construct";
// the PP_Var remains valid while the resultant NPVariant is in use.
bool PPVarToNPVariantNoCopy(PP_Var var, NPVariant* result) {
switch (var.type) {
- case PP_VARTYPE_VOID:
+ case PP_VARTYPE_UNDEFINED:
VOID_TO_NPVARIANT(*result);
break;
case PP_VARTYPE_NULL:
@@ -157,7 +157,7 @@ class ObjectAccessorWithIdentifierTryCatch : public ObjectAccessorTryCatch {
// PPB_Var methods -------------------------------------------------------------
PP_Var VarFromUtf8(PP_Module module_id, const char* data, uint32_t len) {
- PluginModule* module = PluginModule::FromPPModule(module_id);
+ PluginModule* module = ResourceTracker::Get()->GetModule(module_id);
if (!module)
return PP_MakeNull();
return StringVar::StringToPPVar(module, data, len);
@@ -185,9 +185,9 @@ bool HasProperty(PP_Var var,
accessor.identifier());
}
-bool HasMethod(PP_Var var,
- PP_Var name,
- PP_Var* exception) {
+bool HasMethodDeprecated(PP_Var var,
+ PP_Var name,
+ PP_Var* exception) {
ObjectAccessorWithIdentifierTryCatch accessor(var, name, exception);
if (accessor.has_exception())
return false;
@@ -200,14 +200,14 @@ PP_Var GetProperty(PP_Var var,
PP_Var* exception) {
ObjectAccessorWithIdentifierTryCatch accessor(var, name, exception);
if (accessor.has_exception())
- return PP_MakeVoid();
+ return PP_MakeUndefined();
NPVariant result;
if (!WebBindings::getProperty(NULL, accessor.object()->np_object(),
accessor.identifier(), &result)) {
// An exception may have been raised.
accessor.SetException(kUnableToGetPropertyException);
- return PP_MakeVoid();
+ return PP_MakeUndefined();
}
PP_Var ret = Var::NPVariantToPPVar(accessor.object()->module(), &result);
@@ -215,7 +215,7 @@ PP_Var GetProperty(PP_Var var,
return ret;
}
-void GetAllPropertyNames(PP_Var var,
+void EnumerateProperties(PP_Var var,
uint32_t* property_count,
PP_Var** properties,
PP_Var* exception) {
@@ -246,10 +246,10 @@ void GetAllPropertyNames(PP_Var var,
free(identifiers);
}
-void SetProperty(PP_Var var,
- PP_Var name,
- PP_Var value,
- PP_Var* exception) {
+void SetPropertyDeprecated(PP_Var var,
+ PP_Var name,
+ PP_Var value,
+ PP_Var* exception) {
ObjectAccessorWithIdentifierTryCatch accessor(var, name, exception);
if (accessor.has_exception())
return;
@@ -264,7 +264,7 @@ void SetProperty(PP_Var var,
accessor.SetException(kUnableToSetPropertyException);
}
-void RemoveProperty(PP_Var var,
+void DeleteProperty(PP_Var var,
PP_Var name,
PP_Var* exception) {
ObjectAccessorWithIdentifierTryCatch accessor(var, name, exception);
@@ -276,28 +276,28 @@ void RemoveProperty(PP_Var var,
accessor.SetException(kUnableToRemovePropertyException);
}
-PP_Var Call(PP_Var var,
- PP_Var method_name,
- uint32_t argc,
- PP_Var* argv,
- PP_Var* exception) {
+PP_Var CallDeprecated(PP_Var var,
+ PP_Var method_name,
+ uint32_t argc,
+ PP_Var* argv,
+ PP_Var* exception) {
ObjectAccessorTryCatch accessor(var, exception);
if (accessor.has_exception())
- return PP_MakeVoid();
+ return PP_MakeUndefined();
NPIdentifier identifier;
- if (method_name.type == PP_VARTYPE_VOID) {
+ if (method_name.type == PP_VARTYPE_UNDEFINED) {
identifier = NULL;
} else if (method_name.type == PP_VARTYPE_STRING) {
// Specifically allow only string functions to be called.
identifier = Var::PPVarToNPIdentifier(method_name);
if (!identifier) {
accessor.SetException(kInvalidPropertyException);
- return PP_MakeVoid();
+ return PP_MakeUndefined();
}
} else {
accessor.SetException(kInvalidPropertyException);
- return PP_MakeVoid();
+ return PP_MakeUndefined();
}
scoped_array<NPVariant> args;
@@ -307,7 +307,7 @@ PP_Var Call(PP_Var var,
if (!PPVarToNPVariantNoCopy(argv[i], &args[i])) {
// This argument was invalid, throw an exception & give up.
accessor.SetException(kInvalidValueException);
- return PP_MakeVoid();
+ return PP_MakeUndefined();
}
}
}
@@ -326,7 +326,7 @@ PP_Var Call(PP_Var var,
if (!ok) {
// An exception may have been raised.
accessor.SetException(kUnableToCallMethodException);
- return PP_MakeVoid();
+ return PP_MakeUndefined();
}
PP_Var ret = Var::NPVariantToPPVar(accessor.module(), &result);
@@ -340,7 +340,7 @@ PP_Var Construct(PP_Var var,
PP_Var* exception) {
ObjectAccessorTryCatch accessor(var, exception);
if (accessor.has_exception())
- return PP_MakeVoid();
+ return PP_MakeUndefined();
scoped_array<NPVariant> args;
if (argc) {
@@ -349,7 +349,7 @@ PP_Var Construct(PP_Var var,
if (!PPVarToNPVariantNoCopy(argv[i], &args[i])) {
// This argument was invalid, throw an exception & give up.
accessor.SetException(kInvalidValueException);
- return PP_MakeVoid();
+ return PP_MakeUndefined();
}
}
}
@@ -359,7 +359,7 @@ PP_Var Construct(PP_Var var,
args.get(), argc, &result)) {
// An exception may have been raised.
accessor.SetException(kUnableToConstructException);
- return PP_MakeVoid();
+ return PP_MakeUndefined();
}
PP_Var ret = Var::NPVariantToPPVar(accessor.module(), &result);
@@ -367,9 +367,9 @@ PP_Var Construct(PP_Var var,
return ret;
}
-bool IsInstanceOf(PP_Var var,
- const PPP_Class* ppp_class,
- void** ppp_class_data) {
+bool IsInstanceOfDeprecated(PP_Var var,
+ const PPP_Class_Deprecated* ppp_class,
+ void** ppp_class_data) {
scoped_refptr<ObjectVar> object(ObjectVar::FromPPVar(var));
if (!object)
return false; // Not an object at all.
@@ -378,30 +378,30 @@ bool IsInstanceOf(PP_Var var,
ppp_class, ppp_class_data);
}
-PP_Var CreateObject(PP_Module module_id,
- const PPP_Class* ppp_class,
- void* ppp_class_data) {
- PluginModule* module = PluginModule::FromPPModule(module_id);
+PP_Var CreateObjectDeprecated(PP_Module module_id,
+ const PPP_Class_Deprecated* ppp_class,
+ void* ppp_class_data) {
+ PluginModule* module = ResourceTracker::Get()->GetModule(module_id);
if (!module)
return PP_MakeNull();
return PluginObject::Create(module, ppp_class, ppp_class_data);
}
-const PPB_Var var_interface = {
+const PPB_Var_Deprecated var_deprecated_interface = {
&Var::PluginAddRefPPVar,
&Var::PluginReleasePPVar,
&VarFromUtf8,
&VarToUtf8,
&HasProperty,
- &HasMethod,
+ &HasMethodDeprecated,
&GetProperty,
- &GetAllPropertyNames,
- &SetProperty,
- &RemoveProperty,
- &Call,
+ &EnumerateProperties,
+ &SetPropertyDeprecated,
+ &DeleteProperty,
+ &CallDeprecated,
&Construct,
- &IsInstanceOf,
- &CreateObject
+ &IsInstanceOfDeprecated,
+ &CreateObjectDeprecated
};
} // namespace
@@ -418,7 +418,7 @@ Var::~Var() {
PP_Var Var::NPVariantToPPVar(PluginModule* module, const NPVariant* variant) {
switch (variant->type) {
case NPVariantType_Void:
- return PP_MakeVoid();
+ return PP_MakeUndefined();
case NPVariantType_Null:
return PP_MakeNull();
case NPVariantType_Bool:
@@ -436,7 +436,7 @@ PP_Var Var::NPVariantToPPVar(PluginModule* module, const NPVariant* variant) {
return ObjectVar::NPObjectToPPVar(module, NPVARIANT_TO_OBJECT(*variant));
}
NOTREACHED();
- return PP_MakeVoid();
+ return PP_MakeUndefined();
}
// static
@@ -488,8 +488,8 @@ void Var::PluginReleasePPVar(PP_Var var) {
}
// static
-const PPB_Var* Var::GetInterface() {
- return &var_interface;
+const PPB_Var_Deprecated* Var::GetDeprecatedInterface() {
+ return &var_deprecated_interface;
}
// StringVar -------------------------------------------------------------------
@@ -550,7 +550,7 @@ PP_Var ObjectVar::NPObjectToPPVar(PluginModule* module, NPObject* object) {
object_var = new ObjectVar(module, object);
if (!object_var)
- return PP_MakeVoid();
+ return PP_MakeUndefined();
// Convert to a PP_Var, GetReference will AddRef for us.
PP_Var result;
@@ -570,7 +570,7 @@ scoped_refptr<ObjectVar> ObjectVar::FromPPVar(PP_Var var) {
TryCatch::TryCatch(PluginModule* module, PP_Var* exception)
: module_(module),
- has_exception_(exception && exception->type != PP_VARTYPE_VOID),
+ has_exception_(exception && exception->type != PP_VARTYPE_UNDEFINED),
exception_(exception) {
WebBindings::pushExceptionHandler(&TryCatch::Catch, this);
}
diff --git a/webkit/glue/plugins/pepper_var.h b/webkit/glue/plugins/pepper_var.h
index b618029..0eb1807 100644
--- a/webkit/glue/plugins/pepper_var.h
+++ b/webkit/glue/plugins/pepper_var.h
@@ -10,7 +10,7 @@
#include "webkit/glue/plugins/pepper_resource.h"
struct PP_Var;
-struct PPB_Var;
+struct PPB_Var_Deprecated;
typedef struct NPObject NPObject;
typedef struct _NPVariant NPVariant;
typedef void* NPIdentifier;
@@ -79,8 +79,8 @@ class Var : public Resource {
static void PluginAddRefPPVar(PP_Var var);
static void PluginReleasePPVar(PP_Var var);
- // Returns the PPB_Var interface for the plugin to use.
- static const PPB_Var* GetInterface();
+ // Returns the PPB_Var_Deprecated interface for the plugin to use.
+ static const PPB_Var_Deprecated* GetDeprecatedInterface();
protected:
// This can only be constructed as a StringVar or an ObjectVar.
diff --git a/webkit/glue/plugins/pepper_video_decoder.cc b/webkit/glue/plugins/pepper_video_decoder.cc
index ed572b3..3ca0ab2 100644
--- a/webkit/glue/plugins/pepper_video_decoder.cc
+++ b/webkit/glue/plugins/pepper_video_decoder.cc
@@ -22,7 +22,7 @@ bool GetConfig(PP_Instance instance_id,
PP_VideoConfig_Dev* configs,
int32_t config_size,
int32_t *num_config) {
- PluginInstance* instance = PluginInstance::FromPPInstance(instance_id);
+ PluginInstance* instance = ResourceTracker::Get()->GetInstance(instance_id);
*num_config = 0;
if (!instance)
return false;
@@ -40,7 +40,7 @@ bool GetConfig(PP_Instance instance_id,
PP_Resource Create(PP_Instance instance_id,
const PP_VideoDecoderConfig_Dev* decoder_config) {
- PluginInstance* instance = PluginInstance::FromPPInstance(instance_id);
+ PluginInstance* instance = ResourceTracker::Get()->GetInstance(instance_id);
if (!instance)
return 0;
diff --git a/webkit/glue/plugins/pepper_webplugin_impl.cc b/webkit/glue/plugins/pepper_webplugin_impl.cc
index 32903b0..2e8eb3f 100644
--- a/webkit/glue/plugins/pepper_webplugin_impl.cc
+++ b/webkit/glue/plugins/pepper_webplugin_impl.cc
@@ -4,10 +4,14 @@
#include "webkit/glue/plugins/pepper_webplugin_impl.h"
+#include <cmath>
+
#include "base/message_loop.h"
#include "third_party/ppapi/c/pp_var.h"
#include "third_party/WebKit/WebKit/chromium/public/WebPluginParams.h"
+#include "third_party/WebKit/WebKit/chromium/public/WebPoint.h"
#include "third_party/WebKit/WebKit/chromium/public/WebRect.h"
+#include "third_party/WebKit/WebKit/chromium/public/WebView.h"
#include "webkit/glue/plugins/pepper_plugin_instance.h"
#include "webkit/glue/plugins/pepper_plugin_module.h"
#include "webkit/glue/plugins/pepper_url_loader.h"
@@ -16,12 +20,22 @@
using WebKit::WebCanvas;
using WebKit::WebPluginContainer;
using WebKit::WebPluginParams;
+using WebKit::WebPoint;
using WebKit::WebRect;
using WebKit::WebString;
+using WebKit::WebURL;
using WebKit::WebVector;
+using WebKit::WebView;
namespace pepper {
+struct WebPluginImpl::InitData {
+ scoped_refptr<PluginModule> module;
+ base::WeakPtr<PluginDelegate> delegate;
+ std::vector<std::string> arg_names;
+ std::vector<std::string> arg_values;
+};
+
WebPluginImpl::WebPluginImpl(
PluginModule* plugin_module,
const WebPluginParams& params,
@@ -117,7 +131,7 @@ void WebPluginImpl::didReceiveResponse(
const WebKit::WebURLResponse& response) {
DCHECK(!document_loader_);
- document_loader_ = new URLLoader(instance_);
+ document_loader_ = new URLLoader(instance_, true);
document_loader_->didReceiveResponse(NULL, response);
if (!instance_->HandleDocumentLoad(document_loader_))
@@ -157,16 +171,20 @@ bool WebPluginImpl::hasSelection() const {
return !selectionAsText().isEmpty();
}
-WebKit::WebString WebPluginImpl::selectionAsText() const {
+WebString WebPluginImpl::selectionAsText() const {
return instance_->GetSelectedText(false);
}
-WebKit::WebString WebPluginImpl::selectionAsMarkup() const {
+WebString WebPluginImpl::selectionAsMarkup() const {
return instance_->GetSelectedText(true);
}
-void WebPluginImpl::setZoomFactor(float scale, bool text_only) {
- instance_->Zoom(scale, text_only);
+WebURL WebPluginImpl::linkAtPosition(const WebPoint& position) const {
+ return GURL(instance_->GetLinkAtPosition(position));
+}
+
+void WebPluginImpl::setZoomLevel(double level, bool text_only) {
+ instance_->Zoom(WebView::zoomLevelToZoomFactor(level), text_only);
}
bool WebPluginImpl::startFind(const WebKit::WebString& search_text,
diff --git a/webkit/glue/plugins/pepper_webplugin_impl.h b/webkit/glue/plugins/pepper_webplugin_impl.h
index 9d2f313..15ee784 100644
--- a/webkit/glue/plugins/pepper_webplugin_impl.h
+++ b/webkit/glue/plugins/pepper_webplugin_impl.h
@@ -63,7 +63,8 @@ class WebPluginImpl : public WebKit::WebPlugin {
virtual bool hasSelection() const;
virtual WebKit::WebString selectionAsText() const;
virtual WebKit::WebString selectionAsMarkup() const;
- virtual void setZoomFactor(float scale, bool text_only);
+ virtual WebKit::WebURL linkAtPosition(const WebKit::WebPoint& position) const;
+ virtual void setZoomLevel(double level, bool text_only);
virtual bool startFind(const WebKit::WebString& search_text,
bool case_sensitive,
int identifier);
@@ -75,12 +76,7 @@ class WebPluginImpl : public WebKit::WebPlugin {
virtual bool printPage(int page_number, WebKit::WebCanvas* canvas);
virtual void printEnd();
- struct InitData {
- scoped_refptr<PluginModule> module;
- base::WeakPtr<PluginDelegate> delegate;
- std::vector<std::string> arg_names;
- std::vector<std::string> arg_values;
- };
+ struct InitData;
scoped_ptr<InitData> init_data_; // Cleared upon successful initialization.
// True if the instance represents the entire document in a frame instead of
diff --git a/webkit/glue/plugins/pepper_widget.cc b/webkit/glue/plugins/pepper_widget.cc
index 1ba5280..7002576 100644
--- a/webkit/glue/plugins/pepper_widget.cc
+++ b/webkit/glue/plugins/pepper_widget.cc
@@ -88,7 +88,7 @@ void Widget::Invalidate(const PP_Rect* dirty) {
if (!widget)
return;
ScopedResourceId resource(this);
- widget->Invalidate(instance_->GetPPInstance(), resource.id, dirty);
+ widget->Invalidate(instance_->pp_instance(), resource.id, dirty);
}
} // namespace pepper
diff --git a/webkit/glue/plugins/plugin_group.cc b/webkit/glue/plugins/plugin_group.cc
new file mode 100644
index 0000000..ee3155e
--- /dev/null
+++ b/webkit/glue/plugins/plugin_group.cc
@@ -0,0 +1,419 @@
+// Copyright (c) 2010 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "webkit/glue/plugins/plugin_group.h"
+
+#include "base/linked_ptr.h"
+#include "base/string_util.h"
+#include "base/sys_string_conversions.h"
+#include "base/utf_string_conversions.h"
+#include "base/values.h"
+#include "base/version.h"
+#include "webkit/glue/plugins/plugin_list.h"
+#include "webkit/glue/plugins/webplugininfo.h"
+
+const char* PluginGroup::kAdobeReader8GroupName = "Adobe Reader 8";
+const char* PluginGroup::kAdobeReader9GroupName = "Adobe Reader 9";
+
+#if defined(OS_MACOSX)
+// Plugin Groups for Mac.
+// Plugins are listed here as soon as vulnerabilities and solutions
+// (new versions) are published.
+// TODO(panayiotis): Get the Real Player version on Mac, somehow.
+static const PluginGroupDefinition kGroupDefinitions[] = {
+ { "apple-quicktime", "Quicktime", "QuickTime Plug-in", "", "", "7.6.6",
+ "http://www.apple.com/quicktime/download/" },
+ { "java-runtime-environment", "Java", "Java", "", "", "",
+ "http://support.apple.com/kb/HT1338" },
+ { "adobe-flash-player", "Flash", "Shockwave Flash", "", "", "10.1.85",
+ "http://get.adobe.com/flashplayer/" },
+ { "silverlight-3", "Silverlight 3", "Silverlight", "0", "4", "3.0.50106.0",
+ "http://www.microsoft.com/getsilverlight/" },
+ { "silverlight-4", "Silverlight 4", "Silverlight", "4", "5", "",
+ "http://www.microsoft.com/getsilverlight/" },
+ { "flip4mac", "Flip4Mac", "Flip4Mac", "", "", "2.2.1",
+ "http://www.telestream.net/flip4mac-wmv/overview.htm" },
+ { "shockwave", "Shockwave", "Shockwave for Director", "", "", "11.5.8.612",
+ "http://www.adobe.com/shockwave/download/" }
+};
+
+#elif defined(OS_WIN)
+// TODO(panayiotis): We should group "RealJukebox NS Plugin" with the rest of
+// the RealPlayer files.
+static const PluginGroupDefinition kGroupDefinitions[] = {
+ { "apple-quicktime", "Quicktime", "QuickTime Plug-in", "", "", "7.6.8",
+ "http://www.apple.com/quicktime/download/" },
+ { "java-runtime-environment", "Java 6", "Java", "", "6", "6.0.220",
+ "http://www.java.com/" },
+ { "adobe-reader", PluginGroup::kAdobeReader9GroupName, "Adobe Acrobat", "9",
+ "10", "9.4.0", "http://get.adobe.com/reader/" },
+ { "adobe-reader-8", PluginGroup::kAdobeReader8GroupName, "Adobe Acrobat", "0",
+ "9", "8.2.5", "http://get.adobe.com/reader/" },
+ { "adobe-flash-player", "Flash", "Shockwave Flash", "", "", "10.1.85",
+ "http://get.adobe.com/flashplayer/" },
+ { "silverlight-3", "Silverlight 3", "Silverlight", "0", "4", "3.0.50106.0",
+ "http://www.microsoft.com/getsilverlight/" },
+ { "silverlight-4", "Silverlight 4", "Silverlight", "4", "5", "",
+ "http://www.microsoft.com/getsilverlight/" },
+ { "shockwave", "Shockwave", "Shockwave for Director", "", "", "11.5.8.612",
+ "http://www.adobe.com/shockwave/download/" },
+ { "divx-player", "DivX Player", "DivX Web Player", "", "", "1.4.3.4",
+ "http://download.divx.com/divx/autoupdate/player/"
+ "DivXWebPlayerInstaller.exe" },
+ // These are here for grouping, no vulnerabilies known.
+ { "windows-media-player", "Windows Media Player", "Windows Media Player",
+ "", "", "", "" },
+ { "microsoft-office", "Microsoft Office", "Microsoft Office",
+ "", "", "", "" },
+ // TODO(panayiotis): The vulnerable versions are
+ // (v >= 6.0.12.1040 && v <= 6.0.12.1663)
+ // || v == 6.0.12.1698 || v == 6.0.12.1741
+ { "realplayer", "RealPlayer", "RealPlayer", "", "", "",
+ "http://www.adobe.com/shockwave/download/" },
+};
+
+#else
+static const PluginGroupDefinition kGroupDefinitions[] = {};
+#endif
+
+/*static*/
+std::set<string16>* PluginGroup::policy_disabled_plugin_patterns_;
+
+/*static*/
+const PluginGroupDefinition* PluginGroup::GetPluginGroupDefinitions() {
+ return kGroupDefinitions;
+}
+
+/*static*/
+size_t PluginGroup::GetPluginGroupDefinitionsSize() {
+ // TODO(viettrungluu): |arraysize()| doesn't work with zero-size arrays.
+ return ARRAYSIZE_UNSAFE(kGroupDefinitions);
+}
+
+/*static*/
+void PluginGroup::SetPolicyDisabledPluginPatterns(
+ const std::set<string16>& set) {
+ if (!policy_disabled_plugin_patterns_)
+ policy_disabled_plugin_patterns_ = new std::set<string16>(set);
+ else
+ *policy_disabled_plugin_patterns_ = set;
+}
+
+/*static*/
+bool PluginGroup::IsPluginNameDisabledByPolicy(const string16& plugin_name) {
+ if (!policy_disabled_plugin_patterns_)
+ return false;
+
+ std::set<string16>::const_iterator pattern(
+ policy_disabled_plugin_patterns_->begin());
+ while (pattern != policy_disabled_plugin_patterns_->end()) {
+ if (MatchPattern(plugin_name, *pattern))
+ return true;
+ ++pattern;
+ }
+
+ return false;
+}
+
+/*static*/
+bool PluginGroup::IsPluginPathDisabledByPolicy(const FilePath& plugin_path) {
+ std::vector<WebPluginInfo> plugins;
+ NPAPI::PluginList::Singleton()->GetPlugins(false, &plugins);
+ for (std::vector<WebPluginInfo>::const_iterator it = plugins.begin();
+ it != plugins.end();
+ ++it) {
+ if (FilePath::CompareEqualIgnoreCase(it->path.value(),
+ plugin_path.value()) && IsPluginNameDisabledByPolicy(it->name)) {
+ return true;
+ }
+ }
+ return false;
+}
+
+PluginGroup::PluginGroup(const string16& group_name,
+ const string16& name_matcher,
+ const std::string& version_range_low,
+ const std::string& version_range_high,
+ const std::string& min_version,
+ const std::string& update_url,
+ const std::string& identifier)
+ : identifier_(identifier),
+ group_name_(group_name),
+ name_matcher_(name_matcher),
+ version_range_low_str_(version_range_low),
+ version_range_high_str_(version_range_high),
+ update_url_(update_url),
+ enabled_(false),
+ min_version_str_(min_version),
+ version_(Version::GetVersionFromString("0")) {
+ if (!version_range_low.empty())
+ version_range_low_.reset(Version::GetVersionFromString(version_range_low));
+ if (!version_range_high.empty()) {
+ version_range_high_.reset(
+ Version::GetVersionFromString(version_range_high));
+ }
+ if (!min_version.empty())
+ min_version_.reset(Version::GetVersionFromString(min_version));
+}
+
+PluginGroup* PluginGroup::FromPluginGroupDefinition(
+ const PluginGroupDefinition& definition) {
+ return new PluginGroup(ASCIIToUTF16(definition.name),
+ ASCIIToUTF16(definition.name_matcher),
+ definition.version_matcher_low,
+ definition.version_matcher_high,
+ definition.min_version,
+ definition.update_url,
+ definition.identifier);
+}
+
+PluginGroup::~PluginGroup() { }
+
+PluginGroup* PluginGroup::FromWebPluginInfo(const WebPluginInfo& wpi) {
+ // Create a matcher from the name of this plugin.
+#if defined(OS_POSIX)
+ std::string identifier = wpi.path.BaseName().value();
+#elif defined(OS_WIN)
+ std::string identifier = base::SysWideToUTF8(wpi.path.BaseName().value());
+#endif
+ return new PluginGroup(wpi.name, wpi.name, std::string(), std::string(),
+ std::string(), std::string(), identifier);
+}
+
+PluginGroup* PluginGroup::CopyOrCreatePluginGroup(
+ const WebPluginInfo& info) {
+ static PluginMap* hardcoded_plugin_groups = NULL;
+ if (!hardcoded_plugin_groups) {
+ PluginMap* groups = new PluginMap();
+ const PluginGroupDefinition* definitions = GetPluginGroupDefinitions();
+ for (size_t i = 0; i < GetPluginGroupDefinitionsSize(); ++i) {
+ PluginGroup* definition_group = PluginGroup::FromPluginGroupDefinition(
+ definitions[i]);
+ std::string identifier = definition_group->identifier();
+ DCHECK(groups->find(identifier) == groups->end());
+ (*groups)[identifier] = linked_ptr<PluginGroup>(definition_group);
+ }
+ hardcoded_plugin_groups = groups;
+ }
+
+ // See if this plugin matches any of the hardcoded groups.
+ PluginGroup* hardcoded_group = FindGroupMatchingPlugin(
+ *hardcoded_plugin_groups, info);
+ if (hardcoded_group) {
+ // Make a copy.
+ return hardcoded_group->Copy();
+ } else {
+ // Not found in our hardcoded list, create a new one.
+ return PluginGroup::FromWebPluginInfo(info);
+ }
+}
+
+PluginGroup* PluginGroup::FindGroupMatchingPlugin(
+ const PluginMap& plugin_groups,
+ const WebPluginInfo& plugin) {
+ for (std::map<std::string, linked_ptr<PluginGroup> >::const_iterator it =
+ plugin_groups.begin();
+ it != plugin_groups.end();
+ ++it) {
+ if (it->second->Match(plugin))
+ return it->second.get();
+ }
+ return NULL;
+}
+
+bool PluginGroup::Match(const WebPluginInfo& plugin) const {
+ if (name_matcher_.empty()) {
+ return false;
+ }
+
+ // Look for the name matcher anywhere in the plugin name.
+ if (plugin.name.find(name_matcher_) == string16::npos) {
+ return false;
+ }
+
+ if (version_range_low_.get() == NULL ||
+ version_range_high_.get() == NULL) {
+ return true;
+ }
+
+ // There's a version range, we must be in it.
+ scoped_ptr<Version> plugin_version(
+ Version::GetVersionFromString(UTF16ToWide(plugin.version)));
+ if (plugin_version.get() == NULL) {
+ // No version could be extracted, assume we don't match the range.
+ return false;
+ }
+
+ // We match if we are in the range: [low, high)
+ return (version_range_low_->CompareTo(*plugin_version) <= 0 &&
+ version_range_high_->CompareTo(*plugin_version) > 0);
+}
+
+Version* PluginGroup::CreateVersionFromString(const string16& version_string) {
+ // Remove spaces and ')' from the version string,
+ // Replace any instances of 'r', ',' or '(' with a dot.
+ std::wstring version = UTF16ToWide(version_string);
+ RemoveChars(version, L") ", &version);
+ std::replace(version.begin(), version.end(), 'r', '.');
+ std::replace(version.begin(), version.end(), ',', '.');
+ std::replace(version.begin(), version.end(), '(', '.');
+
+ return Version::GetVersionFromString(version);
+}
+
+void PluginGroup::UpdateActivePlugin(const WebPluginInfo& plugin) {
+ // A group is enabled if any of the files are enabled.
+ if (plugin.enabled) {
+ if (!enabled_) {
+ // If this is the first enabled plugin, use its description.
+ enabled_ = true;
+ UpdateDescriptionAndVersion(plugin);
+ }
+ } else {
+ // If this is the first plugin and it's disabled,
+ // use its description for now.
+ if (description_.empty())
+ UpdateDescriptionAndVersion(plugin);
+ }
+}
+
+void PluginGroup::UpdateDescriptionAndVersion(const WebPluginInfo& plugin) {
+ description_ = plugin.desc;
+ if (Version* new_version = CreateVersionFromString(plugin.version))
+ version_.reset(new_version);
+ else
+ version_.reset(Version::GetVersionFromString("0"));
+}
+
+void PluginGroup::AddPlugin(const WebPluginInfo& plugin, int position) {
+ web_plugin_infos_.push_back(plugin);
+ // The position of this plugin relative to the global list of plugins.
+ web_plugin_positions_.push_back(position);
+ UpdateActivePlugin(plugin);
+}
+
+string16 PluginGroup::GetGroupName() const {
+ if (!group_name_.empty())
+ return group_name_;
+ DCHECK_EQ(1u, web_plugin_infos_.size());
+ FilePath::StringType path =
+ web_plugin_infos_[0].path.BaseName().RemoveExtension().value();
+#if defined(OS_POSIX)
+ return UTF8ToUTF16(path);
+#elif defined(OS_WIN)
+ return WideToUTF16(path);
+#endif
+}
+
+DictionaryValue* PluginGroup::GetSummary() const {
+ DictionaryValue* result = new DictionaryValue();
+ result->SetString("name", GetGroupName());
+ result->SetBoolean("enabled", enabled_);
+ return result;
+}
+
+DictionaryValue* PluginGroup::GetDataForUI() const {
+ string16 name = GetGroupName();
+ DictionaryValue* result = new DictionaryValue();
+ result->SetString("name", name);
+ result->SetString("description", description_);
+ result->SetString("version", version_->GetString());
+ result->SetString("update_url", update_url_);
+ result->SetBoolean("critical", IsVulnerable());
+
+ bool group_disabled_by_policy = IsPluginNameDisabledByPolicy(name);
+ ListValue* plugin_files = new ListValue();
+ bool all_plugins_disabled_by_policy = true;
+ for (size_t i = 0; i < web_plugin_infos_.size(); ++i) {
+ const WebPluginInfo& web_plugin = web_plugin_infos_[i];
+ int priority = web_plugin_positions_[i];
+ DictionaryValue* plugin_file = new DictionaryValue();
+ plugin_file->SetString("name", web_plugin.name);
+ plugin_file->SetString("description", web_plugin.desc);
+ plugin_file->SetString("path", web_plugin.path.value());
+ plugin_file->SetString("version", web_plugin.version);
+ bool plugin_disabled_by_policy = group_disabled_by_policy ||
+ IsPluginNameDisabledByPolicy(web_plugin.name);
+ if (plugin_disabled_by_policy) {
+ plugin_file->SetString("enabledMode", "disabledByPolicy");
+ } else {
+ all_plugins_disabled_by_policy = false;
+ plugin_file->SetString("enabledMode",
+ web_plugin.enabled ? "enabled" : "disabledByUser");
+ }
+ plugin_file->SetInteger("priority", priority);
+
+ ListValue* mime_types = new ListValue();
+ for (std::vector<WebPluginMimeType>::const_iterator type_it =
+ web_plugin.mime_types.begin();
+ type_it != web_plugin.mime_types.end();
+ ++type_it) {
+ DictionaryValue* mime_type = new DictionaryValue();
+ mime_type->SetString("mimeType", type_it->mime_type);
+ mime_type->SetString("description", type_it->description);
+
+ ListValue* file_extensions = new ListValue();
+ for (std::vector<std::string>::const_iterator ext_it =
+ type_it->file_extensions.begin();
+ ext_it != type_it->file_extensions.end();
+ ++ext_it) {
+ file_extensions->Append(new StringValue(*ext_it));
+ }
+ mime_type->Set("fileExtensions", file_extensions);
+
+ mime_types->Append(mime_type);
+ }
+ plugin_file->Set("mimeTypes", mime_types);
+
+ plugin_files->Append(plugin_file);
+ }
+
+ if (group_disabled_by_policy || all_plugins_disabled_by_policy) {
+ result->SetString("enabledMode", "disabledByPolicy");
+ } else {
+ result->SetString("enabledMode", enabled_ ? "enabled" : "disabledByUser");
+ }
+ result->Set("plugin_files", plugin_files);
+
+ return result;
+}
+
+// Returns true if the latest version of this plugin group is vulnerable.
+bool PluginGroup::IsVulnerable() const {
+ if (min_version_.get() == NULL || version_->GetString() == "0") {
+ return false;
+ }
+ return version_->CompareTo(*min_version_) < 0;
+}
+
+void PluginGroup::DisableOutdatedPlugins() {
+ if (!min_version_.get())
+ return;
+
+ description_ = string16();
+ enabled_ = false;
+
+ for (std::vector<WebPluginInfo>::iterator it =
+ web_plugin_infos_.begin();
+ it != web_plugin_infos_.end(); ++it) {
+ scoped_ptr<Version> version(CreateVersionFromString(it->version));
+ if (version.get() && version->CompareTo(*min_version_) < 0) {
+ it->enabled = false;
+ NPAPI::PluginList::Singleton()->DisablePlugin(it->path);
+ }
+ UpdateActivePlugin(*it);
+ }
+}
+
+void PluginGroup::Enable(bool enable) {
+ for (std::vector<WebPluginInfo>::const_iterator it =
+ web_plugin_infos_.begin();
+ it != web_plugin_infos_.end(); ++it) {
+ if (enable && !IsPluginNameDisabledByPolicy(it->name)) {
+ NPAPI::PluginList::Singleton()->EnablePlugin(it->path);
+ } else {
+ NPAPI::PluginList::Singleton()->DisablePlugin(it->path);
+ }
+ }
+}
diff --git a/webkit/glue/plugins/plugin_group.h b/webkit/glue/plugins/plugin_group.h
new file mode 100644
index 0000000..2281437
--- /dev/null
+++ b/webkit/glue/plugins/plugin_group.h
@@ -0,0 +1,184 @@
+// Copyright (c) 2010 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef WEBKIT_GLUE_PLUGINS_PLUGIN_GROUP_H_
+#define WEBKIT_GLUE_PLUGINS_PLUGIN_GROUP_H_
+#pragma once
+
+#include <map>
+#include <set>
+#include <vector>
+
+#include "base/gtest_prod_util.h"
+#include "base/scoped_ptr.h"
+#include "base/string16.h"
+
+class DictionaryValue;
+class FilePath;
+class Version;
+struct WebPluginInfo;
+
+namespace NPAPI {
+ class PluginList;
+};
+
+template <typename T>
+class linked_ptr;
+
+// Hard-coded definitions of plugin groups.
+struct PluginGroupDefinition {
+ const char* identifier; // Unique identifier for this group.
+ const char* name; // Name of this group.
+ const char* name_matcher; // Substring matcher for the plugin name.
+ const char* version_matcher_low; // Matchers for the plugin version.
+ const char* version_matcher_high;
+ const char* min_version; // Minimum secure version.
+ const char* update_url; // Location of latest secure version.
+};
+
+// A PluginGroup can match a range of versions of a specific plugin (as defined
+// by matching a substring of its name).
+// It contains all WebPluginInfo structs (at least one) matching its definition.
+// In addition, it knows about a security "baseline", i.e. the minimum version
+// of a plugin that is needed in order not to exhibit known security
+// vulnerabilities.
+
+class PluginGroup {
+ public:
+ // Used by about:plugins to disable Reader plugin when internal PDF viewer is
+ // enabled.
+ static const char* kAdobeReader8GroupName;
+ static const char* kAdobeReader9GroupName;
+
+ typedef std::map<std::string, linked_ptr<PluginGroup> > PluginMap;
+
+ // Creates a PluginGroup from a PluginGroupDefinition.
+ static PluginGroup* FromPluginGroupDefinition(
+ const PluginGroupDefinition& definition);
+
+ ~PluginGroup();
+
+ // Creates a PluginGroup from a WebPluginInfo -- when no hard-coded
+ // definition is found.
+ static PluginGroup* FromWebPluginInfo(const WebPluginInfo& wpi);
+
+ // Find a plugin group matching |info| in the list of hardcoded plugins and
+ // returns a copy of it if found, or a new group matching exactly this plugin
+ // otherwise.
+ // The caller should take ownership of the return PluginGroup.
+ static PluginGroup* CopyOrCreatePluginGroup(const WebPluginInfo& info);
+
+ // Configures the set of plugin name patterns for disabling plugins via
+ // enterprise configuration management.
+ static void SetPolicyDisabledPluginPatterns(const std::set<string16>& set);
+
+ // Tests to see if a plugin is on the blacklist using its name as
+ // the lookup key.
+ static bool IsPluginNameDisabledByPolicy(const string16& plugin_name);
+
+ // Tests to see if a plugin is on the blacklist using its path as
+ // the lookup key.
+ static bool IsPluginPathDisabledByPolicy(const FilePath& plugin_path);
+
+ // Find the PluginGroup matching a Plugin in a list of plugin groups. Returns
+ // NULL if no matching PluginGroup is found.
+ static PluginGroup* FindGroupMatchingPlugin(
+ const std::map<std::string, linked_ptr<PluginGroup> >& plugin_groups,
+ const WebPluginInfo& plugin);
+
+ // Creates a copy of this plugin group.
+ PluginGroup* Copy() {
+ return new PluginGroup(group_name_, name_matcher_, version_range_low_str_,
+ version_range_high_str_, min_version_str_,
+ update_url_, identifier_);
+ }
+
+ // Returns true if the given plugin matches this group.
+ bool Match(const WebPluginInfo& plugin) const;
+
+ // Adds the given plugin to this group. Provide the position of the
+ // plugin as given by PluginList so we can display its priority.
+ void AddPlugin(const WebPluginInfo& plugin, int position);
+
+ // Enables/disables this group. This enables/disables all plugins in the
+ // group.
+ void Enable(bool enable);
+
+ // Returns whether the plugin group is enabled or not.
+ bool Enabled() const { return enabled_; }
+
+ // Returns a unique identifier for this group, if one is defined, or the empty
+ // string otherwise.
+ const std::string& identifier() const { return identifier_; }
+
+ // Returns this group's name, or the filename without extension if the name
+ // is empty.
+ string16 GetGroupName() const;
+
+ // Returns the description of the highest-priority plug-in in the group.
+ const string16& description() const { return description_; }
+
+ // Returns a DictionaryValue with data to display in the UI.
+ DictionaryValue* GetDataForUI() const;
+
+ // Returns a DictionaryValue with data to save in the preferences.
+ DictionaryValue* GetSummary() const;
+
+ // Returns the update URL.
+ std::string GetUpdateURL() const { return update_url_; }
+
+ // Returns true if the highest-priority plugin in this group has known
+ // security problems.
+ bool IsVulnerable() const;
+
+ // Disables all plugins in this group that are older than the
+ // minimum version.
+ void DisableOutdatedPlugins();
+
+ private:
+ FRIEND_TEST_ALL_PREFIXES(PluginGroupTest, PluginGroupDefinition);
+
+ static const PluginGroupDefinition* GetPluginGroupDefinitions();
+ static size_t GetPluginGroupDefinitionsSize();
+
+ PluginGroup(const string16& group_name,
+ const string16& name_matcher,
+ const std::string& version_range_low,
+ const std::string& version_range_high,
+ const std::string& min_version,
+ const std::string& update_url,
+ const std::string& identifier);
+
+ Version* CreateVersionFromString(const string16& version_string);
+
+ // Set the description and version for this plugin group from the
+ // given plug-in.
+ void UpdateDescriptionAndVersion(const WebPluginInfo& plugin);
+
+ // Updates the active plugin in the group. The active plugin is the first
+ // enabled one, or if all plugins are disabled, simply the first one.
+ void UpdateActivePlugin(const WebPluginInfo& plugin);
+
+ static std::set<string16>* policy_disabled_plugin_patterns_;
+
+ std::string identifier_;
+ string16 group_name_;
+ string16 name_matcher_;
+ std::string version_range_low_str_;
+ std::string version_range_high_str_;
+ scoped_ptr<Version> version_range_low_;
+ scoped_ptr<Version> version_range_high_;
+ string16 description_;
+ std::string update_url_;
+ bool enabled_;
+ std::string min_version_str_;
+ scoped_ptr<Version> min_version_;
+ scoped_ptr<Version> version_;
+ std::vector<WebPluginInfo> web_plugin_infos_;
+ std::vector<int> web_plugin_positions_;
+
+ DISALLOW_COPY_AND_ASSIGN(PluginGroup);
+};
+
+#endif // WEBKIT_GLUE_PLUGINS_PLUGIN_GROUP_H_
diff --git a/webkit/glue/plugins/plugin_group_unittest.cc b/webkit/glue/plugins/plugin_group_unittest.cc
new file mode 100644
index 0000000..467c273
--- /dev/null
+++ b/webkit/glue/plugins/plugin_group_unittest.cc
@@ -0,0 +1,181 @@
+// Copyright (c) 2010 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "webkit/glue/plugins/plugin_group.h"
+
+#include <string>
+#include <vector>
+
+#include "base/scoped_ptr.h"
+#include "base/string_util.h"
+#include "base/utf_string_conversions.h"
+#include "base/values.h"
+#include "base/version.h"
+#include "testing/gtest/include/gtest/gtest.h"
+#include "webkit/glue/plugins/webplugininfo.h"
+
+static const PluginGroupDefinition kPluginDef = {
+ "myplugin", "MyPlugin", "MyPlugin", "", "", "3.0.44", "http://latest/" };
+static const PluginGroupDefinition kPluginDef3 = {
+ "myplugin-3", "MyPlugin 3", "MyPlugin", "0", "4", "3.0.44", "http://latest" };
+static const PluginGroupDefinition kPluginDef4 = {
+ "myplugin-4", "MyPlugin 4", "MyPlugin", "4", "5", "4.0.44", "http://latest" };
+static const PluginGroupDefinition kPluginDefNotVulnerable = {
+ "myplugin-latest", "MyPlugin", "MyPlugin", "", "", "", "http://latest" };
+
+// name, path, version, desc, mime_types, enabled.
+static WebPluginInfo kPlugin2043 = WebPluginInfo(
+ ASCIIToUTF16("MyPlugin"), ASCIIToUTF16("2.0.43"),
+ ASCIIToUTF16("MyPlugin version 2.0.43"));
+static WebPluginInfo kPlugin3043 = WebPluginInfo(
+ ASCIIToUTF16("MyPlugin"), ASCIIToUTF16("3.0.43"),
+ ASCIIToUTF16("MyPlugin version 3.0.43"));
+static WebPluginInfo kPlugin3044 = WebPluginInfo(
+ ASCIIToUTF16("MyPlugin"), ASCIIToUTF16("3.0.44"),
+ ASCIIToUTF16("MyPlugin version 3.0.44"));
+static WebPluginInfo kPlugin3045 = WebPluginInfo(
+ ASCIIToUTF16("MyPlugin"), ASCIIToUTF16("3.0.45"),
+ ASCIIToUTF16("MyPlugin version 3.0.45"));
+static WebPluginInfo kPlugin4043 = WebPluginInfo(
+ ASCIIToUTF16("MyPlugin"), ASCIIToUTF16("4.0.43"),
+ ASCIIToUTF16("MyPlugin version 4.0.43"));
+
+class PluginGroupTest : public testing::Test {
+ protected:
+ virtual void TearDown() {
+ PluginGroup::SetPolicyDisabledPluginPatterns(std::set<string16>());
+ }
+};
+
+TEST(PluginGroupTest, PluginGroupMatch) {
+ scoped_ptr<PluginGroup> group(PluginGroup::FromPluginGroupDefinition(
+ kPluginDef3));
+ EXPECT_TRUE(group->Match(kPlugin3045));
+ group->AddPlugin(kPlugin3045, 0);
+ EXPECT_FALSE(group->IsVulnerable());
+}
+
+TEST(PluginGroupTest, PluginGroupMatchCorrectVersion) {
+ scoped_ptr<PluginGroup> group(PluginGroup::FromPluginGroupDefinition(
+ kPluginDef3));
+ EXPECT_TRUE(group->Match(kPlugin2043));
+ EXPECT_TRUE(group->Match(kPlugin3043));
+ EXPECT_FALSE(group->Match(kPlugin4043));
+
+ group.reset(PluginGroup::FromPluginGroupDefinition(kPluginDef4));
+ EXPECT_FALSE(group->Match(kPlugin2043));
+ EXPECT_FALSE(group->Match(kPlugin3043));
+ EXPECT_TRUE(group->Match(kPlugin4043));
+}
+
+TEST(PluginGroupTest, PluginGroupDescription) {
+ string16 desc3043(ASCIIToUTF16("MyPlugin version 3.0.43"));
+ string16 desc3045(ASCIIToUTF16("MyPlugin version 3.0.45"));
+ WebPluginInfo plugin3043(kPlugin3043);
+ WebPluginInfo plugin3045(kPlugin3045);
+
+ {
+ scoped_ptr<PluginGroup> group(PluginGroup::FromPluginGroupDefinition(
+ kPluginDef3));
+ EXPECT_TRUE(group->Match(plugin3043));
+ group->AddPlugin(plugin3043, 0);
+ EXPECT_EQ(desc3043, group->description());
+ EXPECT_TRUE(group->IsVulnerable());
+ EXPECT_TRUE(group->Match(plugin3045));
+ group->AddPlugin(plugin3045, 1);
+ EXPECT_EQ(desc3043, group->description());
+ EXPECT_TRUE(group->IsVulnerable());
+ }
+
+ {
+ // Disable the first plugin.
+ plugin3043.enabled = false;
+ scoped_ptr<PluginGroup> group(PluginGroup::FromPluginGroupDefinition(
+ kPluginDef3));
+ EXPECT_TRUE(group->Match(plugin3043));
+ group->AddPlugin(plugin3043, 0);
+ EXPECT_EQ(desc3043, group->description());
+ EXPECT_TRUE(group->IsVulnerable());
+ EXPECT_TRUE(group->Match(plugin3045));
+ group->AddPlugin(plugin3045, 1);
+ EXPECT_EQ(desc3045, group->description());
+ EXPECT_FALSE(group->IsVulnerable());
+ }
+
+ {
+ // Disable the second plugin.
+ plugin3045.enabled = false;
+ scoped_ptr<PluginGroup> group(PluginGroup::FromPluginGroupDefinition(
+ kPluginDef3));
+ EXPECT_TRUE(group->Match(plugin3043));
+ group->AddPlugin(plugin3043, 1);
+ EXPECT_EQ(desc3043, group->description());
+ EXPECT_TRUE(group->IsVulnerable());
+ EXPECT_TRUE(group->Match(plugin3045));
+ group->AddPlugin(plugin3045, 0);
+ EXPECT_EQ(desc3043, group->description());
+ EXPECT_TRUE(group->IsVulnerable());
+ }
+}
+
+TEST(PluginGroupTest, PluginGroupDefinition) {
+ const PluginGroupDefinition* definitions =
+ PluginGroup::GetPluginGroupDefinitions();
+ for (size_t i = 0; i < PluginGroup::GetPluginGroupDefinitionsSize(); ++i) {
+ scoped_ptr<PluginGroup> def_group(
+ PluginGroup::FromPluginGroupDefinition(definitions[i]));
+ ASSERT_TRUE(def_group.get() != NULL);
+ EXPECT_FALSE(def_group->Match(kPlugin2043));
+ }
+}
+
+TEST(PluginGroupTest, DisableOutdated) {
+ scoped_ptr<PluginGroup> group(PluginGroup::FromPluginGroupDefinition(
+ kPluginDef3));
+ group->AddPlugin(kPlugin3043, 0);
+ group->AddPlugin(kPlugin3045, 1);
+ EXPECT_EQ(ASCIIToUTF16("MyPlugin version 3.0.43"), group->description());
+ EXPECT_TRUE(group->IsVulnerable());
+
+ group->DisableOutdatedPlugins();
+ EXPECT_EQ(ASCIIToUTF16("MyPlugin version 3.0.45"), group->description());
+ EXPECT_FALSE(group->IsVulnerable());
+}
+
+TEST(PluginGroupTest, VersionExtraction) {
+ // Some real-world plugin versions (spaces, commata, parentheses, 'r', oh my)
+ const char* versions[][2] = {
+ { "7.6.6 (1671)", "7.6.6.1671" }, // Quicktime
+ { "2, 0, 0, 254", "2.0.0.254" }, // DivX
+ { "3, 0, 0, 0", "3.0.0.0" }, // Picasa
+ { "1, 0, 0, 1", "1.0.0.1" }, // Earth
+ { "10,0,45,2", "10.0.45.2" }, // Flash
+ { "11.5.7r609", "11.5.7.609"} // Shockwave
+ };
+
+ for (size_t i = 0; i < arraysize(versions); i++) {
+ const WebPluginInfo plugin = WebPluginInfo(
+ ASCIIToUTF16("Blah Plugin"), ASCIIToUTF16(versions[i][0]), string16());
+ scoped_ptr<PluginGroup> group(PluginGroup::FromWebPluginInfo(plugin));
+ EXPECT_TRUE(group->Match(plugin));
+ group->AddPlugin(plugin, 0);
+ scoped_ptr<DictionaryValue> data(group->GetDataForUI());
+ std::string version;
+ data->GetString("version", &version);
+ EXPECT_EQ(versions[i][1], version);
+ }
+}
+
+TEST(PluginGroupTest, DisabledByPolicy) {
+ std::set<string16> disabled_plugins;
+ disabled_plugins.insert(ASCIIToUTF16("Disable this!"));
+ disabled_plugins.insert(ASCIIToUTF16("*Google*"));
+ PluginGroup::SetPolicyDisabledPluginPatterns(disabled_plugins);
+
+ EXPECT_FALSE(PluginGroup::IsPluginNameDisabledByPolicy(ASCIIToUTF16("42")));
+ EXPECT_TRUE(PluginGroup::IsPluginNameDisabledByPolicy(
+ ASCIIToUTF16("Disable this!")));
+ EXPECT_TRUE(PluginGroup::IsPluginNameDisabledByPolicy(
+ ASCIIToUTF16("Google Earth")));
+}
diff --git a/webkit/glue/plugins/plugin_host.cc b/webkit/glue/plugins/plugin_host.cc
index a1a6d5f..add6c03 100644
--- a/webkit/glue/plugins/plugin_host.cc
+++ b/webkit/glue/plugins/plugin_host.cc
@@ -310,7 +310,7 @@ uint32_t NPN_MemFlush(uint32_t size) {
// Should force a re-scan of the plugins directory to load new ones.
void NPN_ReloadPlugins(NPBool reloadPages) {
// TODO: implement me
- DLOG(INFO) << "NPN_ReloadPlugin is not implemented yet.";
+ DVLOG(1) << "NPN_ReloadPlugin is not implemented yet.";
}
// Requests a range of bytes for a seekable stream.
@@ -526,7 +526,7 @@ NPError NPN_NewStream(NPP id,
// Browser should put this stream into a window target.
//
// TODO: implement me
- DLOG(INFO) << "NPN_NewStream is not implemented yet.";
+ DVLOG(1) << "NPN_NewStream is not implemented yet.";
return NPERR_GENERIC_ERROR;
}
@@ -534,7 +534,7 @@ int32_t NPN_Write(NPP id, NPStream* stream, int32_t len, void* buffer) {
// Writes data to an existing Plugin-created stream.
// TODO: implement me
- DLOG(INFO) << "NPN_Write is not implemented yet.";
+ DVLOG(1) << "NPN_Write is not implemented yet.";
return NPERR_GENERIC_ERROR;
}
@@ -594,7 +594,7 @@ void NPN_Status(NPP id, const char* message) {
// Displays a message on the status line of the browser window.
// TODO: implement me
- DLOG(INFO) << "NPN_Status is not implemented yet.";
+ DVLOG(1) << "NPN_Status is not implemented yet.";
}
void NPN_InvalidateRect(NPP id, NPRect *invalidRect) {
@@ -797,16 +797,21 @@ NPError NPN_GetValue(NPP id, NPNVariable variable, void* value) {
rv = NPERR_NO_ERROR;
break;
}
- case NPNVsupportsCoreAnimationBool:
- case NPNVsupportsInvalidatingCoreAnimationBool: {
+ case NPNVsupportsCoreAnimationBool: {
// We only support the Core Animation model on 10.6 and higher
// TODO(stuartmorgan): Once existing CA plugins have implemented the
- // invalidating version, remove support for the other version.
+ // invalidating version, remove support for this one.
NPBool* supports_model = reinterpret_cast<NPBool*>(value);
*supports_model = SupportsSharingAcceleratedSurfaces() ? true : false;
rv = NPERR_NO_ERROR;
break;
}
+ case NPNVsupportsInvalidatingCoreAnimationBool: {
+ NPBool* supports_model = reinterpret_cast<NPBool*>(value);
+ *supports_model = true;
+ rv = NPERR_NO_ERROR;
+ break;
+ }
case NPNVsupportsOpenGLBool: {
// This drawing model was never widely supported, and we don't plan to
// support it.
@@ -824,7 +829,7 @@ NPError NPN_GetValue(NPP id, NPNVariable variable, void* value) {
rv = NPAPI::GetPepperExtensionsFunctions(value);
break;
default:
- DLOG(INFO) << "NPN_GetValue(" << variable << ") is not implemented yet.";
+ DVLOG(1) << "NPN_GetValue(" << variable << ") is not implemented yet.";
break;
}
return rv;
@@ -859,24 +864,22 @@ NPError NPN_SetValue(NPP id, NPPVariable variable, void* value) {
// Specifies whether you are pushing or popping the JSContext off.
// the stack
// TODO: implement me
- DLOG(INFO) <<
- "NPN_SetValue(NPPVJavascriptPushCallerBool) is not implemented.";
+ DVLOG(1) << "NPN_SetValue(NPPVJavascriptPushCallerBool) is not "
+ "implemented.";
return NPERR_GENERIC_ERROR;
case NPPVpluginKeepLibraryInMemory:
// Tells browser that plugin library should live longer than usual.
// TODO: implement me
- DLOG(INFO) <<
- "NPN_SetValue(NPPVpluginKeepLibraryInMemory) is not implemented.";
+ DVLOG(1) << "NPN_SetValue(NPPVpluginKeepLibraryInMemory) is not "
+ "implemented.";
return NPERR_GENERIC_ERROR;
#if defined(OS_MACOSX)
case NPPVpluginDrawingModel: {
int model = reinterpret_cast<int>(value);
- if (model == NPDrawingModelCoreGraphics) {
- plugin->set_drawing_model(static_cast<NPDrawingModel>(model));
- return NPERR_NO_ERROR;
- } else if ((model == NPDrawingModelCoreAnimation ||
- model == NPDrawingModelInvalidatingCoreAnimation) &&
- SupportsSharingAcceleratedSurfaces()) {
+ if (model == NPDrawingModelCoreGraphics ||
+ model == NPDrawingModelInvalidatingCoreAnimation ||
+ (model == NPDrawingModelCoreAnimation &&
+ SupportsSharingAcceleratedSurfaces())) {
plugin->set_drawing_model(static_cast<NPDrawingModel>(model));
return NPERR_NO_ERROR;
}
@@ -899,7 +902,7 @@ NPError NPN_SetValue(NPP id, NPPVariable variable, void* value) {
#endif
default:
// TODO: implement me
- DLOG(INFO) << "NPN_SetValue(" << variable << ") is not implemented.";
+ DVLOG(1) << "NPN_SetValue(" << variable << ") is not implemented.";
break;
}
@@ -909,13 +912,13 @@ NPError NPN_SetValue(NPP id, NPPVariable variable, void* value) {
void* NPN_GetJavaEnv() {
// TODO: implement me
- DLOG(INFO) << "NPN_GetJavaEnv is not implemented.";
+ DVLOG(1) << "NPN_GetJavaEnv is not implemented.";
return NULL;
}
void* NPN_GetJavaPeer(NPP) {
// TODO: implement me
- DLOG(INFO) << "NPN_GetJavaPeer is not implemented.";
+ DVLOG(1) << "NPN_GetJavaPeer is not implemented.";
return NULL;
}
diff --git a/webkit/glue/plugins/plugin_lib.cc b/webkit/glue/plugins/plugin_lib.cc
index 9a0770e..6c95274 100644
--- a/webkit/glue/plugins/plugin_lib.cc
+++ b/webkit/glue/plugins/plugin_lib.cc
@@ -6,7 +6,7 @@
#include "base/logging.h"
#include "base/message_loop.h"
-#include "base/stats_counters.h"
+#include "base/metrics/stats_counters.h"
#include "base/string_util.h"
#include "webkit/glue/webkit_glue.h"
#include "webkit/glue/plugins/plugin_instance.h"
@@ -72,7 +72,7 @@ PluginLib::PluginLib(const WebPluginInfo& info,
saved_data_(0),
instance_count_(0),
skip_unload_(false) {
- StatsCounter(kPluginLibrariesLoadedCounter).Increment();
+ base::StatsCounter(kPluginLibrariesLoadedCounter).Increment();
memset(static_cast<void*>(&plugin_funcs_), 0, sizeof(plugin_funcs_));
g_loaded_libs->push_back(this);
@@ -87,7 +87,7 @@ PluginLib::PluginLib(const WebPluginInfo& info,
}
PluginLib::~PluginLib() {
- StatsCounter(kPluginLibrariesLoadedCounter).Decrement();
+ base::StatsCounter(kPluginLibrariesLoadedCounter).Decrement();
if (saved_data_ != 0) {
// TODO - delete the savedData object here
}
@@ -143,13 +143,13 @@ void PluginLib::PreventLibraryUnload() {
PluginInstance* PluginLib::CreateInstance(const std::string& mime_type) {
PluginInstance* new_instance = new PluginInstance(this, mime_type);
instance_count_++;
- StatsCounter(kPluginInstancesActiveCounter).Increment();
+ base::StatsCounter(kPluginInstancesActiveCounter).Increment();
DCHECK_NE(static_cast<PluginInstance*>(NULL), new_instance);
return new_instance;
}
void PluginLib::CloseInstance() {
- StatsCounter(kPluginInstancesActiveCounter).Decrement();
+ base::StatsCounter(kPluginInstancesActiveCounter).Decrement();
instance_count_--;
// If a plugin is running in its own process it will get unloaded on process
// shutdown.
diff --git a/webkit/glue/plugins/plugin_lib_mac.mm b/webkit/glue/plugins/plugin_lib_mac.mm
index 07da77c..89444c8 100644
--- a/webkit/glue/plugins/plugin_lib_mac.mm
+++ b/webkit/glue/plugins/plugin_lib_mac.mm
@@ -6,8 +6,8 @@
#include "webkit/glue/plugins/plugin_lib.h"
+#include "base/mac/scoped_cftyperef.h"
#include "base/native_library.h"
-#include "base/scoped_cftyperef.h"
#include "base/scoped_ptr.h"
#include "base/string_split.h"
#include "base/string_util.h"
@@ -19,8 +19,9 @@ static const short kSTRTypeDefinitionResourceID = 128;
static const short kSTRTypeDescriptionResourceID = 127;
static const short kSTRPluginDescriptionResourceID = 126;
-namespace NPAPI
-{
+using base::mac::ScopedCFTypeRef;
+
+namespace NPAPI {
namespace {
@@ -161,7 +162,7 @@ bool GetSTRResource(CFBundleRef bundle, short res_id,
pointer += sizeof(short);
for (short i = 0; i < num_strings; ++i) {
// Despite being 8-bits wide, these are legacy encoded. Make a round trip.
- scoped_cftyperef<CFStringRef> str(CFStringCreateWithPascalStringNoCopy(
+ ScopedCFTypeRef<CFStringRef> str(CFStringCreateWithPascalStringNoCopy(
kCFAllocatorDefault,
(unsigned char*)pointer,
GetApplicationTextEncoding(), // is this right?
@@ -200,8 +201,8 @@ bool ReadSTRPluginInfo(const FilePath& filename, CFBundleRef bundle,
mime.mime_type = StringToLowerASCII(type_strings[2*i]);
if (have_type_descs && i < type_descs.size())
mime.description = UTF8ToUTF16(type_descs[i]);
- SplitString(StringToLowerASCII(type_strings[2*i+1]), ',',
- &mime.file_extensions);
+ base::SplitString(
+ StringToLowerASCII(type_strings[2*i+1]), ',', &mime.file_extensions);
info->mime_types.push_back(mime);
}
@@ -309,13 +310,13 @@ bool PluginLib::ReadWebPluginInfo(const FilePath &filename,
//
// Strictly speaking, only STR# 128 is required.
- scoped_cftyperef<CFURLRef> bundle_url(CFURLCreateFromFileSystemRepresentation(
+ ScopedCFTypeRef<CFURLRef> bundle_url(CFURLCreateFromFileSystemRepresentation(
kCFAllocatorDefault, (const UInt8*)filename.value().c_str(),
filename.value().length(), true));
if (!bundle_url)
return false;
- scoped_cftyperef<CFBundleRef> bundle(CFBundleCreate(kCFAllocatorDefault,
- bundle_url.get()));
+ ScopedCFTypeRef<CFBundleRef> bundle(CFBundleCreate(kCFAllocatorDefault,
+ bundle_url.get()));
if (!bundle)
return false;
diff --git a/webkit/glue/plugins/plugin_lib_posix.cc b/webkit/glue/plugins/plugin_lib_posix.cc
index fb813b6..ac937e1 100644
--- a/webkit/glue/plugins/plugin_lib_posix.cc
+++ b/webkit/glue/plugins/plugin_lib_posix.cc
@@ -235,7 +235,7 @@ void PluginLib::ParseMIMEDescription(
if (end == std::string::npos)
break;
const std::string extensions = description.substr(ofs, end - ofs);
- SplitString(extensions, ',', &mime_type.file_extensions);
+ base::SplitString(extensions, ',', &mime_type.file_extensions);
ofs = end + 1;
end = description.find(';', ofs);
diff --git a/webkit/glue/plugins/plugin_list.cc b/webkit/glue/plugins/plugin_list.cc
index b2a7634..4b3ce27 100644
--- a/webkit/glue/plugins/plugin_list.cc
+++ b/webkit/glue/plugins/plugin_list.cc
@@ -11,6 +11,7 @@
#include "base/logging.h"
#include "base/string_split.h"
#include "base/string_util.h"
+#include "base/sys_string_conversions.h"
#include "base/utf_string_conversions.h"
#include "googleurl/src/gurl.h"
#include "net/base/mime_util.h"
@@ -23,12 +24,19 @@ namespace NPAPI {
base::LazyInstance<PluginList> g_singleton(base::LINKER_INITIALIZED);
+static LoadPluginsFromDiskHookFunc g_load_plugins_hook;
+
// static
PluginList* PluginList::Singleton() {
return g_singleton.Pointer();
}
// static
+void PluginList::SetPluginLoadHook(LoadPluginsFromDiskHookFunc hook) {
+ g_load_plugins_hook = hook;
+}
+
+// static
bool PluginList::DebugPluginLoading() {
return CommandLine::ForCurrentProcess()->HasSwitch(
switches::kDebugPluginLoading);
@@ -108,9 +116,9 @@ bool PluginList::CreateWebPluginInfo(const PluginVersionInfo& pvi,
WebPluginInfo* info) {
std::vector<std::string> mime_types, file_extensions;
std::vector<string16> descriptions;
- SplitString(WideToUTF8(pvi.mime_types), '|', &mime_types);
- SplitString(WideToUTF8(pvi.file_extensions), '|', &file_extensions);
- SplitString(WideToUTF16(pvi.type_descriptions), '|', &descriptions);
+ base::SplitString(WideToUTF8(pvi.mime_types), '|', &mime_types);
+ base::SplitString(WideToUTF8(pvi.file_extensions), '|', &file_extensions);
+ base::SplitString(WideToUTF16(pvi.type_descriptions), '|', &descriptions);
info->mime_types.clear();
@@ -130,7 +138,7 @@ bool PluginList::CreateWebPluginInfo(const PluginVersionInfo& pvi,
WebPluginMimeType mime_type;
mime_type.mime_type = StringToLowerASCII(mime_types[i]);
if (file_extensions.size() > i)
- SplitString(file_extensions[i], ',', &mime_type.file_extensions);
+ base::SplitString(file_extensions[i], ',', &mime_type.file_extensions);
if (descriptions.size() > i) {
mime_type.description = descriptions[i];
@@ -154,10 +162,21 @@ bool PluginList::CreateWebPluginInfo(const PluginVersionInfo& pvi,
}
PluginList::PluginList()
- : plugins_loaded_(false), plugins_need_refresh_(false) {
+ : plugins_loaded_(false),
+ plugins_need_refresh_(false),
+ disable_outdated_plugins_(false) {
PlatformInit();
}
+bool PluginList::ShouldDisableGroup(const string16& group_name) {
+ AutoLock lock(lock_);
+ if (PluginGroup::IsPluginNameDisabledByPolicy(group_name)) {
+ disabled_groups_.insert(group_name);
+ return true;
+ }
+ return disabled_groups_.count(group_name) > 0;
+}
+
void PluginList::LoadPlugins(bool refresh) {
// Don't want to hold the lock while loading new plugins, so we don't block
// other methods if they're called on other threads.
@@ -177,6 +196,9 @@ void PluginList::LoadPlugins(bool refresh) {
internal_plugins = internal_plugins_;
}
+ if (g_load_plugins_hook)
+ g_load_plugins_hook();
+
std::vector<WebPluginInfo> new_plugins;
std::set<FilePath> visited_plugins;
@@ -216,15 +238,37 @@ void PluginList::LoadPlugins(bool refresh) {
if (webkit_glue::IsDefaultPluginEnabled())
LoadPlugin(FilePath(kDefaultPluginLibraryName), &new_plugins);
+ // Disable all of the plugins and plugin groups that are disabled by policy.
+ // There's currenly a bug that makes it impossible to correctly re-enable
+ // plugins or plugin-groups to their original, "pre-policy" state, so
+ // plugins and groups are only changed to a more "safe" state after a policy
+ // change, i.e. from enabled to disabled. See bug 54681.
+ PluginMap plugin_groups;
+ GetPluginGroups(&new_plugins, &plugin_groups);
+ for (PluginMap::const_iterator it = plugin_groups.begin();
+ it != plugin_groups.end(); ++it) {
+ PluginGroup* group = it->second.get();
+ string16 group_name = group->GetGroupName();
+ if (ShouldDisableGroup(group_name)) {
+ it->second->Enable(false);
+ }
+
+ if (disable_outdated_plugins_) {
+ group->DisableOutdatedPlugins();
+ if (!group->Enabled()) {
+ AutoLock lock(lock_);
+ disabled_groups_.insert(group_name);
+ }
+ }
+ }
+
// Only update the data now since loading plugins can take a while.
AutoLock lock(lock_);
- // Go through and mark new plugins in the disabled list as, well, disabled.
- for (std::vector<WebPluginInfo>::iterator it = new_plugins.begin();
- it != new_plugins.end();
- ++it) {
- if (disabled_plugins_.find(it->path) != disabled_plugins_.end())
- it->enabled = false;
+ // Mark disabled plugins as such.
+ for (size_t i = 0; i < new_plugins.size(); ++i) {
+ if (disabled_plugins_.count(new_plugins[i].path))
+ new_plugins[i].enabled = false;
}
plugins_ = new_plugins;
@@ -263,65 +307,6 @@ void PluginList::LoadPlugin(const FilePath& path,
plugins->push_back(plugin_info);
}
-bool PluginList::FindPlugin(const std::string& mime_type,
- bool allow_wildcard,
- WebPluginInfo* info) {
- DCHECK(mime_type == StringToLowerASCII(mime_type));
-
- LoadPlugins(false);
- AutoLock lock(lock_);
- for (size_t i = 0; i < plugins_.size(); ++i) {
- if (plugins_[i].enabled &&
- SupportsType(plugins_[i], mime_type, allow_wildcard)) {
- *info = plugins_[i];
- return true;
- }
- }
-
- return false;
-}
-
-bool PluginList::FindDisabledPlugin(const std::string& mime_type,
- bool allow_wildcard,
- WebPluginInfo* info) {
- DCHECK(mime_type == StringToLowerASCII(mime_type));
-
- LoadPlugins(false);
- AutoLock lock(lock_);
- for (size_t i = 0; i < plugins_.size(); ++i) {
- if (!plugins_[i].enabled &&
- SupportsType(plugins_[i], mime_type, allow_wildcard)) {
- *info = plugins_[i];
- return true;
- }
- }
-
- return false;
-}
-
-bool PluginList::FindPlugin(const GURL &url,
- std::string* actual_mime_type,
- WebPluginInfo* info) {
- LoadPlugins(false);
- AutoLock lock(lock_);
- std::string path = url.path();
- std::string::size_type last_dot = path.rfind('.');
- if (last_dot == std::string::npos)
- return false;
-
- std::string extension = StringToLowerASCII(std::string(path, last_dot+1));
-
- for (size_t i = 0; i < plugins_.size(); ++i) {
- if (plugins_[i].enabled &&
- SupportsExtension(plugins_[i], extension, actual_mime_type)) {
- *info = plugins_[i];
- return true;
- }
- }
-
- return false;
-}
-
bool PluginList::SupportsType(const WebPluginInfo& info,
const std::string &mime_type,
bool allow_wildcard) {
@@ -380,20 +365,111 @@ void PluginList::GetEnabledPlugins(bool refresh,
}
}
+void PluginList::GetPluginInfoArray(const GURL& url,
+ const std::string& mime_type,
+ bool allow_wildcard,
+ std::vector<WebPluginInfo>* info,
+ std::vector<std::string>* actual_mime_types)
+{
+ DCHECK(mime_type == StringToLowerASCII(mime_type));
+ DCHECK(info);
+
+ LoadPlugins(false);
+ AutoLock lock(lock_);
+ info->clear();
+ if (actual_mime_types)
+ actual_mime_types->clear();
+
+ std::set<FilePath> visited_plugins;
+
+ // Add in enabled plugins by mime type.
+ WebPluginInfo default_plugin;
+ for (size_t i = 0; i < plugins_.size(); ++i) {
+ if (plugins_[i].enabled &&
+ SupportsType(plugins_[i], mime_type, allow_wildcard)) {
+ FilePath path = plugins_[i].path;
+ if (path.value() != kDefaultPluginLibraryName &&
+ visited_plugins.insert(path).second) {
+ info->push_back(plugins_[i]);
+ if (actual_mime_types)
+ actual_mime_types->push_back(mime_type);
+ }
+ }
+ }
+
+ // Add in enabled plugins by url.
+ std::string path = url.path();
+ std::string::size_type last_dot = path.rfind('.');
+ if (last_dot != std::string::npos) {
+ std::string extension = StringToLowerASCII(std::string(path, last_dot+1));
+ std::string actual_mime_type;
+ for (size_t i = 0; i < plugins_.size(); ++i) {
+ if (plugins_[i].enabled &&
+ SupportsExtension(plugins_[i], extension, &actual_mime_type)) {
+ FilePath path = plugins_[i].path;
+ if (path.value() != kDefaultPluginLibraryName &&
+ visited_plugins.insert(path).second) {
+ info->push_back(plugins_[i]);
+ if (actual_mime_types)
+ actual_mime_types->push_back(actual_mime_type);
+ }
+ }
+ }
+ }
+
+ // Add in disabled plugins by mime type.
+ for (size_t i = 0; i < plugins_.size(); ++i) {
+ if (!plugins_[i].enabled &&
+ SupportsType(plugins_[i], mime_type, allow_wildcard)) {
+ FilePath path = plugins_[i].path;
+ if (path.value() != kDefaultPluginLibraryName &&
+ visited_plugins.insert(path).second) {
+ info->push_back(plugins_[i]);
+ if (actual_mime_types)
+ actual_mime_types->push_back(mime_type);
+ }
+ }
+ }
+
+ // Add the default plugin at the end if it supports the mime type given,
+ // and the default plugin is enabled.
+ if (!plugins_.empty() && webkit_glue::IsDefaultPluginEnabled()) {
+ const WebPluginInfo& default_info = plugins_.back();
+ if (SupportsType(default_info, mime_type, allow_wildcard)) {
+ info->push_back(default_info);
+ if (actual_mime_types)
+ actual_mime_types->push_back(mime_type);
+ }
+ }
+}
+
bool PluginList::GetPluginInfo(const GURL& url,
const std::string& mime_type,
bool allow_wildcard,
WebPluginInfo* info,
std::string* actual_mime_type) {
- bool found = FindPlugin(mime_type, allow_wildcard, info);
- if (!found || (info->path.value() == kDefaultPluginLibraryName)) {
- if (FindPlugin(url, actual_mime_type, info) ||
- FindDisabledPlugin(mime_type, allow_wildcard, info)) {
- found = true;
+ DCHECK(info);
+ std::vector<WebPluginInfo> info_list;
+
+ // GetPluginInfoArray has slightly less work to do if we can pass
+ // NULL for the mime type list...
+ if (actual_mime_type) {
+ std::vector<std::string> mime_type_list;
+ GetPluginInfoArray(
+ url, mime_type, allow_wildcard, &info_list, &mime_type_list);
+ if (!info_list.empty()) {
+ *info = info_list[0];
+ *actual_mime_type = mime_type_list[0];
+ return true;
+ }
+ } else {
+ GetPluginInfoArray(url, mime_type, allow_wildcard, &info_list, NULL);
+ if (!info_list.empty()) {
+ *info = info_list[0];
+ return true;
}
}
-
- return found;
+ return false;
}
bool PluginList::GetPluginInfoByPath(const FilePath& plugin_path,
@@ -410,6 +486,47 @@ bool PluginList::GetPluginInfoByPath(const FilePath& plugin_path,
return false;
}
+void PluginList::GetPluginGroups(bool load_if_necessary,
+ PluginMap* plugin_groups) {
+ if (load_if_necessary)
+ LoadPlugins(false);
+
+ AutoLock lock(lock_);
+ GetPluginGroups(&plugins_, plugin_groups);
+}
+
+// static
+void PluginList::GetPluginGroups(const std::vector<WebPluginInfo>* plugins,
+ PluginMap* plugin_groups) {
+ plugin_groups->clear();
+ // We first search for an existing group that matches our name,
+ // and only create a new group if we can't find any.
+ for (size_t i = 0; i < plugins->size(); ++i) {
+ const WebPluginInfo& web_plugin = (*plugins)[i];
+ PluginGroup* group = PluginGroup::FindGroupMatchingPlugin(
+ *plugin_groups, web_plugin);
+ if (!group) {
+ group = PluginGroup::CopyOrCreatePluginGroup(web_plugin);
+ std::string identifier = group->identifier();
+ // If the identifier is not unique, use the full path. This means that we
+ // probably won't be able to search for this group by identifier, but at
+ // least it's going to be in the set of plugin groups, and if there
+ // is already a plug-in with the same filename, it's probably going to
+ // handle the same MIME types (and it has a higher priority), so this one
+ // is not going to run anyway.
+ if (plugin_groups->find(identifier) != plugin_groups->end())
+#if defined(OS_POSIX)
+ identifier = web_plugin.path.value();
+#elif defined(OS_WIN)
+ identifier = base::SysWideToUTF8(web_plugin.path.value());
+#endif
+ DCHECK(plugin_groups->find(identifier) == plugin_groups->end());
+ (*plugin_groups)[identifier] = linked_ptr<PluginGroup>(group);
+ }
+ group->AddPlugin(web_plugin, i);
+ }
+}
+
bool PluginList::EnablePlugin(const FilePath& filename) {
AutoLock lock(lock_);
@@ -459,6 +576,46 @@ bool PluginList::DisablePlugin(const FilePath& filename) {
return did_disable;
}
+bool PluginList::EnableGroup(bool enable, const string16& group_name) {
+ bool did_change = false;
+ {
+ AutoLock lock(lock_);
+
+ std::set<string16>::iterator entry = disabled_groups_.find(group_name);
+ if (enable) {
+ if (entry == disabled_groups_.end())
+ return did_change; // Early exit if group not in disabled list.
+ disabled_groups_.erase(entry); // Remove from disabled list.
+ } else {
+ if (entry != disabled_groups_.end())
+ return did_change; // Early exit if group already in disabled list.
+ disabled_groups_.insert(group_name);
+ }
+ }
+
+ PluginMap plugin_groups;
+ GetPluginGroups(false, &plugin_groups);
+ for (PluginMap::const_iterator it = plugin_groups.begin();
+ it != plugin_groups.end(); ++it) {
+ if (it->second->GetGroupName() == group_name) {
+ if (it->second->Enabled() != enable) {
+ it->second->Enable(enable);
+ did_change = true;
+ break;
+ }
+ }
+ }
+
+ return did_change;
+}
+
+void PluginList::DisableOutdatedPluginGroups() {
+ disable_outdated_plugins_ = true;
+}
+
+PluginList::~PluginList() {
+}
+
void PluginList::Shutdown() {
// TODO
}
diff --git a/webkit/glue/plugins/plugin_list.h b/webkit/glue/plugins/plugin_list.h
index ce9da28..25b903b 100644
--- a/webkit/glue/plugins/plugin_list.h
+++ b/webkit/glue/plugins/plugin_list.h
@@ -5,6 +5,7 @@
#ifndef WEBKIT_GLUE_PLUGINS_PLUGIN_LIST_H_
#define WEBKIT_GLUE_PLUGINS_PLUGIN_LIST_H_
+#include <map>
#include <set>
#include <string>
#include <vector>
@@ -12,8 +13,10 @@
#include "base/basictypes.h"
#include "base/file_path.h"
+#include "base/linked_ptr.h"
#include "base/lock.h"
#include "third_party/npapi/bindings/nphostapi.h"
+#include "webkit/glue/plugins/plugin_group.h"
#include "webkit/glue/plugins/webplugininfo.h"
class GURL;
@@ -60,6 +63,8 @@ struct PluginVersionInfo {
PluginEntryPoints entry_points;
};
+typedef void (*LoadPluginsFromDiskHookFunc)();
+
// The PluginList is responsible for loading our NPAPI based plugins. It does
// so in whatever manner is appropriate for the platform. On Windows, it loads
// plugins from a known directory by looking for DLLs which start with "NP",
@@ -73,6 +78,9 @@ class PluginList {
// Gets the one instance of the PluginList.
static PluginList* Singleton();
+ // Set a hook that is called whenever we load plugins from the disk.
+ static void SetPluginLoadHook(LoadPluginsFromDiskHookFunc hook);
+
// Returns true if we're in debug-plugin-loading mode. This is controlled
// by a command line switch.
static bool DebugPluginLoading();
@@ -125,12 +133,24 @@ class PluginList {
// Get all the enabled plugins.
void GetEnabledPlugins(bool refresh, std::vector<WebPluginInfo>* plugins);
- // Returns true if a plugin is found for the given url and mime type
- // (including disabled plugins, for which |info->enabled| is false).
- // The mime type which corresponds to the URL is optionally returned
- // back.
- // The allow_wildcard parameter controls whether this function returns
- // plugins which support wildcard mime types (* as the mime type).
+ // Returns a list in |info| containing plugins that are found for
+ // the given url and mime type (including disabled plugins, for
+ // which |info->enabled| is false). The mime type which corresponds
+ // to the URL is optionally returned back in |actual_mime_types| (if
+ // it is non-NULL), one for each of the plugin info objects found.
+ // The |allow_wildcard| parameter controls whether this function
+ // returns plugins which support wildcard mime types (* as the mime
+ // type). The |info| parameter is required to be non-NULL. The
+ // list is in order of "most desirable" to "least desirable",
+ // meaning that the default plugin is at the end of the list.
+ void GetPluginInfoArray(const GURL& url,
+ const std::string& mime_type,
+ bool allow_wildcard,
+ std::vector<WebPluginInfo>* info,
+ std::vector<std::string>* actual_mime_types);
+
+ // Returns the first item from the list returned in GetPluginInfo in |info|.
+ // Returns true if it found a match. |actual_mime_type| may be NULL.
bool GetPluginInfo(const GURL& url,
const std::string& mime_type,
bool allow_wildcard,
@@ -142,6 +162,14 @@ class PluginList {
bool GetPluginInfoByPath(const FilePath& plugin_path,
WebPluginInfo* info);
+ typedef std::map<std::string, linked_ptr<PluginGroup> > PluginMap;
+
+ // Fill the map from identifier to plugin group for all plugin groups. If
+ // |load_if_necessary| is set, the plugins will be loaded if they haven't
+ // already been loaded, or if Refresh() has been called in the meantime;
+ // otherwise a possibly empty or stale list may be returned.
+ void GetPluginGroups(bool load_if_necessary, PluginMap* plugin_groups);
+
// Load a specific plugin with full path.
void LoadPlugin(const FilePath& filename,
std::vector<WebPluginInfo>* plugins);
@@ -159,6 +187,21 @@ class PluginList {
// will be disabled.
bool DisablePlugin(const FilePath& filename);
+ // Enable/disable a plugin group, specified by group_name. Returns |true| iff
+ // a plugin currently in the plugin list was actually enabled/disabled as a
+ // result; regardless of return value, if a plugin is found in the future with
+ // the given name, it will be enabled/disabled. Note that plugins are enabled
+ // by default as far as |PluginList| is concerned.
+ bool EnableGroup(bool enable, const string16& name);
+
+ // Disable all plugins groups that are known to be outdated, according to
+ // the information hardcoded in PluginGroup, to make sure that they can't
+ // be loaded on a web page and instead show a UI to update to the latest
+ // version.
+ void DisableOutdatedPluginGroups();
+
+ ~PluginList();
+
private:
// Constructors are private for singletons
PluginList();
@@ -180,23 +223,15 @@ class PluginList {
bool ShouldLoadPlugin(const WebPluginInfo& info,
std::vector<WebPluginInfo>* plugins);
- // Find a plugin by mime type; only searches enabled plugins.
- // The allow_wildcard parameter controls whether this function returns
- // plugins which support wildcard mime types (* as the mime type)
- bool FindPlugin(const std::string &mime_type,
- bool allow_wildcard,
- WebPluginInfo* info);
+ // Return whether a plug-in group with the given name should be disabled,
+ // either because it already is on the list of disabled groups, or because it
+ // is blacklisted by a policy. In the latter case, add the plugin group to the
+ // list of disabled groups as well.
+ bool ShouldDisableGroup(const string16& group_name);
- // Just like |FindPlugin| but it only looks at the disabled plug-ins.
- bool FindDisabledPlugin(const std::string &mime_type,
- bool allow_wildcard,
- WebPluginInfo* info);
-
- // Find a plugin by extension; only searches enabled plugins. Returns the
- // corresponding mime type.
- bool FindPlugin(const GURL &url,
- std::string* actual_mime_type,
- WebPluginInfo* info);
+ // Like GetPluginGroups above, but works on a given vector of plugins.
+ static void GetPluginGroups(const std::vector<WebPluginInfo>* plugins,
+ PluginMap* plugin_groups);
// Returns true if the given WebPluginInfo supports "mime-type".
// mime_type should be all lower case.
@@ -261,6 +296,11 @@ class PluginList {
// Path names of plugins to disable (the default is to enable them all).
std::set<FilePath> disabled_plugins_;
+ // Group names disable (the default is to enable them all).
+ std::set<string16> disabled_groups_;
+
+ bool disable_outdated_plugins_;
+
// Need synchronization for the above members since this object can be
// accessed on multiple threads.
Lock lock_;
diff --git a/webkit/glue/plugins/plugin_list_posix.cc b/webkit/glue/plugins/plugin_list_posix.cc
index b23909b..72891d1 100644
--- a/webkit/glue/plugins/plugin_list_posix.cc
+++ b/webkit/glue/plugins/plugin_list_posix.cc
@@ -133,7 +133,7 @@ void PluginList::GetPluginDirectories(std::vector<FilePath>* plugin_dirs) {
const char* moz_plugin_path = getenv("MOZ_PLUGIN_PATH");
if (moz_plugin_path) {
std::vector<std::string> paths;
- SplitString(moz_plugin_path, ':', &paths);
+ base::SplitString(moz_plugin_path, ':', &paths);
for (size_t i = 0; i < paths.size(); ++i)
plugin_dirs->push_back(FilePath(paths[i]));
}
diff --git a/webkit/glue/plugins/plugin_list_win.cc b/webkit/glue/plugins/plugin_list_win.cc
index b5ded9e..4869262 100644
--- a/webkit/glue/plugins/plugin_list_win.cc
+++ b/webkit/glue/plugins/plugin_list_win.cc
@@ -12,11 +12,11 @@
#include "base/command_line.h"
#include "base/file_util.h"
#include "base/path_service.h"
-#include "base/registry.h"
#include "base/scoped_ptr.h"
#include "base/string_number_conversions.h"
#include "base/string_split.h"
#include "base/string_util.h"
+#include "base/win/registry.h"
#include "webkit/glue/plugins/plugin_constants_win.h"
#include "webkit/glue/plugins/plugin_lib.h"
#include "webkit/glue/webkit_glue.h"
@@ -67,7 +67,7 @@ bool GetInstalledPath(const TCHAR* app, FilePath* out) {
reg_path.append(L"\\");
reg_path.append(app);
- RegKey key(HKEY_LOCAL_MACHINE, reg_path.c_str(), KEY_READ);
+ base::win::RegKey key(HKEY_LOCAL_MACHINE, reg_path.c_str(), KEY_READ);
std::wstring path;
if (key.ReadValue(kRegistryPath, &path)) {
*out = FilePath(path);
@@ -82,13 +82,13 @@ void GetPluginsInRegistryDirectory(
HKEY root_key,
const std::wstring& registry_folder,
std::set<FilePath>* plugin_dirs) {
- for (RegistryKeyIterator iter(root_key, registry_folder.c_str());
+ for (base::win::RegistryKeyIterator iter(root_key, registry_folder.c_str());
iter.Valid(); ++iter) {
// Use the registry to gather plugin across the file system.
std::wstring reg_path = registry_folder;
reg_path.append(L"\\");
reg_path.append(iter.Name());
- RegKey key(root_key, reg_path.c_str(), KEY_READ);
+ base::win::RegKey key(root_key, reg_path.c_str(), KEY_READ);
std::wstring path;
if (key.ReadValue(kRegistryPath, &path))
@@ -99,11 +99,12 @@ void GetPluginsInRegistryDirectory(
// Enumerate through the registry key to find all installed FireFox paths.
// FireFox 3 beta and version 2 can coexist. See bug: 1025003
void GetFirefoxInstalledPaths(std::vector<FilePath>* out) {
- RegistryKeyIterator it(HKEY_LOCAL_MACHINE, kRegistryFirefoxInstalled);
+ base::win::RegistryKeyIterator it(HKEY_LOCAL_MACHINE,
+ kRegistryFirefoxInstalled);
for (; it.Valid(); ++it) {
std::wstring full_path = std::wstring(kRegistryFirefoxInstalled) + L"\\" +
it.Name() + L"\\Main";
- RegKey key(HKEY_LOCAL_MACHINE, full_path.c_str(), KEY_READ);
+ base::win::RegKey key(HKEY_LOCAL_MACHINE, full_path.c_str(), KEY_READ);
std::wstring install_dir;
if (!key.ReadValue(L"Install Directory", &install_dir))
continue;
@@ -180,7 +181,8 @@ void GetWindowsMediaDirectory(std::set<FilePath>* plugin_dirs) {
void GetJavaDirectory(std::set<FilePath>* plugin_dirs) {
// Load the new NPAPI Java plugin
// 1. Open the main JRE key under HKLM
- RegKey java_key(HKEY_LOCAL_MACHINE, kRegistryJava, KEY_QUERY_VALUE);
+ base::win::RegKey java_key(HKEY_LOCAL_MACHINE, kRegistryJava,
+ KEY_QUERY_VALUE);
// 2. Read the current Java version
std::wstring java_version;
@@ -304,13 +306,13 @@ bool HaveSharedMimeType(const WebPluginInfo& plugin1,
// version is newer than a's, or false if it's equal or older.
bool IsNewerVersion(const std::wstring& a, const std::wstring& b) {
std::vector<std::wstring> a_ver, b_ver;
- SplitString(a, ',', &a_ver);
- SplitString(b, ',', &b_ver);
+ base::SplitString(a, ',', &a_ver);
+ base::SplitString(b, ',', &b_ver);
if (a_ver.size() == 1 && b_ver.size() == 1) {
a_ver.clear();
b_ver.clear();
- SplitString(a, '.', &a_ver);
- SplitString(b, '.', &b_ver);
+ base::SplitString(a, '.', &a_ver);
+ base::SplitString(b, '.', &b_ver);
}
if (a_ver.size() != b_ver.size())
return false;
@@ -371,7 +373,7 @@ bool PluginList::ShouldLoadPlugin(const WebPluginInfo& info,
// and don't depend on XPCOM.
if (filename == kJavaPlugin1 || filename == kJavaPlugin2) {
std::vector<std::wstring> ver;
- SplitString(info.version, '.', &ver);
+ base::SplitString(info.version, '.', &ver);
int major, minor, update;
if (ver.size() == 4 &&
base::StringToInt(ver[0], &major) &&
diff --git a/webkit/glue/plugins/plugin_web_event_converter_mac.h b/webkit/glue/plugins/plugin_web_event_converter_mac.h
index 02f113a..ec5b86f 100644
--- a/webkit/glue/plugins/plugin_web_event_converter_mac.h
+++ b/webkit/glue/plugins/plugin_web_event_converter_mac.h
@@ -25,12 +25,6 @@ class PluginWebEventConverter {
// could not be converted.
virtual bool InitWithEvent(const WebKit::WebInputEvent& web_event);
- // Sets a zoom level to apply to mouse coordinates. Must be called after
- // InitWithEvent.
- // TODO(stuartmorgan): Re-evaluate whether this is necessary when
- // http://crbug.com/9996 is fixed.
- virtual void SetZoomLevel(float zoom) = 0;
-
// Returns a pointer to a plugin event--suitable for passing to
// NPP_HandleEvent--corresponding to the the web event this converter was
// created with. The pointer is valid only as long as this object is.
diff --git a/webkit/glue/plugins/plugin_web_event_converter_mac.mm b/webkit/glue/plugins/plugin_web_event_converter_mac.mm
index d8b5c05..030ed06 100644
--- a/webkit/glue/plugins/plugin_web_event_converter_mac.mm
+++ b/webkit/glue/plugins/plugin_web_event_converter_mac.mm
@@ -49,8 +49,6 @@ class CarbonPluginWebEventConverter : public PluginWebEventConverter {
virtual bool InitWithEvent(const WebInputEvent& web_event);
- virtual void SetZoomLevel(float zooom);
-
virtual void* plugin_event() { return &carbon_event_; }
protected:
@@ -77,12 +75,6 @@ bool CarbonPluginWebEventConverter::InitWithEvent(
return PluginWebEventConverter::InitWithEvent(web_event);
}
-void CarbonPluginWebEventConverter::SetZoomLevel(float zoom) {
- // Nothing to do here; because the event is built using the WebMouseEvent's
- // global coordinates, and the dummy window is in the right place, zoom has
- // no effect.
-}
-
bool CarbonPluginWebEventConverter::ConvertKeyboardEvent(
const WebKeyboardEvent& key_event) {
// TODO: Figure out how to handle Unicode input to plugins, if that's
@@ -185,8 +177,6 @@ public:
virtual bool InitWithEvent(const WebInputEvent& web_event);
- virtual void SetZoomLevel(float zoom);
-
virtual void* plugin_event() { return &cocoa_event_; }
protected:
@@ -212,24 +202,6 @@ bool CocoaPluginWebEventConverter::InitWithEvent(
return PluginWebEventConverter::InitWithEvent(web_event);
}
-void CocoaPluginWebEventConverter::SetZoomLevel(float zoom) {
- // Make sure we are dealing with a mouse event.
- if (!(cocoa_event_.type != NPCocoaEventMouseDown ||
- cocoa_event_.type != NPCocoaEventMouseUp ||
- cocoa_event_.type != NPCocoaEventMouseMoved ||
- cocoa_event_.type != NPCocoaEventMouseEntered ||
- cocoa_event_.type != NPCocoaEventMouseExited ||
- cocoa_event_.type != NPCocoaEventMouseDragged ||
- cocoa_event_.type != NPCocoaEventScrollWheel)) {
- NOTREACHED();
- return;
- }
- cocoa_event_.data.mouse.pluginX =
- round(cocoa_event_.data.mouse.pluginX * zoom);
- cocoa_event_.data.mouse.pluginY =
- round(cocoa_event_.data.mouse.pluginY * zoom);
-}
-
bool CocoaPluginWebEventConverter::ConvertKeyboardEvent(
const WebKeyboardEvent& key_event) {
cocoa_event_.data.key.keyCode = key_event.nativeKeyCode;
diff --git a/webkit/glue/plugins/ppb_private.h b/webkit/glue/plugins/ppb_private.h
index 218f73a..07b32ec 100644
--- a/webkit/glue/plugins/ppb_private.h
+++ b/webkit/glue/plugins/ppb_private.h
@@ -5,13 +5,20 @@
#ifndef WEBKIT_GLUE_PLUGINS_PPB_PRIVATE_H_
#define WEBKIT_GLUE_PLUGINS_PPB_PRIVATE_H_
+#include "third_party/ppapi/c/dev/ppb_font_dev.h"
+#include "third_party/ppapi/c/pp_instance.h"
#include "third_party/ppapi/c/pp_module.h"
+#include "third_party/ppapi/c/pp_resource.h"
#include "third_party/ppapi/c/pp_var.h"
#define PPB_PRIVATE_INTERFACE "PPB_Private;1"
+// From the public PPB_Font_Dev file.
+struct PP_FontDescription_Dev;
+
typedef enum {
PP_RESOURCESTRING_PDFGETPASSWORD = 0,
+ PP_RESOURCESTRING_PDFLOADING = 1
} PP_ResourceString;
typedef enum {
@@ -41,17 +48,6 @@ typedef enum {
} PP_ResourceImage;
typedef enum {
- PP_PRIVATEFONTPITCH_DEFAULT = 0,
- PP_PRIVATEFONTPITCH_FIXED = 1
-} PP_PrivateFontPitch;
-
-typedef enum {
- PP_PRIVATEFONTFAMILY_DEFAULT = 0,
- PP_PRIVATEFONTFAMILY_ROMAN = 1,
- PP_PRIVATEFONTFAMILY_SCRIPT = 2
-} PP_PrivateFontFamily;
-
-typedef enum {
PP_PRIVATEFONTCHARSET_ANSI = 0,
PP_PRIVATEFONTCHARSET_DEFAULT = 1,
PP_PRIVATEFONTCHARSET_SYMBOL = 2,
@@ -77,9 +73,11 @@ struct PP_PrivateFontFileDescription {
const char* face;
uint32_t weight;
bool italic;
- PP_PrivateFontPitch pitch;
- PP_PrivateFontFamily family;
- PP_PrivateFontCharset charset;
+};
+
+struct PP_PrivateFindResult {
+ int start_index;
+ int length;
};
struct PPB_Private {
@@ -91,10 +89,13 @@ struct PPB_Private {
PP_ResourceImage image_id);
// Returns a resource identifying a font file corresponding to the given font
- // request after applying the browser-specific fallback. Linux only.
+ // request after applying the browser-specific fallback.
+ //
+ // Currently Linux-only.
PP_Resource (*GetFontFileWithFallback)(
PP_Module module,
- const PP_PrivateFontFileDescription* description);
+ const PP_FontDescription_Dev* description,
+ PP_PrivateFontCharset charset);
// Given a resource previously returned by GetFontFileWithFallback, returns
// a pointer to the requested font table. Linux only.
@@ -102,6 +103,29 @@ struct PPB_Private {
uint32_t table,
void* output,
uint32_t* output_length);
+
+ // Search the given string using ICU. Use PPB_Core's MemFree on results when
+ // done.
+ void (*SearchString)(
+ PP_Module module,
+ const unsigned short* string,
+ const unsigned short* term,
+ bool case_sensitive,
+ PP_PrivateFindResult** results,
+ int* count);
+
+ // Since WebFrame doesn't know about Pepper requests, it'll think the page has
+ // finished loading even if there are outstanding requests by the plugin.
+ // Take this out once WebFrame knows about requests by pepper plugins.
+ void (*DidStartLoading)(PP_Instance instance);
+ void (*DidStopLoading)(PP_Instance instance);
+
+ // Sets content restriction for a full-page plugin (i.e. can't copy/print).
+ // The value is a bitfield of ContentRestriction enums.
+ void (*SetContentRestriction)(PP_Instance instance, int restrictions);
+
+ // Use UMA so we know average pdf page count.
+ void (*HistogramPDFPageCount)(int count);
};
#endif // WEBKIT_GLUE_PLUGINS_PPB_PRIVATE_H_
diff --git a/webkit/glue/plugins/ppb_private2.h b/webkit/glue/plugins/ppb_private2.h
index ca45471..0b0df98 100644
--- a/webkit/glue/plugins/ppb_private2.h
+++ b/webkit/glue/plugins/ppb_private2.h
@@ -5,17 +5,106 @@
#ifndef WEBKIT_GLUE_PLUGINS_PPB_PRIVATE2_H_
#define WEBKIT_GLUE_PLUGINS_PPB_PRIVATE2_H_
+#ifdef _WIN32
+#include <windows.h>
+#endif
+
+#include "third_party/ppapi/c/pp_errors.h"
#include "third_party/ppapi/c/pp_instance.h"
#include "third_party/ppapi/c/pp_module.h"
+#include "third_party/ppapi/c/pp_point.h"
+#include "third_party/ppapi/c/pp_rect.h"
+#include "third_party/ppapi/c/pp_resource.h"
#include "third_party/ppapi/c/pp_var.h"
-#define PPB_PRIVATE2_INTERFACE "PPB_Private2;1"
+#define PPB_PRIVATE2_INTERFACE "PPB_Private2;3"
+
+#ifdef _WIN32
+typedef HANDLE PP_FileHandle;
+static const PP_FileHandle PP_kInvalidFileHandle = NULL;
+#else
+typedef int PP_FileHandle;
+static const PP_FileHandle PP_kInvalidFileHandle = -1;
+#endif
+
+struct PP_FontDescription_Dev;
+struct PP_FileInfo_Dev;
+
+struct PP_DirEntry_Dev {
+ const char* name;
+ bool is_dir;
+};
+
+struct PP_DirContents_Dev {
+ int32_t count;
+ PP_DirEntry_Dev* entries;
+};
struct PPB_Private2 {
// Sets or clears the rendering hint that the given plugin instance is always
// on top of page content. Somewhat more optimized painting can be used in
// this case.
void (*SetInstanceAlwaysOnTop)(PP_Instance instance, bool on_top);
+
+ bool (*DrawGlyphs)(PP_Resource pp_image_data,
+ const PP_FontDescription_Dev* font_desc,
+ uint32_t color,
+ PP_Point position,
+ PP_Rect clip,
+ float transformation[3][3],
+ uint32_t glyph_count,
+ uint16_t glyph_indices[],
+ PP_Point glyph_advances[]);
+
+ // Retrieves the proxy that will be used for the given URL. The result will
+ // be a string in PAC format, or an undefined var on error.
+ PP_Var (*GetProxyForURL)(PP_Module module, const char* url);
+
+ // Opens a module-local file, returning a file descriptor (posix) or a HANDLE
+ // (win32) into file. Module-local file paths (here and below) are
+ // '/'-separated UTF-8 strings, relative to a module-specific root. The return
+ // value is the ppapi error, PP_OK if success, one of the PP_ERROR_* in case
+ // of failure.
+ int32_t (*OpenModuleLocalFile)(PP_Module module,
+ const char* path,
+ int32_t mode,
+ PP_FileHandle* file);
+
+ // Renames a module-local file. The return value is the ppapi error, PP_OK if
+ // success, one of the PP_ERROR_* in case of failure.
+ int32_t (*RenameModuleLocalFile)(PP_Module module,
+ const char* path_from,
+ const char* path_to);
+
+ // Deletes a module-local file or directory. If recursive is set and the path
+ // points to a directory, deletes all the contents of the directory. The
+ // return value is the ppapi error, PP_OK if success, one of the PP_ERROR_* in
+ // case of failure.
+ int32_t (*DeleteModuleLocalFileOrDir)(PP_Module module,
+ const char* path,
+ bool recursive);
+
+ // Creates a module-local directory. The return value is the ppapi error,
+ // PP_OK if success, one of the PP_ERROR_* in case of failure.
+ int32_t (*CreateModuleLocalDir)(PP_Module module, const char* path);
+
+ // Queries information about a module-local file. The return value is the
+ // ppapi error, PP_OK if success, one of the PP_ERROR_* in case of failure.
+ int32_t (*QueryModuleLocalFile)(PP_Module module,
+ const char* path,
+ PP_FileInfo_Dev* info);
+
+ // Gets the list of files contained in a module-local directory. The return
+ // value is the ppapi error, PP_OK if success, one of the PP_ERROR_* in case
+ // of failure. If non-NULL, the returned contents should be freed with
+ // FreeModuleLocalDirContents.
+ int32_t (*GetModuleLocalDirContents)(PP_Module module,
+ const char* path,
+ PP_DirContents_Dev** contents);
+
+ // Frees the data allocated by GetModuleLocalDirContents.
+ void (*FreeModuleLocalDirContents)(PP_Module module,
+ PP_DirContents_Dev* contents);
};
#endif // WEBKIT_GLUE_PLUGINS_PPB_PRIVATE2_H_
diff --git a/webkit/glue/plugins/ppp_private.h b/webkit/glue/plugins/ppp_private.h
new file mode 100644
index 0000000..4bc3812
--- /dev/null
+++ b/webkit/glue/plugins/ppp_private.h
@@ -0,0 +1,20 @@
+// Copyright (c) 2010 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef WEBKIT_GLUE_PLUGINS_PPP_PRIVATE_H_
+#define WEBKIT_GLUE_PLUGINS_PPP_PRIVATE_H_
+
+#include "third_party/ppapi/c/pp_instance.h"
+#include "third_party/ppapi/c/pp_point.h"
+#include "third_party/ppapi/c/pp_var.h"
+
+#define PPP_PRIVATE_INTERFACE "PPP_Private;1"
+
+struct PPP_Private {
+ // Returns an absolute URL if the position is over a link.
+ PP_Var (*GetLinkAtPosition)(PP_Instance instance,
+ PP_Point point);
+};
+
+#endif // WEBKIT_GLUE_PLUGINS_PPP_PRIVATE_H_
diff --git a/webkit/glue/plugins/webplugin.h b/webkit/glue/plugins/webplugin.h
index 19c6cb0..36426fa 100644
--- a/webkit/glue/plugins/webplugin.h
+++ b/webkit/glue/plugins/webplugin.h
@@ -29,6 +29,9 @@ namespace webkit_glue {
class WebPluginDelegate;
class WebPluginParentView;
class WebPluginResourceClient;
+#if defined(OS_MACOSX)
+class WebPluginAcceleratedSurface;
+#endif
// Describes the new location for a plugin window.
struct WebPluginGeometry {
@@ -146,24 +149,19 @@ class WebPlugin {
bool defer) = 0;
#if defined(OS_MACOSX)
+ // Enables/disables plugin IME.
+ virtual void SetImeEnabled(bool enabled) {};
+
// Synthesize a fake window handle for the plug-in to identify the instance
// to the browser, allowing mapping to a surface for hardware accelleration
// of plug-in content. The browser generates the handle which is then set on
// the plug-in. |opaque| indicates whether the content should be treated as
// opaque or translucent.
+ // TODO(stuartmorgan): Move this into WebPluginProxy.
virtual void BindFakePluginWindowHandle(bool opaque) {}
- // Tell the browser (via the renderer) to invalidate because the
- // accelerated buffers have changed.
- virtual void AcceleratedFrameBuffersDidSwap(gfx::PluginWindowHandle window) {}
-
- // Tell the renderer and browser to associate the given plugin handle with
- // |accelerated_surface_identifier|. The geometry is used to resize any
- // native "window" (which on the Mac is a CALayer).
- virtual void SetAcceleratedSurface(gfx::PluginWindowHandle window,
- int32 width,
- int32 height,
- uint64 accelerated_surface_identifier) {}
+ // Returns the accelerated surface abstraction for accelerated plugins.
+ virtual WebPluginAcceleratedSurface* GetAcceleratedSurface() { return NULL; }
#endif
// Gets the WebPluginDelegate that implements the interface.
diff --git a/webkit/glue/plugins/webplugin_accelerated_surface_mac.h b/webkit/glue/plugins/webplugin_accelerated_surface_mac.h
new file mode 100644
index 0000000..ba3f8ca
--- /dev/null
+++ b/webkit/glue/plugins/webplugin_accelerated_surface_mac.h
@@ -0,0 +1,43 @@
+// Copyright (c) 2006-2009 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef WEBKIT_GLUE_WEBPLUGIN_ACCELERATED_SURFACE_MAC_H_
+#define WEBKIT_GLUE_WEBPLUGIN_ACCELERATED_SURFACE_MAC_H_
+#pragma once
+
+#include "gfx/native_widget_types.h"
+#include "gfx/size.h"
+
+// Avoid having to include OpenGL headers here.
+typedef struct _CGLContextObject* CGLContextObj;
+
+namespace webkit_glue {
+
+// Interface class for interacting with an accelerated plugin surface, used
+// for the Core Animation flavors of plugin drawing on the Mac.
+class WebPluginAcceleratedSurface {
+ public:
+ virtual ~WebPluginAcceleratedSurface() {}
+
+ // Sets the window handle used throughout the browser to identify this
+ // surface.
+ virtual void SetWindowHandle(gfx::PluginWindowHandle window) = 0;
+
+ // Sets the size of the surface.
+ virtual void SetSize(const gfx::Size& size) = 0;
+
+ // Returns the context used to draw into this surface.
+ virtual CGLContextObj context() = 0;
+
+ // Readies the surface for drawing. Must be called before any drawing session.
+ virtual void StartDrawing() = 0;
+
+ // Ends a drawing session. Changes to the surface may not be reflected until
+ // this is called.
+ virtual void EndDrawing() = 0;
+};
+
+} // namespace webkit_glue
+
+#endif // WEBKIT_GLUE_WEBPLUGIN_ACCELERATED_SURFACE_MAC_H_
diff --git a/webkit/glue/plugins/webplugin_delegate_impl.cc b/webkit/glue/plugins/webplugin_delegate_impl.cc
index 5374546..c54bbc8 100644
--- a/webkit/glue/plugins/webplugin_delegate_impl.cc
+++ b/webkit/glue/plugins/webplugin_delegate_impl.cc
@@ -1,4 +1,4 @@
-// Copyright (c) 2006-2008 The Chromium Authors. All rights reserved.
+// Copyright (c) 2010 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
@@ -11,7 +11,6 @@
#include "base/message_loop.h"
#include "base/process_util.h"
#include "base/scoped_ptr.h"
-#include "base/stats_counters.h"
#include "base/string_util.h"
#include "third_party/WebKit/WebKit/chromium/public/WebInputEvent.h"
#include "webkit/glue/plugins/plugin_constants_win.h"
diff --git a/webkit/glue/plugins/webplugin_delegate_impl.h b/webkit/glue/plugins/webplugin_delegate_impl.h
index 650d398..30a4a58 100644
--- a/webkit/glue/plugins/webplugin_delegate_impl.h
+++ b/webkit/glue/plugins/webplugin_delegate_impl.h
@@ -11,6 +11,7 @@
#include <list>
#include "base/ref_counted.h"
+#include "base/scoped_ptr.h"
#include "base/task.h"
#include "base/time.h"
#include "base/timer.h"
@@ -20,10 +21,6 @@
#include "webkit/glue/plugins/webplugin_delegate.h"
#include "webkit/glue/webcursor.h"
-#if defined(OS_MACOSX)
-#include "app/surface/accelerated_surface_mac.h"
-#endif
-
#if defined(USE_X11)
#include "app/x11_util.h"
@@ -52,6 +49,9 @@ class QuickDrawDrawingManager;
class CALayer;
class CARenderer;
#endif
+namespace webkit_glue {
+class WebPluginAcceleratedSurface;
+}
#endif
// An implementation of WebPluginDelegate that runs in the plugin process,
@@ -161,6 +161,8 @@ class WebPluginDelegateImpl : public webkit_glue::WebPluginDelegate {
// Frames are in screen coordinates.
void WindowFrameChanged(const gfx::Rect& window_frame,
const gfx::Rect& view_frame);
+ // Informs the plugin that IME composition has been confirmed.
+ void ImeCompositionConfirmed(const string16& text);
// Informs the delegate that the plugin set a Carbon ThemeCursor.
void SetThemeCursor(ThemeCursor cursor);
// Informs the delegate that the plugin set a Carbon Cursor.
@@ -385,20 +387,15 @@ class WebPluginDelegateImpl : public webkit_glue::WebPluginDelegate {
void SetContentAreaOrigin(const gfx::Point& origin);
// Updates everything that depends on the plugin's absolute screen location.
void PluginScreenLocationChanged();
+ // Updates anything that depends on plugin visibility.
+ void PluginVisibilityChanged();
- // Returns the apparent zoom ratio for the given event, as inferred from our
- // current knowledge about about where on screen the plugin is.
- // This is a temporary workaround for <http://crbug.com/9996>; once that is
- // fixed we should have correct event coordinates (or an explicit
- // notification of zoom level).
- float ApparentEventZoomLevel(const WebKit::WebMouseEvent& event);
+ // Enables/disables IME.
+ void SetImeEnabled(bool enabled);
// Informs the browser about the updated accelerated drawing surface.
void UpdateAcceleratedSurface();
- // Updates anything that depends on plugin visibility.
- void PluginVisibilityChanged();
-
// Uses a CARenderer to draw the plug-in's layer in our OpenGL surface.
void DrawLayerInSurface();
@@ -432,7 +429,7 @@ class WebPluginDelegateImpl : public webkit_glue::WebPluginDelegate {
#endif
CALayer* layer_; // Used for CA drawing mode. Weak, retained by plug-in.
- AcceleratedSurface* surface_;
+ webkit_glue::WebPluginAcceleratedSurface* surface_; // Weak ref.
CARenderer* renderer_; // Renders layer_ to surface_.
scoped_ptr<base::RepeatingTimer<WebPluginDelegateImpl> > redraw_timer_;
@@ -447,6 +444,8 @@ class WebPluginDelegateImpl : public webkit_glue::WebPluginDelegate {
gfx::Rect cached_clip_rect_;
+ bool ime_enabled_;
+
scoped_ptr<ExternalDragTracker> external_drag_tracker_;
#endif // OS_MACOSX
diff --git a/webkit/glue/plugins/webplugin_delegate_impl_gtk.cc b/webkit/glue/plugins/webplugin_delegate_impl_gtk.cc
index 3d112fa..bceda0e 100644
--- a/webkit/glue/plugins/webplugin_delegate_impl_gtk.cc
+++ b/webkit/glue/plugins/webplugin_delegate_impl_gtk.cc
@@ -14,7 +14,7 @@
#include "base/file_util.h"
#include "base/message_loop.h"
#include "base/process_util.h"
-#include "base/stats_counters.h"
+#include "base/metrics/stats_counters.h"
#include "base/string_util.h"
#include "gfx/blit.h"
#include "skia/ext/platform_canvas.h"
@@ -443,8 +443,8 @@ void WebPluginDelegateImpl::WindowlessPaint(cairo_t* context,
}
// Tell the plugin to paint into the pixmap.
- static StatsRate plugin_paint("Plugin.Paint");
- StatsScope<StatsRate> scope(plugin_paint);
+ static base::StatsRate plugin_paint("Plugin.Paint");
+ base::StatsScope<base::StatsRate> scope(plugin_paint);
NPError err = instance()->NPP_HandleEvent(&np_event);
DCHECK_EQ(err, NPERR_NO_ERROR);
@@ -474,8 +474,8 @@ void WebPluginDelegateImpl::WindowlessPaint(cairo_t* context,
event.drawable = GDK_PIXMAP_XID(pixmap_);
// Tell the plugin to paint into the pixmap.
- static StatsRate plugin_paint("Plugin.Paint");
- StatsScope<StatsRate> scope(plugin_paint);
+ static base::StatsRate plugin_paint("Plugin.Paint");
+ base::StatsScope<base::StatsRate> scope(plugin_paint);
NPError err = instance()->NPP_HandleEvent(&np_event);
DCHECK_EQ(err, NPERR_NO_ERROR);
diff --git a/webkit/glue/plugins/webplugin_delegate_impl_mac.mm b/webkit/glue/plugins/webplugin_delegate_impl_mac.mm
index 614f1d2..cca8695 100644
--- a/webkit/glue/plugins/webplugin_delegate_impl_mac.mm
+++ b/webkit/glue/plugins/webplugin_delegate_impl_mac.mm
@@ -13,10 +13,11 @@
#include "base/file_util.h"
#include "base/message_loop.h"
+#include "base/metrics/stats_counters.h"
#include "base/scoped_ptr.h"
-#include "base/stats_counters.h"
#include "base/string_util.h"
#include "base/utf_string_conversions.h"
+#include "base/sys_string_conversions.h"
#include "third_party/WebKit/WebKit/chromium/public/WebInputEvent.h"
#include "webkit/glue/plugins/plugin_instance.h"
#include "webkit/glue/plugins/plugin_lib.h"
@@ -24,6 +25,7 @@
#include "webkit/glue/plugins/plugin_stream_url.h"
#include "webkit/glue/plugins/plugin_web_event_converter_mac.h"
#include "webkit/glue/plugins/webplugin.h"
+#include "webkit/glue/plugins/webplugin_accelerated_surface_mac.h"
#include "webkit/glue/webkit_glue.h"
#ifndef NP_NO_CARBON
@@ -262,6 +264,7 @@ WebPluginDelegateImpl::WebPluginDelegateImpl(
initial_window_focus_(false),
container_is_visible_(false),
have_called_set_window_(false),
+ ime_enabled_(false),
external_drag_tracker_(new ExternalDragTracker()),
handle_event_depth_(0),
first_set_window_call_(true),
@@ -359,9 +362,9 @@ bool WebPluginDelegateImpl::PlatformInitialize() {
if (instance()->event_model() != NPEventModelCocoa)
return false;
window_.type = NPWindowTypeDrawable;
- // Ask the plug-in for the CALayer it created for rendering content. Have
- // the renderer tell the browser to create a "windowed plugin" to host
- // the IOSurface.
+ // Ask the plug-in for the CALayer it created for rendering content.
+ // Create a surface to host it, and request a "window" handle to identify
+ // the surface.
CALayer* layer = nil;
NPError err = instance()->NPP_GetValue(NPPVpluginCoreAnimationLayer,
reinterpret_cast<void*>(&layer));
@@ -371,8 +374,8 @@ bool WebPluginDelegateImpl::PlatformInitialize() {
redraw_timer_.reset(new base::RepeatingTimer<WebPluginDelegateImpl>);
}
layer_ = layer;
- surface_ = new AcceleratedSurface;
- surface_->Initialize(NULL, true);
+ surface_ = plugin_->GetAcceleratedSurface();
+
renderer_ = [[CARenderer rendererWithCGLContext:surface_->context()
options:NULL] retain];
[renderer_ setLayer:layer_];
@@ -421,11 +424,6 @@ void WebPluginDelegateImpl::PlatformDestroyInstance() {
[renderer_ release];
renderer_ = nil;
layer_ = nil;
- if (surface_) {
- surface_->Destroy();
- delete surface_;
- surface_ = NULL;
- }
}
void WebPluginDelegateImpl::UpdateGeometryAndContext(
@@ -577,7 +575,13 @@ bool WebPluginDelegateImpl::PlatformHandleInputEvent(
event_scope.reset(new NPAPI::ScopedCurrentPluginEvent(
instance(), static_cast<NPCocoaEvent*>(plugin_event)));
}
- bool handled = instance()->NPP_HandleEvent(plugin_event) != 0;
+ int16_t handle_response = instance()->NPP_HandleEvent(plugin_event);
+ bool handled = handle_response != kNPEventNotHandled;
+
+ if (handled && event.type == WebInputEvent::KeyDown) {
+ // Update IME state as requested by the plugin.
+ SetImeEnabled(handle_response == kNPEventStartIME);
+ }
// Plugins don't give accurate information about whether or not they handled
// events, so browsers on the Mac ignore the return value.
@@ -654,8 +658,8 @@ void WebPluginDelegateImpl::WindowlessPaint(gfx::NativeDrawingContext context,
return;
DCHECK(buffer_context_ == context);
- static StatsRate plugin_paint("Plugin.Paint");
- StatsScope<StatsRate> scope(plugin_paint);
+ static base::StatsRate plugin_paint("Plugin.Paint");
+ base::StatsScope<base::StatsRate> scope(plugin_paint);
// Plugin invalidates trigger asynchronous paints with the original
// invalidation rect; the plugin may be resized before the paint is handled,
@@ -782,6 +786,9 @@ void WebPluginDelegateImpl::SetWindowHasFocus(bool has_focus) {
return;
containing_window_has_focus_ = has_focus;
+ if (!has_focus)
+ SetImeEnabled(false);
+
#ifndef NP_NO_QUICKDRAW
// Make sure controls repaint with the correct look.
if (quirks_ & PLUGIN_QUIRK_ALLOW_FASTER_QUICKDRAW_PATH)
@@ -818,6 +825,9 @@ bool WebPluginDelegateImpl::PlatformSetPluginHasFocus(bool focused) {
if (!have_called_set_window_)
return false;
+ if (!focused)
+ SetImeEnabled(false);
+
ScopedActiveDelegate active_delegate(this);
switch (instance()->event_model()) {
@@ -882,6 +892,20 @@ void WebPluginDelegateImpl::WindowFrameChanged(const gfx::Rect& window_frame,
SetContentAreaOrigin(gfx::Point(view_frame.x(), view_frame.y()));
}
+void WebPluginDelegateImpl::ImeCompositionConfirmed(const string16& text) {
+ if (instance()->event_model() != NPEventModelCocoa) {
+ DLOG(ERROR) << "IME text receieved in Carbon event model";
+ return;
+ }
+
+ NPCocoaEvent text_event;
+ memset(&text_event, 0, sizeof(NPCocoaEvent));
+ text_event.type = NPCocoaEventTextInput;
+ text_event.data.text.text =
+ reinterpret_cast<NPNSString*>(base::SysUTF16ToNSString(text));
+ instance()->NPP_HandleEvent(&text_event);
+}
+
void WebPluginDelegateImpl::SetThemeCursor(ThemeCursor cursor) {
current_windowless_cursor_.InitFromThemeCursor(cursor);
}
@@ -940,6 +964,15 @@ void WebPluginDelegateImpl::PluginVisibilityChanged() {
}
}
+void WebPluginDelegateImpl::SetImeEnabled(bool enabled) {
+ if (instance()->event_model() != NPEventModelCocoa)
+ return;
+ if (enabled == ime_enabled_)
+ return;
+ ime_enabled_ = enabled;
+ plugin_->SetImeEnabled(enabled);
+}
+
#pragma mark -
#pragma mark Core Animation Support
@@ -948,9 +981,7 @@ void WebPluginDelegateImpl::DrawLayerInSurface() {
if (!windowed_handle())
return;
- surface_->MakeCurrent();
-
- surface_->Clear(window_rect_);
+ surface_->StartDrawing();
[renderer_ beginFrameAtTime:CACurrentMediaTime() timeStamp:NULL];
if (CGRectIsEmpty([renderer_ updateBounds])) {
@@ -963,34 +994,30 @@ void WebPluginDelegateImpl::DrawLayerInSurface() {
[renderer_ render];
[renderer_ endFrame];
- surface_->SwapBuffers();
- plugin_->AcceleratedFrameBuffersDidSwap(windowed_handle());
+ surface_->EndDrawing();
}
-// Update the size of the IOSurface to match the current size of the plug-in,
-// then tell the browser host view so it can adjust its bookkeeping and CALayer
-// appropriately.
+// Update the size of the surface to match the current size of the plug-in.
void WebPluginDelegateImpl::UpdateAcceleratedSurface() {
// Will only have a window handle when using a Core Animation drawing model.
if (!windowed_handle() || !layer_)
return;
+ [CATransaction begin];
+ [CATransaction setValue:[NSNumber numberWithInt:0]
+ forKey:kCATransactionAnimationDuration];
[layer_ setFrame:CGRectMake(0, 0,
window_rect_.width(), window_rect_.height())];
- [renderer_ setBounds:[layer_ bounds]];
+ [CATransaction commit];
- uint64 io_surface_id = surface_->SetSurfaceSize(window_rect_.size());
- if (io_surface_id) {
- plugin_->SetAcceleratedSurface(windowed_handle(),
- window_rect_.width(),
- window_rect_.height(),
- io_surface_id);
- }
+ [renderer_ setBounds:[layer_ bounds]];
+ surface_->SetSize(window_rect_.size());
}
void WebPluginDelegateImpl::set_windowed_handle(
gfx::PluginWindowHandle handle) {
windowed_handle_ = handle;
+ surface_->SetWindowHandle(handle);
UpdateAcceleratedSurface();
// Kick off the drawing timer, if necessary.
PluginVisibilityChanged();
diff --git a/webkit/glue/plugins/webplugin_delegate_impl_win.cc b/webkit/glue/plugins/webplugin_delegate_impl_win.cc
index 9cdc7db..da7a68f 100644
--- a/webkit/glue/plugins/webplugin_delegate_impl_win.cc
+++ b/webkit/glue/plugins/webplugin_delegate_impl_win.cc
@@ -8,18 +8,18 @@
#include <string>
#include <vector>
+#include "app/win/iat_patch_function.h"
#include "base/file_util.h"
-#include "base/iat_patch.h"
#include "base/lazy_instance.h"
#include "base/message_loop.h"
-#include "base/registry.h"
+#include "base/metrics/stats_counters.h"
#include "base/scoped_ptr.h"
-#include "base/stats_counters.h"
#include "base/string_number_conversions.h"
#include "base/string_split.h"
#include "base/string_util.h"
#include "base/stringprintf.h"
-#include "base/win_util.h"
+#include "base/win/registry.h"
+#include "base/win/windows_version.h"
#include "skia/ext/platform_canvas.h"
#include "third_party/WebKit/WebKit/chromium/public/WebInputEvent.h"
#include "webkit/glue/plugins/default_plugin_shared.h"
@@ -70,15 +70,15 @@ base::LazyInstance<std::map<HWND, WNDPROC> > g_window_handle_proc_map(
// Helper object for patching the TrackPopupMenu API.
-base::LazyInstance<iat_patch::IATPatchFunction> g_iat_patch_track_popup_menu(
+base::LazyInstance<app::win::IATPatchFunction> g_iat_patch_track_popup_menu(
base::LINKER_INITIALIZED);
// Helper object for patching the SetCursor API.
-base::LazyInstance<iat_patch::IATPatchFunction> g_iat_patch_set_cursor(
+base::LazyInstance<app::win::IATPatchFunction> g_iat_patch_set_cursor(
base::LINKER_INITIALIZED);
// Helper object for patching the RegEnumKeyExW API.
-base::LazyInstance<iat_patch::IATPatchFunction> g_iat_patch_reg_enum_key_ex_w(
+base::LazyInstance<app::win::IATPatchFunction> g_iat_patch_reg_enum_key_ex_w(
base::LINKER_INITIALIZED);
// http://crbug.com/16114
@@ -289,7 +289,7 @@ WebPluginDelegateImpl::WebPluginDelegateImpl(
} else if (filename == kAcrobatReaderPlugin) {
// Check for the version number above or equal 9.
std::vector<std::wstring> version;
- SplitString(plugin_info.version, L'.', &version);
+ base::SplitString(plugin_info.version, L'.', &version);
if (version.size() > 0) {
int major;
base::StringToInt(version[0], &major);
@@ -415,8 +415,8 @@ bool WebPluginDelegateImpl::PlatformInitialize() {
// name of the current process. We do it in the installer for admin users,
// for the rest patch this function.
if ((quirks_ & PLUGIN_QUIRK_PATCH_REGENUMKEYEXW) &&
- win_util::GetWinVersion() == win_util::WINVERSION_XP &&
- !RegKey().Open(HKEY_LOCAL_MACHINE,
+ base::win::GetVersion() == base::win::VERSION_XP &&
+ !base::win::RegKey().Open(HKEY_LOCAL_MACHINE,
L"SOFTWARE\\Microsoft\\MediaPlayer\\ShimInclusionList\\chrome.exe",
KEY_READ) &&
!g_iat_patch_reg_enum_key_ex_w.Pointer()->is_patched()) {
@@ -1020,6 +1020,8 @@ void WebPluginDelegateImpl::WindowlessPaint(HDC hdc,
damage_rect_win.right = damage_rect_win.left + damage_rect.width();
damage_rect_win.bottom = damage_rect_win.top + damage_rect.height();
+ // Save away the old HDC as this could be a nested invocation.
+ void* old_dc = window_.window;
window_.window = hdc;
NPEvent paint_event;
@@ -1027,9 +1029,10 @@ void WebPluginDelegateImpl::WindowlessPaint(HDC hdc,
// NOTE: NPAPI is not 64bit safe. It puts pointers into 32bit values.
paint_event.wParam = PtrToUlong(hdc);
paint_event.lParam = PtrToUlong(&damage_rect_win);
- static StatsRate plugin_paint("Plugin.Paint");
- StatsScope<StatsRate> scope(plugin_paint);
+ static base::StatsRate plugin_paint("Plugin.Paint");
+ base::StatsScope<base::StatsRate> scope(plugin_paint);
instance()->NPP_HandleEvent(&paint_event);
+ window_.window = old_dc;
}
void WebPluginDelegateImpl::WindowlessSetWindow() {
diff --git a/webkit/glue/plugins/webplugin_impl.cc b/webkit/glue/plugins/webplugin_impl.cc
index 80bc197..704145b 100644
--- a/webkit/glue/plugins/webplugin_impl.cc
+++ b/webkit/glue/plugins/webplugin_impl.cc
@@ -4,6 +4,7 @@
#include "webkit/glue/plugins/webplugin_impl.h"
+#include "base/linked_ptr.h"
#include "base/logging.h"
#include "base/message_loop.h"
#include "base/string_util.h"
@@ -207,6 +208,14 @@ void GetResponseInfo(const WebURLResponse& response,
// WebKit::WebPlugin ----------------------------------------------------------
+struct WebPluginImpl::ClientInfo {
+ unsigned long id;
+ WebPluginResourceClient* client;
+ WebKit::WebURLRequest request;
+ bool pending_failure_notification;
+ linked_ptr<WebKit::WebURLLoader> loader;
+};
+
bool WebPluginImpl::initialize(WebPluginContainer* container) {
if (!page_delegate_)
return false;
diff --git a/webkit/glue/plugins/webplugin_impl.h b/webkit/glue/plugins/webplugin_impl.h
index 5fe96d2..cb0970b 100644
--- a/webkit/glue/plugins/webplugin_impl.h
+++ b/webkit/glue/plugins/webplugin_impl.h
@@ -11,7 +11,6 @@
#include "base/basictypes.h"
#include "base/file_path.h"
-#include "base/linked_ptr.h"
#include "base/task.h"
#include "base/weak_ptr.h"
#include "gfx/native_widget_types.h"
@@ -256,13 +255,7 @@ class WebPluginImpl : public WebPlugin,
// Delayed task for downloading the plugin source URL.
void OnDownloadPluginSrcUrl();
- struct ClientInfo {
- unsigned long id;
- WebPluginResourceClient* client;
- WebKit::WebURLRequest request;
- bool pending_failure_notification;
- linked_ptr<WebKit::WebURLLoader> loader;
- };
+ struct ClientInfo;
// Helper functions
WebPluginResourceClient* GetClientFromLoader(WebKit::WebURLLoader* loader);
diff --git a/webkit/glue/plugins/webplugininfo.cc b/webkit/glue/plugins/webplugininfo.cc
new file mode 100644
index 0000000..7d2b4e4
--- /dev/null
+++ b/webkit/glue/plugins/webplugininfo.cc
@@ -0,0 +1,44 @@
+// Copyright (c) 2010 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "webkit/glue/plugins/webplugininfo.h"
+
+WebPluginMimeType::WebPluginMimeType() {}
+
+WebPluginMimeType::~WebPluginMimeType() {}
+
+WebPluginInfo::WebPluginInfo() : enabled(false) {}
+
+WebPluginInfo::WebPluginInfo(const WebPluginInfo& rhs)
+ : name(rhs.name),
+ path(rhs.path),
+ version(rhs.version),
+ desc(rhs.desc),
+ mime_types(rhs.mime_types),
+ enabled(rhs.enabled) {
+}
+
+WebPluginInfo::~WebPluginInfo() {}
+
+WebPluginInfo& WebPluginInfo::operator=(const WebPluginInfo& rhs) {
+ name = rhs.name;
+ path = rhs.path;
+ version = rhs.version;
+ desc = rhs.desc;
+ mime_types = rhs.mime_types;
+ enabled = rhs.enabled;
+ return *this;
+}
+
+WebPluginInfo::WebPluginInfo(const string16& fake_name,
+ const string16& fake_version,
+ const string16& fake_desc)
+ : name(fake_name),
+ path(),
+ version(fake_version),
+ desc(fake_desc),
+ mime_types(),
+ enabled(true) {
+}
+
diff --git a/webkit/glue/plugins/webplugininfo.h b/webkit/glue/plugins/webplugininfo.h
index 9d2ab6e..34eff3d 100644
--- a/webkit/glue/plugins/webplugininfo.h
+++ b/webkit/glue/plugins/webplugininfo.h
@@ -13,6 +13,9 @@
// Describes a mime type entry for a plugin.
struct WebPluginMimeType {
+ WebPluginMimeType();
+ ~WebPluginMimeType();
+
// The name of the mime type (e.g., "application/x-shockwave-flash").
std::string mime_type;
@@ -25,6 +28,16 @@ struct WebPluginMimeType {
// Describes an available NPAPI plugin.
struct WebPluginInfo {
+ WebPluginInfo();
+ WebPluginInfo(const WebPluginInfo& rhs);
+ ~WebPluginInfo();
+ WebPluginInfo& operator=(const WebPluginInfo& rhs);
+
+ // Special constructor only used during unit testing:
+ WebPluginInfo(const string16& fake_name,
+ const string16& fake_version,
+ const string16& fake_desc);
+
// The name of the plugin (i.e. Flash).
string16 name;
diff --git a/webkit/glue/plugins/webview_plugin.cc b/webkit/glue/plugins/webview_plugin.cc
index 231bd37..feb5720 100644
--- a/webkit/glue/plugins/webview_plugin.cc
+++ b/webkit/glue/plugins/webview_plugin.cc
@@ -4,17 +4,17 @@
#include "webkit/glue/plugins/webview_plugin.h"
-#include "base/histogram.h"
#include "base/message_loop.h"
+#include "base/metrics/histogram.h"
#include "third_party/WebKit/WebKit/chromium/public/WebCursorInfo.h"
#include "third_party/WebKit/WebKit/chromium/public/WebFrame.h"
#include "third_party/WebKit/WebKit/chromium/public/WebPluginContainer.h"
-#include "third_party/WebKit/WebKit/chromium/public/WebSettings.h"
#include "third_party/WebKit/WebKit/chromium/public/WebSize.h"
#include "third_party/WebKit/WebKit/chromium/public/WebURL.h"
#include "third_party/WebKit/WebKit/chromium/public/WebURLRequest.h"
#include "third_party/WebKit/WebKit/chromium/public/WebURLResponse.h"
#include "third_party/WebKit/WebKit/chromium/public/WebView.h"
+#include "webkit/glue/webpreferences.h"
#if WEBKIT_USING_CG
#include <CoreGraphics/CGContext.h>
@@ -48,6 +48,18 @@ WebViewPlugin::WebViewPlugin(WebViewPlugin::Delegate* delegate)
web_view_->initializeMainFrame(this);
}
+// static
+WebViewPlugin* WebViewPlugin::Create(WebViewPlugin::Delegate* delegate,
+ const WebPreferences& preferences,
+ const std::string& html_data,
+ const GURL& url) {
+ WebViewPlugin* plugin = new WebViewPlugin(delegate);
+ WebView* web_view = plugin->web_view();
+ preferences.Apply(web_view);
+ web_view->mainFrame()->loadHTMLString(html_data, url);
+ return plugin;
+}
+
WebViewPlugin::~WebViewPlugin() {
web_view_->close();
}
@@ -78,8 +90,10 @@ bool WebViewPlugin::initialize(WebPluginContainer* container) {
}
void WebViewPlugin::destroy() {
- delegate_->WillDestroyPlugin();
- delegate_ = NULL;
+ if (delegate_) {
+ delegate_->WillDestroyPlugin();
+ delegate_ = NULL;
+ }
container_ = NULL;
MessageLoop::current()->DeleteSoon(FROM_HERE, this);
}
diff --git a/webkit/glue/plugins/webview_plugin.h b/webkit/glue/plugins/webview_plugin.h
index 757a012..9695aa2 100644
--- a/webkit/glue/plugins/webview_plugin.h
+++ b/webkit/glue/plugins/webview_plugin.h
@@ -15,6 +15,8 @@
#include "third_party/WebKit/WebKit/chromium/public/WebURLResponse.h"
#include "third_party/WebKit/WebKit/chromium/public/WebViewClient.h"
+struct WebPreferences;
+
// This class implements the WebPlugin interface by forwarding drawing and
// handling input events to a WebView.
// It can be used as a placeholder for an actual plugin, using HTML for the UI.
@@ -39,6 +41,14 @@ class WebViewPlugin: public WebKit::WebPlugin, public WebKit::WebViewClient,
explicit WebViewPlugin(Delegate* delegate);
+ // Convenience method to set up a new WebViewPlugin using |preferences|
+ // and displaying |html_data|. |url| should be a (fake) chrome:// URL; it is
+ // only used for navigation and never actually resolved.
+ static WebViewPlugin* Create(Delegate* delegate,
+ const WebPreferences& preferences,
+ const std::string& html_data,
+ const GURL& url);
+
WebKit::WebView* web_view() { return web_view_; }
WebKit::WebPluginContainer* container() { return container_; }