diff options
author | raymes@chromium.org <raymes@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98> | 2012-12-06 03:25:24 +0000 |
---|---|---|
committer | raymes@chromium.org <raymes@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98> | 2012-12-06 03:25:24 +0000 |
commit | d146b8bf4a1ed1860452e0ebdeb9c52c135226e2 (patch) | |
tree | 27012d7f0c43fdfe8dacab51ddfdd9861a9fae7c | |
parent | f121ad61e72e32caf56df8732f2eee90343781b1 (diff) | |
download | chromium_src-d146b8bf4a1ed1860452e0ebdeb9c52c135226e2.zip chromium_src-d146b8bf4a1ed1860452e0ebdeb9c52c135226e2.tar.gz chromium_src-d146b8bf4a1ed1860452e0ebdeb9c52c135226e2.tar.bz2 |
Revert 171080
> The refactors PPB_Flash_File_ModuleLocal/FileRef to the new resource model. Calls for both these interfaces are now made directly to the browser. This removes the in-process implementation for these interfaces also (as they are flash-only). Tests are added for PPB_Flash_File_ModuleLocal.
>
> Review URL: https://codereview.chromium.org/11359097
TBR=raymes@chromium.org
Review URL: https://codereview.chromium.org/11437038
git-svn-id: svn://svn.chromium.org/chrome/trunk/src@171389 0039d316-1c4b-4281-b951-d872f2087c98
68 files changed, 1676 insertions, 1270 deletions
diff --git a/chrome/browser/chrome_content_browser_client.cc b/chrome/browser/chrome_content_browser_client.cc index a188c1c..8a2daec 100644 --- a/chrome/browser/chrome_content_browser_client.cc +++ b/chrome/browser/chrome_content_browser_client.cc @@ -1826,6 +1826,11 @@ bool ChromeContentBrowserClient::AllowPepperSocketAPI( return false; } +bool ChromeContentBrowserClient::AllowPepperPrivateFileAPI() { + return CommandLine::ForCurrentProcess()->HasSwitch( + switches::kPpapiFlashInProcess); +} + FilePath ChromeContentBrowserClient::GetHyphenDictionaryDirectory() { FilePath directory; PathService::Get(chrome::DIR_APP_DICTIONARIES, &directory); diff --git a/chrome/browser/chrome_content_browser_client.h b/chrome/browser/chrome_content_browser_client.h index 53a89f3..75ce0ae 100644 --- a/chrome/browser/chrome_content_browser_client.h +++ b/chrome/browser/chrome_content_browser_client.h @@ -213,6 +213,7 @@ class ChromeContentBrowserClient : public content::ContentBrowserClient { content::BrowserContext* browser_context, const GURL& url, const content::SocketPermissionRequest& params) OVERRIDE; + virtual bool AllowPepperPrivateFileAPI() OVERRIDE; virtual FilePath GetHyphenDictionaryDirectory() OVERRIDE; #if defined(OS_POSIX) && !defined(OS_MACOSX) diff --git a/chrome/browser/nacl_host/nacl_process_host.cc b/chrome/browser/nacl_host/nacl_process_host.cc index eef1dac..8c5a86b 100644 --- a/chrome/browser/nacl_host/nacl_process_host.cc +++ b/chrome/browser/nacl_host/nacl_process_host.cc @@ -771,7 +771,6 @@ void NaClProcessHost::OnPpapiChannelCreated( ipc_proxy_channel_.get(), //process_.get(), // sender permissions_, process_->GetData().handle, - process_->GetData().id, ipc_proxy_channel_.get(), chrome_render_message_filter_->GetHostResolver(), chrome_render_message_filter_->render_process_id(), diff --git a/chrome/nacl/nacl_ipc_adapter.cc b/chrome/nacl/nacl_ipc_adapter.cc index d7e7786..2bbaa1f 100644 --- a/chrome/nacl/nacl_ipc_adapter.cc +++ b/chrome/nacl/nacl_ipc_adapter.cc @@ -546,10 +546,6 @@ bool NaClIPCAdapter::OnMessageReceived(const IPC::Message& msg) { base::Passed(&response))); break; } - case ppapi::proxy::SerializedHandle::FILE: - // TODO(raymes): Handle file handles for NaCl. - NOTIMPLEMENTED(); - break; case ppapi::proxy::SerializedHandle::INVALID: { // Nothing to do. TODO(dmichael): Should we log this? Or is it // sometimes okay to pass an INVALID handle? diff --git a/chrome/test/ppapi/ppapi_browsertest.cc b/chrome/test/ppapi/ppapi_browsertest.cc index 964d0e7..293bd32 100644 --- a/chrome/test/ppapi/ppapi_browsertest.cc +++ b/chrome/test/ppapi/ppapi_browsertest.cc @@ -659,6 +659,8 @@ TEST_PPAPI_OUT_OF_PROCESS(Flash_SetInstanceAlwaysOnTop) TEST_PPAPI_OUT_OF_PROCESS(Flash_GetLocalTimeZoneOffset) TEST_PPAPI_OUT_OF_PROCESS(Flash_GetCommandLineArgs) TEST_PPAPI_OUT_OF_PROCESS(Flash_GetSetting) +// No in-process test for SetCrashData. +TEST_PPAPI_OUT_OF_PROCESS(Flash_SetCrashData) // NaCl based PPAPI tests with WebSocket server TEST_PPAPI_IN_PROCESS(WebSocket_IsWebSocket) @@ -884,9 +886,8 @@ TEST_PPAPI_OUT_OF_PROCESS(MessageLoop_Post) // Going forward, Flash APIs will only work out-of-process. TEST_PPAPI_OUT_OF_PROCESS(Flash_GetProxyForURL) -TEST_PPAPI_OUT_OF_PROCESS(Flash_SetCrashData) TEST_PPAPI_OUT_OF_PROCESS(FlashClipboard) -TEST_PPAPI_OUT_OF_PROCESS(FlashFile) +TEST_PPAPI_OUT_OF_PROCESS(FlashFile_CreateTemporaryFile) // Mac/Aura reach NOTIMPLEMENTED/time out. // mac: http://crbug.com/96767 // aura: http://crbug.com/104384 diff --git a/content/browser/plugin_data_remover_impl.cc b/content/browser/plugin_data_remover_impl.cc index 9c11458..679b9ac 100644 --- a/content/browser/plugin_data_remover_impl.cc +++ b/content/browser/plugin_data_remover_impl.cc @@ -14,7 +14,7 @@ #include "base/version.h" #include "content/browser/plugin_process_host.h" #include "content/browser/plugin_service_impl.h" -#include "content/browser/renderer_host/pepper/pepper_flash_file_host.h" +#include "content/browser/renderer_host/pepper/pepper_file_message_filter.h" #include "content/common/child_process_host_impl.h" #include "content/common/plugin_messages.h" #include "content/public/browser/browser_context.h" @@ -208,7 +208,7 @@ class PluginDataRemoverImpl::Context #if defined(ENABLE_PLUGINS) IPC::Message* CreatePpapiClearSiteDataMsg(uint64 max_age) { FilePath profile_path = - PepperFlashFileHost::GetDataDirName(browser_context_path_); + PepperFileMessageFilter::GetDataDirName(browser_context_path_); // TODO(vtl): This "duplicates" logic in webkit/plugins/ppapi/file_path.cc // (which prepends the plugin name to the relative part of the path // instead, with the absolute, profile-dependent part being enforced by diff --git a/content/browser/ppapi_plugin_process_host.cc b/content/browser/ppapi_plugin_process_host.cc index 4d0213b..655c513 100644 --- a/content/browser/ppapi_plugin_process_host.cc +++ b/content/browser/ppapi_plugin_process_host.cc @@ -172,10 +172,13 @@ PpapiPluginProcessHost::PpapiPluginProcessHost( permissions_, host_resolver); - host_impl_.reset(new BrowserPpapiHostImpl(this, permissions_, info.name, - profile_data_directory, process_->GetData().id)); + host_impl_.reset(new BrowserPpapiHostImpl(this, permissions_)); + + file_filter_ = new PepperTrustedFileMessageFilter( + process_->GetData().id, info.name, profile_data_directory); process_->GetHost()->AddFilter(filter_.get()); + process_->GetHost()->AddFilter(file_filter_.get()); process_->GetHost()->AddFilter(host_impl_->message_filter()); GetContentClient()->browser()->DidCreatePpapiPlugin(host_impl_.get()); @@ -187,12 +190,7 @@ PpapiPluginProcessHost::PpapiPluginProcessHost() PROCESS_TYPE_PPAPI_BROKER, this)); ppapi::PpapiPermissions permissions; // No permissions. - // The plugin name and profile data directory shouldn't be needed for the - // broker. - std::string plugin_name; - FilePath profile_data_directory; - host_impl_.reset(new BrowserPpapiHostImpl(this, permissions, plugin_name, - profile_data_directory, process_->GetData().id)); + host_impl_.reset(new BrowserPpapiHostImpl(this, permissions)); } bool PpapiPluginProcessHost::Init(const PepperPluginInfo& info) { diff --git a/content/browser/ppapi_plugin_process_host.h b/content/browser/ppapi_plugin_process_host.h index 9dc3481..cbab68c 100644 --- a/content/browser/ppapi_plugin_process_host.h +++ b/content/browser/ppapi_plugin_process_host.h @@ -13,6 +13,7 @@ #include "base/memory/ref_counted.h" #include "base/memory/scoped_ptr.h" #include "content/browser/renderer_host/pepper/browser_ppapi_host_impl.h" +#include "content/browser/renderer_host/pepper/pepper_file_message_filter.h" #include "content/browser/renderer_host/pepper/pepper_message_filter.h" #include "content/public/browser/browser_child_process_host_delegate.h" #include "content/public/browser/browser_child_process_host_iterator.h" @@ -139,6 +140,9 @@ class PpapiPluginProcessHost : public BrowserChildProcessHostDelegate, ppapi::PpapiPermissions permissions_; scoped_ptr<BrowserPpapiHostImpl> host_impl_; + // Handles filesystem requests from flash plugins. May be NULL. + scoped_refptr<PepperFileMessageFilter> file_filter_; + // Observes network changes. May be NULL. scoped_ptr<PluginNetworkObserver> network_observer_; diff --git a/content/browser/renderer_host/pepper/browser_ppapi_host_impl.cc b/content/browser/renderer_host/pepper/browser_ppapi_host_impl.cc index d7faf83..3e074c4 100644 --- a/content/browser/renderer_host/pepper/browser_ppapi_host_impl.cc +++ b/content/browser/renderer_host/pepper/browser_ppapi_host_impl.cc @@ -3,8 +3,8 @@ // found in the LICENSE file. #include "content/browser/renderer_host/pepper/browser_ppapi_host_impl.h" - #include "content/browser/renderer_host/pepper/pepper_message_filter.h" + #include "content/public/browser/browser_thread.h" #include "content/public/browser/render_view_host.h" #include "ipc/ipc_message_macros.h" @@ -16,19 +16,12 @@ BrowserPpapiHost* BrowserPpapiHost::CreateExternalPluginProcess( IPC::Sender* sender, ppapi::PpapiPermissions permissions, base::ProcessHandle plugin_child_process, - int plugin_child_process_id, IPC::ChannelProxy* channel, net::HostResolver* host_resolver, int render_process_id, int render_view_id) { - // TODO(raymes): Figure out how to plumb plugin_name and - // profile_data_directory through for NaCl. They are currently only needed for - // PPB_Flash_File interfaces so it doesn't matter. - std::string plugin_name; - FilePath profile_data_directory; BrowserPpapiHostImpl* browser_ppapi_host = - new BrowserPpapiHostImpl(sender, permissions, plugin_name, - profile_data_directory, plugin_child_process_id); + new BrowserPpapiHostImpl(sender, permissions); browser_ppapi_host->set_plugin_process_handle(plugin_child_process); channel->AddFilter( @@ -44,15 +37,9 @@ BrowserPpapiHost* BrowserPpapiHost::CreateExternalPluginProcess( BrowserPpapiHostImpl::BrowserPpapiHostImpl( IPC::Sender* sender, - const ppapi::PpapiPermissions& permissions, - const std::string& plugin_name, - const FilePath& profile_data_directory, - int plugin_process_id) + const ppapi::PpapiPermissions& permissions) : ppapi_host_(sender, permissions), - plugin_process_handle_(base::kNullProcessHandle), - plugin_name_(plugin_name), - profile_data_directory_(profile_data_directory), - plugin_process_id_(plugin_process_id) { + plugin_process_handle_(base::kNullProcessHandle) { message_filter_ = new HostMessageFilter(&ppapi_host_); ppapi_host_.AddHostFactoryFilter(scoped_ptr<ppapi::host::HostFactory>( new ContentBrowserPepperHostFactory(this))); @@ -93,18 +80,6 @@ bool BrowserPpapiHostImpl::GetRenderViewIDsForInstance( return true; } -const std::string& BrowserPpapiHostImpl::GetPluginName() { - return plugin_name_; -} - -const FilePath& BrowserPpapiHostImpl::GetProfileDataDirectory() { - return profile_data_directory_; -} - -int BrowserPpapiHostImpl::GetPluginProcessID() { - return plugin_process_id_; -} - void BrowserPpapiHostImpl::AddInstanceForView(PP_Instance instance, int render_process_id, int render_view_id) { diff --git a/content/browser/renderer_host/pepper/browser_ppapi_host_impl.h b/content/browser/renderer_host/pepper/browser_ppapi_host_impl.h index 77eb8a8..bee35a6 100644 --- a/content/browser/renderer_host/pepper/browser_ppapi_host_impl.h +++ b/content/browser/renderer_host/pepper/browser_ppapi_host_impl.h @@ -6,11 +6,9 @@ #define CONTENT_BROWSER_RENDERER_HOST_PEPPER_BROWSER_PPAPI_HOST_IMPL_H_ #include <map> -#include <string> #include "base/basictypes.h" #include "base/compiler_specific.h" -#include "base/file_path.h" #include "content/browser/renderer_host/pepper/content_browser_pepper_host_factory.h" #include "content/common/content_export.h" #include "content/public/browser/browser_ppapi_host.h" @@ -25,10 +23,7 @@ class CONTENT_EXPORT BrowserPpapiHostImpl : public BrowserPpapiHost { // as it is known (we start the process asynchronously so it won't be known // when this object is created). BrowserPpapiHostImpl(IPC::Sender* sender, - const ppapi::PpapiPermissions& permissions, - const std::string& plugin_name, - const FilePath& profile_data_directory, - int plugin_process_id); + const ppapi::PpapiPermissions& permissions); virtual ~BrowserPpapiHostImpl(); // BrowserPpapiHost. @@ -38,9 +33,6 @@ class CONTENT_EXPORT BrowserPpapiHostImpl : public BrowserPpapiHost { virtual bool GetRenderViewIDsForInstance(PP_Instance instance, int* render_process_id, int* render_view_id) const OVERRIDE; - virtual const std::string& GetPluginName() OVERRIDE; - virtual const FilePath& GetProfileDataDirectory() OVERRIDE; - virtual int GetPluginProcessID() OVERRIDE; void set_plugin_process_handle(base::ProcessHandle handle) { plugin_process_handle_ = handle; @@ -87,9 +79,6 @@ class CONTENT_EXPORT BrowserPpapiHostImpl : public BrowserPpapiHost { ppapi::host::PpapiHost ppapi_host_; base::ProcessHandle plugin_process_handle_; - std::string plugin_name_; - FilePath profile_data_directory_; - int plugin_process_id_; // Tracks all PP_Instances in this plugin and maps them to // RenderProcess/RenderView IDs. diff --git a/content/browser/renderer_host/pepper/browser_ppapi_host_test.cc b/content/browser/renderer_host/pepper/browser_ppapi_host_test.cc index a85f086..941782c 100644 --- a/content/browser/renderer_host/pepper/browser_ppapi_host_test.cc +++ b/content/browser/renderer_host/pepper/browser_ppapi_host_test.cc @@ -13,10 +13,7 @@ BrowserPpapiHostTest::BrowserPpapiHostTest() : sink_() { ppapi_host_.reset(new BrowserPpapiHostImpl( &sink_, - ppapi::PpapiPermissions::AllPermissions(), - std::string(), - FilePath(), - 0)); + ppapi::PpapiPermissions::AllPermissions())); ppapi_host_->set_plugin_process_handle(base::GetCurrentProcessHandle()); } diff --git a/content/browser/renderer_host/pepper/content_browser_pepper_host_factory.cc b/content/browser/renderer_host/pepper/content_browser_pepper_host_factory.cc index fd9a13a..3033adb 100644 --- a/content/browser/renderer_host/pepper/content_browser_pepper_host_factory.cc +++ b/content/browser/renderer_host/pepper/content_browser_pepper_host_factory.cc @@ -6,7 +6,6 @@ #include "content/browser/renderer_host/pepper/browser_ppapi_host_impl.h" #include "content/browser/renderer_host/pepper/pepper_flash_browser_host.h" -#include "content/browser/renderer_host/pepper/pepper_flash_file_host.h" #include "content/browser/renderer_host/pepper/pepper_gamepad_host.h" #include "content/browser/renderer_host/pepper/pepper_print_settings_manager.h" #include "content/browser/renderer_host/pepper/pepper_printing_host.h" @@ -63,9 +62,6 @@ scoped_ptr<ResourceHost> ContentBrowserPepperHostFactory::CreateResourceHost( case PpapiHostMsg_Flash_Create::ID: return scoped_ptr<ResourceHost>(new PepperFlashBrowserHost( host_, instance, params.pp_resource())); - case PpapiHostMsg_FlashFile_Create::ID: - return scoped_ptr<ResourceHost>(new PepperFlashFileHost( - host_, instance, params.pp_resource())); } } diff --git a/content/browser/renderer_host/pepper/pepper_file_message_filter.cc b/content/browser/renderer_host/pepper/pepper_file_message_filter.cc new file mode 100644 index 0000000..428c6ed --- /dev/null +++ b/content/browser/renderer_host/pepper/pepper_file_message_filter.cc @@ -0,0 +1,367 @@ +// Copyright (c) 2012 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 "content/browser/renderer_host/pepper/pepper_file_message_filter.h" + +#include "base/callback.h" +#include "base/file_path.h" +#include "base/file_util.h" +#include "base/logging.h" +#include "base/platform_file.h" +#include "base/process_util.h" +#include "base/threading/sequenced_worker_pool.h" +#include "content/browser/child_process_security_policy_impl.h" +#include "content/browser/renderer_host/render_process_host_impl.h" +#include "content/public/browser/browser_thread.h" +#include "content/public/common/content_constants.h" +#include "ipc/ipc_platform_file.h" +#include "ppapi/proxy/pepper_file_messages.h" +#include "ppapi/shared_impl/file_path.h" + +#if defined(OS_POSIX) +#include "base/file_descriptor_posix.h" +#endif + +namespace content { +namespace { + +// Used to check if the renderer has permission for the requested operation. +// TODO(viettrungluu): Verify these. They don't necessarily quite make sense, +// but it seems to be approximately what the file system code does. +const int kReadPermissions = base::PLATFORM_FILE_OPEN | + base::PLATFORM_FILE_READ | + base::PLATFORM_FILE_EXCLUSIVE_READ; +const int kWritePermissions = base::PLATFORM_FILE_OPEN | + base::PLATFORM_FILE_CREATE | + base::PLATFORM_FILE_CREATE_ALWAYS | + base::PLATFORM_FILE_OPEN_TRUNCATED | + base::PLATFORM_FILE_WRITE | + base::PLATFORM_FILE_EXCLUSIVE_WRITE | + base::PLATFORM_FILE_WRITE_ATTRIBUTES; + +IPC::PlatformFileForTransit PlatformFileToPlatformFileForTransit( + base::ProcessHandle peer_handle, + base::PlatformFile file_handle, + base::PlatformFileError* error) { + IPC::PlatformFileForTransit file; +#if defined(OS_WIN) + // Duplicate the file handle so that the renderer process can access the file. + if (!DuplicateHandle(GetCurrentProcess(), file_handle, + peer_handle, &file, 0, false, + DUPLICATE_CLOSE_SOURCE | DUPLICATE_SAME_ACCESS)) { + // file_handle is closed whether or not DuplicateHandle succeeds. + *error = base::PLATFORM_FILE_ERROR_ACCESS_DENIED; + file = INVALID_HANDLE_VALUE; + } +#else + file = base::FileDescriptor(file_handle, true); +#endif + return file; +} + +} // namespace + +PepperFileMessageFilter::PepperFileMessageFilter(int child_id) + : child_id_(child_id), + channel_(NULL) { +} + +base::TaskRunner* PepperFileMessageFilter::OverrideTaskRunnerForMessage( + const IPC::Message& message) { + // The blocking pool provides a pool of threads to run file + // operations, instead of a single thread which might require + // queuing time. Since these messages are synchronous as sent from + // the plugin, the sending thread cannot send a new message until + // this one returns, so there is no need to sequence tasks here. If + // the plugin has multiple threads, it cannot make assumptions about + // ordering of IPC message sends, so it cannot make assumptions + // about ordering of operations caused by those IPC messages. + if (IPC_MESSAGE_CLASS(message) == PepperFileMsgStart) + return BrowserThread::GetBlockingPool(); + return NULL; +} + +bool PepperFileMessageFilter::OnMessageReceived(const IPC::Message& message, + bool* message_was_ok) { + bool handled = true; + IPC_BEGIN_MESSAGE_MAP_EX(PepperFileMessageFilter, message, *message_was_ok) + IPC_MESSAGE_HANDLER(PepperFileMsg_OpenFile, OnOpenFile) + IPC_MESSAGE_HANDLER(PepperFileMsg_RenameFile, OnRenameFile) + IPC_MESSAGE_HANDLER(PepperFileMsg_DeleteFileOrDir, OnDeleteFileOrDir) + IPC_MESSAGE_HANDLER(PepperFileMsg_CreateDir, OnCreateDir) + IPC_MESSAGE_HANDLER(PepperFileMsg_QueryFile, OnQueryFile) + IPC_MESSAGE_HANDLER(PepperFileMsg_GetDirContents, OnGetDirContents) + IPC_MESSAGE_HANDLER(PepperFileMsg_CreateTemporaryFile, + OnCreateTemporaryFile) + IPC_MESSAGE_UNHANDLED(handled = false) + IPC_END_MESSAGE_MAP_EX() + return handled; +} + +void PepperFileMessageFilter::OnDestruct() const { + BrowserThread::DeleteOnIOThread::Destruct(this); +} + +// static +FilePath PepperFileMessageFilter::GetDataDirName(const FilePath& profile_path) { + return profile_path.Append(kPepperDataDirname); +} + +PepperFileMessageFilter::~PepperFileMessageFilter() { + // This function should be called on the IO thread. + DCHECK(BrowserThread::CurrentlyOn(BrowserThread::IO)); +} + +// Called on the FILE thread: +void PepperFileMessageFilter::OnOpenFile( + const ppapi::PepperFilePath& path, + int flags, + base::PlatformFileError* error, + IPC::PlatformFileForTransit* file) { + FilePath full_path = ValidateAndConvertPepperFilePath(path, flags); + if (full_path.empty()) { + *error = base::PLATFORM_FILE_ERROR_ACCESS_DENIED; + *file = IPC::InvalidPlatformFileForTransit(); + return; + } + + base::PlatformFile file_handle = base::CreatePlatformFile( + full_path, flags, NULL, error); + + if (*error != base::PLATFORM_FILE_OK || + file_handle == base::kInvalidPlatformFileValue) { + *file = IPC::InvalidPlatformFileForTransit(); + return; + } + + // Make sure we didn't try to open a directory: directory fd shouldn't pass + // to untrusted processes because they open security holes. + base::PlatformFileInfo info; + if (!base::GetPlatformFileInfo(file_handle, &info) || info.is_directory) { + // When in doubt, throw it out. + *error = base::PLATFORM_FILE_ERROR_ACCESS_DENIED; + *file = IPC::InvalidPlatformFileForTransit(); + return; + } + + *file = PlatformFileToPlatformFileForTransit(peer_handle(), file_handle, + error); +} + +void PepperFileMessageFilter::OnRenameFile( + const ppapi::PepperFilePath& from_path, + const ppapi::PepperFilePath& to_path, + base::PlatformFileError* error) { + FilePath from_full_path = ValidateAndConvertPepperFilePath(from_path, + kWritePermissions); + FilePath to_full_path = ValidateAndConvertPepperFilePath(to_path, + kWritePermissions); + if (from_full_path.empty() || to_full_path.empty()) { + *error = base::PLATFORM_FILE_ERROR_ACCESS_DENIED; + return; + } + + bool result = file_util::Move(from_full_path, to_full_path); + *error = result ? base::PLATFORM_FILE_OK + : base::PLATFORM_FILE_ERROR_ACCESS_DENIED; +} + +void PepperFileMessageFilter::OnDeleteFileOrDir( + const ppapi::PepperFilePath& path, + bool recursive, + base::PlatformFileError* error) { + FilePath full_path = ValidateAndConvertPepperFilePath(path, + kWritePermissions); + if (full_path.empty()) { + *error = base::PLATFORM_FILE_ERROR_ACCESS_DENIED; + return; + } + + bool result = file_util::Delete(full_path, recursive); + *error = result ? base::PLATFORM_FILE_OK + : base::PLATFORM_FILE_ERROR_ACCESS_DENIED; +} + +void PepperFileMessageFilter::OnCreateDir( + const ppapi::PepperFilePath& path, + base::PlatformFileError* error) { + FilePath full_path = ValidateAndConvertPepperFilePath(path, + kWritePermissions); + if (full_path.empty()) { + *error = base::PLATFORM_FILE_ERROR_ACCESS_DENIED; + return; + } + + bool result = file_util::CreateDirectory(full_path); + *error = result ? base::PLATFORM_FILE_OK + : base::PLATFORM_FILE_ERROR_ACCESS_DENIED; +} + +void PepperFileMessageFilter::OnQueryFile( + const ppapi::PepperFilePath& path, + base::PlatformFileInfo* info, + base::PlatformFileError* error) { + FilePath full_path = ValidateAndConvertPepperFilePath(path, kReadPermissions); + if (full_path.empty()) { + *error = base::PLATFORM_FILE_ERROR_ACCESS_DENIED; + return; + } + + bool result = file_util::GetFileInfo(full_path, info); + *error = result ? base::PLATFORM_FILE_OK + : base::PLATFORM_FILE_ERROR_ACCESS_DENIED; +} + +void PepperFileMessageFilter::OnGetDirContents( + const ppapi::PepperFilePath& path, + ppapi::DirContents* contents, + base::PlatformFileError* error) { + FilePath full_path = ValidateAndConvertPepperFilePath(path, kReadPermissions); + if (full_path.empty()) { + *error = base::PLATFORM_FILE_ERROR_ACCESS_DENIED; + return; + } + + contents->clear(); + + file_util::FileEnumerator enumerator(full_path, false, + file_util::FileEnumerator::FILES | + file_util::FileEnumerator::DIRECTORIES | + file_util::FileEnumerator::INCLUDE_DOT_DOT); + + while (!enumerator.Next().empty()) { + file_util::FileEnumerator::FindInfo info; + enumerator.GetFindInfo(&info); + ppapi::DirEntry entry = { + file_util::FileEnumerator::GetFilename(info), + file_util::FileEnumerator::IsDirectory(info) + }; + contents->push_back(entry); + } + + *error = base::PLATFORM_FILE_OK; +} + +void PepperFileMessageFilter::OnCreateTemporaryFile( + base::PlatformFileError* error, + IPC::PlatformFileForTransit* file) { + *error = base::PLATFORM_FILE_ERROR_FAILED; + *file = IPC::InvalidPlatformFileForTransit(); + + ppapi::PepperFilePath dir_path( + ppapi::PepperFilePath::DOMAIN_MODULE_LOCAL, FilePath()); + FilePath validated_dir_path = ValidateAndConvertPepperFilePath( + dir_path, kReadPermissions | kWritePermissions); + if (validated_dir_path.empty() || + (!file_util::DirectoryExists(validated_dir_path) && + !file_util::CreateDirectory(validated_dir_path))) { + *error = base::PLATFORM_FILE_ERROR_ACCESS_DENIED; + return; + } + + FilePath file_path; + if (!file_util::CreateTemporaryFileInDir(validated_dir_path, &file_path)) + return; + + base::PlatformFile file_handle = base::CreatePlatformFile( + file_path, + base::PLATFORM_FILE_CREATE_ALWAYS | base::PLATFORM_FILE_READ | + base::PLATFORM_FILE_WRITE | base::PLATFORM_FILE_TEMPORARY | + base::PLATFORM_FILE_DELETE_ON_CLOSE, + NULL, error); + + if (*error != base::PLATFORM_FILE_OK) { + DCHECK_EQ(file_handle, base::kInvalidPlatformFileValue); + return; + } + + *file = PlatformFileToPlatformFileForTransit(peer_handle(), file_handle, + error); +} + +FilePath PepperFileMessageFilter::ValidateAndConvertPepperFilePath( + const ppapi::PepperFilePath& pepper_path, int flags) { + FilePath file_path; // Empty path returned on error. + if (pepper_path.domain() == ppapi::PepperFilePath::DOMAIN_ABSOLUTE) { + if (pepper_path.path().IsAbsolute() && + ChildProcessSecurityPolicyImpl::GetInstance()->HasPermissionsForFile( + child_id(), pepper_path.path(), flags)) + file_path = pepper_path.path(); + } + return file_path; +} + +PepperTrustedFileMessageFilter::PepperTrustedFileMessageFilter( + int child_id, + const std::string& plugin_name, + const FilePath& profile_data_directory) + : PepperFileMessageFilter(child_id) { + plugin_data_directory_ = GetDataDirName(profile_data_directory).Append( + FilePath::FromUTF8Unsafe(plugin_name)); +} + +PepperTrustedFileMessageFilter::~PepperTrustedFileMessageFilter() { +} + +FilePath PepperTrustedFileMessageFilter::ValidateAndConvertPepperFilePath( + const ppapi::PepperFilePath& pepper_path, + int flags) { + FilePath file_path; // Empty path returned on error. + switch (pepper_path.domain()) { + case ppapi::PepperFilePath::DOMAIN_ABSOLUTE: + if (pepper_path.path().IsAbsolute() && + ChildProcessSecurityPolicyImpl::GetInstance()->HasPermissionsForFile( + child_id(), pepper_path.path(), flags)) + file_path = pepper_path.path(); + break; + case ppapi::PepperFilePath::DOMAIN_MODULE_LOCAL: + // This filter provides the module name portion of the path to prevent + // plugins from accessing each other's data. + if (!pepper_path.path().IsAbsolute() && + !pepper_path.path().ReferencesParent()) + file_path = plugin_data_directory_.Append(pepper_path.path()); + break; + default: + NOTREACHED(); + break; + } + return file_path; +} + +PepperUnsafeFileMessageFilter::PepperUnsafeFileMessageFilter( + int child_id, + const FilePath& profile_data_directory) + : PepperFileMessageFilter(child_id) { + profile_data_directory_ = GetDataDirName(profile_data_directory); +} + +PepperUnsafeFileMessageFilter::~PepperUnsafeFileMessageFilter() { +} + +FilePath PepperUnsafeFileMessageFilter::ValidateAndConvertPepperFilePath( + const ppapi::PepperFilePath& pepper_path, + int flags) { + FilePath file_path; // Empty path returned on error. + switch (pepper_path.domain()) { + case ppapi::PepperFilePath::DOMAIN_ABSOLUTE: + if (pepper_path.path().IsAbsolute() && + ChildProcessSecurityPolicyImpl::GetInstance()->HasPermissionsForFile( + child_id(), pepper_path.path(), flags)) + file_path = pepper_path.path(); + break; + case ppapi::PepperFilePath::DOMAIN_MODULE_LOCAL: + // The message supplies the module portion of the path (so it can't + // really be trusted). + if (!pepper_path.path().IsAbsolute() && + !pepper_path.path().ReferencesParent()) + file_path = profile_data_directory_.Append(pepper_path.path()); + break; + default: + NOTREACHED(); + break; + } + return file_path; +} + +} // namespace content diff --git a/content/browser/renderer_host/pepper/pepper_file_message_filter.h b/content/browser/renderer_host/pepper/pepper_file_message_filter.h new file mode 100644 index 0000000..7efca84 --- /dev/null +++ b/content/browser/renderer_host/pepper/pepper_file_message_filter.h @@ -0,0 +1,138 @@ +// Copyright (c) 2012 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 CONTENT_BROWSER_RENDERER_HOST_PEPPER_PEPPER_FILE_MESSAGE_FILTER_H_ +#define CONTENT_BROWSER_RENDERER_HOST_PEPPER_PEPPER_FILE_MESSAGE_FILTER_H_ + +#include <string> +#include <vector> + +#include "base/file_path.h" +#include "base/memory/ref_counted.h" +#include "base/process.h" +#include "base/sequenced_task_runner_helpers.h" +#include "build/build_config.h" +#include "content/public/browser/browser_message_filter.h" +#include "ipc/ipc_platform_file.h" +#include "ppapi/shared_impl/dir_contents.h" + +namespace ppapi { +class PepperFilePath; +} + +namespace content { +class BrowserContext; + +// A message filter for Pepper-specific File I/O messages. Used on +// renderer channels, this denys the renderer the trusted operations +// permitted only by plugin processes. +class PepperFileMessageFilter : public BrowserMessageFilter { + public: + explicit PepperFileMessageFilter(int child_id); + + // BrowserMessageFilter methods: + virtual base::TaskRunner* OverrideTaskRunnerForMessage( + const IPC::Message& message) OVERRIDE; + virtual bool OnMessageReceived(const IPC::Message& message, + bool* message_was_ok) OVERRIDE; + virtual void OnDestruct() const OVERRIDE; + + int child_id() const { return child_id_; } + + // Returns the name of the pepper data directory that we'll use for local + // storage. The argument is the profile path so that this can be used on any + // thread independent of the profile context. + static FilePath GetDataDirName(const FilePath& profile_path); + + protected: + virtual ~PepperFileMessageFilter(); + + private: + friend class BrowserThread; + friend class base::DeleteHelper<PepperFileMessageFilter>; + + // Called on the FILE thread: + void OnOpenFile(const ppapi::PepperFilePath& path, + int flags, + base::PlatformFileError* error, + IPC::PlatformFileForTransit* file); + void OnRenameFile(const ppapi::PepperFilePath& from_path, + const ppapi::PepperFilePath& to_path, + base::PlatformFileError* error); + void OnDeleteFileOrDir(const ppapi::PepperFilePath& path, + bool recursive, + base::PlatformFileError* error); + void OnCreateDir(const ppapi::PepperFilePath& path, + base::PlatformFileError* error); + void OnQueryFile(const ppapi::PepperFilePath& path, + base::PlatformFileInfo* info, + base::PlatformFileError* error); + void OnGetDirContents(const ppapi::PepperFilePath& path, + ppapi::DirContents* contents, + base::PlatformFileError* error); + void OnCreateTemporaryFile(base::PlatformFileError* error, + IPC::PlatformFileForTransit* file); + + // Validate and convert the Pepper file path to a "real" |FilePath|. Returns + // an empty |FilePath| on error. + virtual FilePath ValidateAndConvertPepperFilePath( + const ppapi::PepperFilePath& pepper_path, int flags); + + // The ID of the child process. + const int child_id_; + + // The channel associated with the renderer connection. This pointer is not + // owned by this class. + IPC::Channel* channel_; + + DISALLOW_COPY_AND_ASSIGN(PepperFileMessageFilter); +}; + +// Message filter used with out-of-process pepper flash plugin channels that +// provides the trusted operations permitted only by plugin processes. +class PepperTrustedFileMessageFilter : public PepperFileMessageFilter { + public: + PepperTrustedFileMessageFilter(int child_id, + const std::string& plugin_name, + const FilePath& profile_data_directory); + + protected: + virtual ~PepperTrustedFileMessageFilter(); + + private: + virtual FilePath ValidateAndConvertPepperFilePath( + const ppapi::PepperFilePath& pepper_path, int flags) OVERRIDE; + + // The path to the per-plugin directory under the per-profile data directory + // (includes module name). + FilePath plugin_data_directory_; + + DISALLOW_COPY_AND_ASSIGN(PepperTrustedFileMessageFilter); +}; + +// Message filter used with in-process pepper flash plugins that provides the +// renderer channels with the trusted operations permitted only by plugin +// process. This should not be used as part of normal operations, and may +// only be applied under the control of a command-line flag. +class PepperUnsafeFileMessageFilter : public PepperFileMessageFilter { + public: + PepperUnsafeFileMessageFilter(int child_id, + const FilePath& profile_data_directory); + + protected: + virtual ~PepperUnsafeFileMessageFilter(); + + private: + virtual FilePath ValidateAndConvertPepperFilePath( + const ppapi::PepperFilePath& pepper_path, int flags) OVERRIDE; + + // The per-profile data directory (not including module name). + FilePath profile_data_directory_; + + DISALLOW_COPY_AND_ASSIGN(PepperUnsafeFileMessageFilter); +}; + +} // namespace content + +#endif // CONTENT_BROWSER_RENDERER_HOST_PEPPER_PEPPER_FILE_MESSAGE_FILTER_H_ diff --git a/content/browser/renderer_host/pepper/pepper_flash_file_host.cc b/content/browser/renderer_host/pepper/pepper_flash_file_host.cc deleted file mode 100644 index 4bd23cd..0000000 --- a/content/browser/renderer_host/pepper/pepper_flash_file_host.cc +++ /dev/null @@ -1,365 +0,0 @@ -// Copyright (c) 2012 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 "content/browser/renderer_host/pepper/pepper_flash_file_host.h" - -#include "base/bind.h" -#include "base/file_util.h" -#include "base/task_runner.h" -#include "base/threading/sequenced_worker_pool.h" -#include "content/browser/child_process_security_policy_impl.h" -#include "content/public/browser/browser_ppapi_host.h" -#include "content/public/browser/browser_thread.h" -#include "content/public/common/content_constants.h" -#include "ipc/ipc_platform_file.h" -#include "ppapi/c/pp_errors.h" -#include "ppapi/host/dispatch_host_message.h" -#include "ppapi/host/host_message_context.h" -#include "ppapi/host/ppapi_host.h" -#include "ppapi/proxy/ppapi_messages.h" -#include "ppapi/shared_impl/file_path.h" -#include "ppapi/shared_impl/file_type_conversion.h" - -namespace content { - -namespace { -// Used to check if the renderer has permission for the requested operation. -// TODO(viettrungluu): Verify these. They don't necessarily quite make sense, -// but it seems to be approximately what the file system code does. -const int kReadPermissions = base::PLATFORM_FILE_OPEN | - base::PLATFORM_FILE_READ | - base::PLATFORM_FILE_EXCLUSIVE_READ; -const int kWritePermissions = base::PLATFORM_FILE_OPEN | - base::PLATFORM_FILE_CREATE | - base::PLATFORM_FILE_CREATE_ALWAYS | - base::PLATFORM_FILE_OPEN_TRUNCATED | - base::PLATFORM_FILE_WRITE | - base::PLATFORM_FILE_EXCLUSIVE_WRITE | - base::PLATFORM_FILE_WRITE_ATTRIBUTES; - -// All file messages are handled by BrowserThread's blocking pool. -class FileMessageFilter : public ppapi::host::ResourceMessageFilter { - public: - FileMessageFilter(const std::string& plugin_name, - const FilePath& profile_data_directory, - int plugin_process_id, - base::ProcessHandle plugin_process_handle); - protected: - // ppapi::host::ResourceMessageFilter implementation. - virtual scoped_refptr<base::TaskRunner> OverrideTaskRunnerForMessage( - const IPC::Message& msg) OVERRIDE; - virtual int32_t OnResourceMessageReceived( - const IPC::Message& msg, - ppapi::host::HostMessageContext* context) OVERRIDE; - - private: - virtual ~FileMessageFilter(); - - int32_t OnOpenFile(ppapi::host::HostMessageContext* context, - const ppapi::PepperFilePath& path, - int flags); - int32_t OnRenameFile(ppapi::host::HostMessageContext* context, - const ppapi::PepperFilePath& from_path, - const ppapi::PepperFilePath& to_path); - int32_t OnDeleteFileOrDir(ppapi::host::HostMessageContext* context, - const ppapi::PepperFilePath& path, - bool recursive); - int32_t OnCreateDir(ppapi::host::HostMessageContext* context, - const ppapi::PepperFilePath& path); - int32_t OnQueryFile(ppapi::host::HostMessageContext* context, - const ppapi::PepperFilePath& path); - int32_t OnGetDirContents(ppapi::host::HostMessageContext* context, - const ppapi::PepperFilePath& path); - int32_t OnCreateTemporaryFile(ppapi::host::HostMessageContext* context); - - FilePath ValidateAndConvertPepperFilePath( - const ppapi::PepperFilePath& pepper_path, - int flags); - - FilePath plugin_data_directory_; - int plugin_process_id_; - base::ProcessHandle plugin_process_handle_; -}; - -FileMessageFilter::FileMessageFilter( - const std::string& plugin_name, - const FilePath& profile_data_directory, - int plugin_process_id, - base::ProcessHandle plugin_process_handle) - : plugin_process_id_(plugin_process_id), - plugin_process_handle_(plugin_process_handle) { - if (profile_data_directory.empty() || plugin_name.empty()) { - // These are used to construct the path. If they are not set it means we - // will construct a bad path and could provide access to the wrong files. - // In this case, |plugin_data_directory_| will remain unset and - // |ValidateAndConvertPepperFilePath| will fail. - NOTREACHED(); - } else { - plugin_data_directory_ = PepperFlashFileHost::GetDataDirName( - profile_data_directory).Append(FilePath::FromUTF8Unsafe(plugin_name)); - } -} - -FileMessageFilter::~FileMessageFilter() { -} - -scoped_refptr<base::TaskRunner> -FileMessageFilter::OverrideTaskRunnerForMessage(const IPC::Message& msg) { - // The blocking pool provides a pool of threads to run file - // operations, instead of a single thread which might require - // queuing time. Since these messages are synchronous as sent from - // the plugin, the sending thread cannot send a new message until - // this one returns, so there is no need to sequence tasks here. If - // the plugin has multiple threads, it cannot make assumptions about - // ordering of IPC message sends, so it cannot make assumptions - // about ordering of operations caused by those IPC messages. - return scoped_refptr<base::TaskRunner>(BrowserThread::GetBlockingPool()); -} - -int32_t FileMessageFilter::OnResourceMessageReceived( - const IPC::Message& msg, - ppapi::host::HostMessageContext* context) { - IPC_BEGIN_MESSAGE_MAP(FileMessageFilter, msg) - PPAPI_DISPATCH_HOST_RESOURCE_CALL(PpapiHostMsg_FlashFile_OpenFile, - OnOpenFile) - PPAPI_DISPATCH_HOST_RESOURCE_CALL(PpapiHostMsg_FlashFile_RenameFile, - OnRenameFile) - PPAPI_DISPATCH_HOST_RESOURCE_CALL(PpapiHostMsg_FlashFile_DeleteFileOrDir, - OnDeleteFileOrDir) - PPAPI_DISPATCH_HOST_RESOURCE_CALL(PpapiHostMsg_FlashFile_CreateDir, - OnCreateDir) - PPAPI_DISPATCH_HOST_RESOURCE_CALL(PpapiHostMsg_FlashFile_QueryFile, - OnQueryFile) - PPAPI_DISPATCH_HOST_RESOURCE_CALL(PpapiHostMsg_FlashFile_GetDirContents, - OnGetDirContents) - PPAPI_DISPATCH_HOST_RESOURCE_CALL_0( - PpapiHostMsg_FlashFile_CreateTemporaryFile, - OnCreateTemporaryFile) - IPC_END_MESSAGE_MAP() - return PP_ERROR_FAILED; -} - -int32_t FileMessageFilter::OnOpenFile( - ppapi::host::HostMessageContext* context, - const ppapi::PepperFilePath& path, - int flags) { - FilePath full_path = ValidateAndConvertPepperFilePath(path, flags); - if (full_path.empty()) { - return ppapi::PlatformFileErrorToPepperError( - base::PLATFORM_FILE_ERROR_ACCESS_DENIED); - } - - base::PlatformFileError error = base::PLATFORM_FILE_ERROR_FAILED; - base::PlatformFile file_handle = base::CreatePlatformFile( - full_path, flags, NULL, &error); - if (error != base::PLATFORM_FILE_OK) { - DCHECK_EQ(file_handle, base::kInvalidPlatformFileValue); - return ppapi::PlatformFileErrorToPepperError(error); - } - - // Make sure we didn't try to open a directory: directory fd shouldn't be - // passed to untrusted processes because they open security holes. - base::PlatformFileInfo info; - if (!base::GetPlatformFileInfo(file_handle, &info) || info.is_directory) { - // When in doubt, throw it out. - base::ClosePlatformFile(file_handle); - return ppapi::PlatformFileErrorToPepperError( - base::PLATFORM_FILE_ERROR_ACCESS_DENIED); - } - - IPC::PlatformFileForTransit file = IPC::GetFileHandleForProcess(file_handle, - plugin_process_handle_, true); - ppapi::host::ReplyMessageContext reply_context = - context->MakeReplyMessageContext(); - reply_context.params.AppendHandle(ppapi::proxy::SerializedHandle( - ppapi::proxy::SerializedHandle::FILE, file)); - SendReply(reply_context, IPC::Message()); - return PP_OK_COMPLETIONPENDING; -} - -int32_t FileMessageFilter::OnRenameFile( - ppapi::host::HostMessageContext* context, - const ppapi::PepperFilePath& from_path, - const ppapi::PepperFilePath& to_path) { - FilePath from_full_path = ValidateAndConvertPepperFilePath(from_path, - kWritePermissions); - FilePath to_full_path = ValidateAndConvertPepperFilePath(to_path, - kWritePermissions); - if (from_full_path.empty() || to_full_path.empty()) { - return ppapi::PlatformFileErrorToPepperError( - base::PLATFORM_FILE_ERROR_ACCESS_DENIED); - } - - bool result = file_util::Move(from_full_path, to_full_path); - return ppapi::PlatformFileErrorToPepperError(result ? - base::PLATFORM_FILE_OK : base::PLATFORM_FILE_ERROR_ACCESS_DENIED); -} - -int32_t FileMessageFilter::OnDeleteFileOrDir( - ppapi::host::HostMessageContext* context, - const ppapi::PepperFilePath& path, - bool recursive) { - FilePath full_path = ValidateAndConvertPepperFilePath(path, - kWritePermissions); - if (full_path.empty()) { - return ppapi::PlatformFileErrorToPepperError( - base::PLATFORM_FILE_ERROR_ACCESS_DENIED); - } - - bool result = file_util::Delete(full_path, recursive); - return ppapi::PlatformFileErrorToPepperError(result ? - base::PLATFORM_FILE_OK : base::PLATFORM_FILE_ERROR_ACCESS_DENIED); -} -int32_t FileMessageFilter::OnCreateDir( - ppapi::host::HostMessageContext* context, - const ppapi::PepperFilePath& path) { - FilePath full_path = ValidateAndConvertPepperFilePath(path, - kWritePermissions); - if (full_path.empty()) { - return ppapi::PlatformFileErrorToPepperError( - base::PLATFORM_FILE_ERROR_ACCESS_DENIED); - } - - bool result = file_util::CreateDirectory(full_path); - return ppapi::PlatformFileErrorToPepperError(result ? - base::PLATFORM_FILE_OK : base::PLATFORM_FILE_ERROR_ACCESS_DENIED); -} - -int32_t FileMessageFilter::OnQueryFile( - ppapi::host::HostMessageContext* context, - const ppapi::PepperFilePath& path) { - FilePath full_path = ValidateAndConvertPepperFilePath(path, - kReadPermissions); - if (full_path.empty()) { - return ppapi::PlatformFileErrorToPepperError( - base::PLATFORM_FILE_ERROR_ACCESS_DENIED); - } - - base::PlatformFileInfo info; - bool result = file_util::GetFileInfo(full_path, &info); - context->reply_msg = PpapiPluginMsg_FlashFile_QueryFileReply(info); - return ppapi::PlatformFileErrorToPepperError(result ? - base::PLATFORM_FILE_OK : base::PLATFORM_FILE_ERROR_ACCESS_DENIED); -} - -int32_t FileMessageFilter::OnGetDirContents( - ppapi::host::HostMessageContext* context, - const ppapi::PepperFilePath& path) { - FilePath full_path = ValidateAndConvertPepperFilePath(path, kReadPermissions); - if (full_path.empty()) { - return ppapi::PlatformFileErrorToPepperError( - base::PLATFORM_FILE_ERROR_ACCESS_DENIED); - } - - ppapi::DirContents contents; - file_util::FileEnumerator enumerator(full_path, false, - file_util::FileEnumerator::FILES | - file_util::FileEnumerator::DIRECTORIES | - file_util::FileEnumerator::INCLUDE_DOT_DOT); - - while (!enumerator.Next().empty()) { - file_util::FileEnumerator::FindInfo info; - enumerator.GetFindInfo(&info); - ppapi::DirEntry entry = { - file_util::FileEnumerator::GetFilename(info), - file_util::FileEnumerator::IsDirectory(info) - }; - contents.push_back(entry); - } - - context->reply_msg = PpapiPluginMsg_FlashFile_GetDirContentsReply(contents); - return PP_OK; -} - -int32_t FileMessageFilter::OnCreateTemporaryFile( - ppapi::host::HostMessageContext* context) { - ppapi::PepperFilePath dir_path( - ppapi::PepperFilePath::DOMAIN_MODULE_LOCAL, FilePath()); - FilePath validated_dir_path = ValidateAndConvertPepperFilePath( - dir_path, kReadPermissions | kWritePermissions); - if (validated_dir_path.empty() || - (!file_util::DirectoryExists(validated_dir_path) && - !file_util::CreateDirectory(validated_dir_path))) { - return ppapi::PlatformFileErrorToPepperError( - base::PLATFORM_FILE_ERROR_ACCESS_DENIED); - } - - FilePath file_path; - if (!file_util::CreateTemporaryFileInDir(validated_dir_path, &file_path)) { - return ppapi::PlatformFileErrorToPepperError( - base::PLATFORM_FILE_ERROR_FAILED); - } - - base::PlatformFileError error = base::PLATFORM_FILE_ERROR_FAILED; - base::PlatformFile file_handle = base::CreatePlatformFile( - file_path, - base::PLATFORM_FILE_CREATE_ALWAYS | base::PLATFORM_FILE_READ | - base::PLATFORM_FILE_WRITE | base::PLATFORM_FILE_TEMPORARY | - base::PLATFORM_FILE_DELETE_ON_CLOSE, - NULL, &error); - - if (error != base::PLATFORM_FILE_OK) { - DCHECK_EQ(file_handle, base::kInvalidPlatformFileValue); - return ppapi::PlatformFileErrorToPepperError(error); - } - - IPC::PlatformFileForTransit file = IPC::GetFileHandleForProcess(file_handle, - plugin_process_handle_, true); - ppapi::host::ReplyMessageContext reply_context = - context->MakeReplyMessageContext(); - reply_context.params.AppendHandle(ppapi::proxy::SerializedHandle( - ppapi::proxy::SerializedHandle::FILE, file)); - SendReply(reply_context, IPC::Message()); - return PP_OK_COMPLETIONPENDING; -} - -FilePath FileMessageFilter::ValidateAndConvertPepperFilePath( - const ppapi::PepperFilePath& pepper_path, - int flags) { - FilePath file_path; // Empty path returned on error. - switch (pepper_path.domain()) { - case ppapi::PepperFilePath::DOMAIN_ABSOLUTE: - if (pepper_path.path().IsAbsolute() && - ChildProcessSecurityPolicyImpl::GetInstance()->HasPermissionsForFile( - plugin_process_id_, pepper_path.path(), flags)) - file_path = pepper_path.path(); - break; - case ppapi::PepperFilePath::DOMAIN_MODULE_LOCAL: - // This filter provides the module name portion of the path to prevent - // plugins from accessing each other's data. - if (!plugin_data_directory_.empty() && - !pepper_path.path().IsAbsolute() && - !pepper_path.path().ReferencesParent()) - file_path = plugin_data_directory_.Append(pepper_path.path()); - break; - default: - NOTREACHED(); - break; - } - return file_path; -} - -} // namespace - -PepperFlashFileHost::PepperFlashFileHost( - BrowserPpapiHost* host, - PP_Instance instance, - PP_Resource resource) - : ResourceHost(host->GetPpapiHost(), instance, resource) { - AddFilter(scoped_refptr<ppapi::host::ResourceMessageFilter>( - new FileMessageFilter(host->GetPluginName(), - host->GetProfileDataDirectory(), - host->GetPluginProcessID(), - host->GetPluginProcessHandle()))); -} - -PepperFlashFileHost::~PepperFlashFileHost() { -} - -// static -FilePath PepperFlashFileHost::GetDataDirName(const FilePath& profile_path) { - return profile_path.Append(kPepperDataDirname); -} - -} // namespace content diff --git a/content/browser/renderer_host/pepper/pepper_flash_file_host.h b/content/browser/renderer_host/pepper/pepper_flash_file_host.h deleted file mode 100644 index 6b45d98..0000000 --- a/content/browser/renderer_host/pepper/pepper_flash_file_host.h +++ /dev/null @@ -1,44 +0,0 @@ -// Copyright (c) 2012 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 CONTENT_BROWSER_RENDERER_HOST_PEPPER_PEPPER_FLASH_FILE_HOST_H_ -#define CONTENT_BROWSER_RENDERER_HOST_PEPPER_PEPPER_FLASH_FILE_HOST_H_ - -#include "base/compiler_specific.h" -#include "base/file_path.h" -#include "base/memory/ref_counted.h" -#include "base/process.h" -#include "ppapi/host/resource_host.h" -#include "ppapi/host/resource_message_filter.h" - -namespace ppapi { -class PepperFilePath; -} - -namespace ppapi { -namespace host { -struct ReplyMessageContext; -} -} - -namespace content { - -class BrowserPpapiHost; - -class PepperFlashFileHost : public ppapi::host::ResourceHost { - public: - PepperFlashFileHost(BrowserPpapiHost* host, - PP_Instance instance, - PP_Resource resource); - virtual ~PepperFlashFileHost(); - - static FilePath GetDataDirName(const FilePath& profile_path); - - private: - DISALLOW_COPY_AND_ASSIGN(PepperFlashFileHost); -}; - -} // namespace content - -#endif // CONTENT_BROWSER_RENDERER_HOST_PEPPER_PEPPER_FLASH_FILE_HOST_H_ diff --git a/content/browser/renderer_host/render_process_host_impl.cc b/content/browser/renderer_host/render_process_host_impl.cc index f5e455f..2e4f096 100644 --- a/content/browser/renderer_host/render_process_host_impl.cc +++ b/content/browser/renderer_host/render_process_host_impl.cc @@ -70,6 +70,7 @@ #include "content/browser/renderer_host/media/media_stream_dispatcher_host.h" #include "content/browser/renderer_host/media/video_capture_host.h" #include "content/browser/renderer_host/p2p/socket_dispatcher_host.h" +#include "content/browser/renderer_host/pepper/pepper_file_message_filter.h" #include "content/browser/renderer_host/pepper/pepper_message_filter.h" #include "content/browser/renderer_host/quota_dispatcher_host.h" #include "content/browser/renderer_host/render_message_filter.h" @@ -538,6 +539,12 @@ void RenderProcessHostImpl::CreateMessageFilters() { channel_->AddFilter(new MediaStreamDispatcherHost(GetID())); #endif #if defined(ENABLE_PLUGINS) + channel_->AddFilter( + GetContentClient()->browser()->AllowPepperPrivateFileAPI() ? + new PepperUnsafeFileMessageFilter( + GetID(), + storage_partition_impl_->GetPath()) : + new PepperFileMessageFilter(GetID())); channel_->AddFilter(new PepperMessageFilter(PepperMessageFilter::RENDERER, GetID(), browser_context)); #endif diff --git a/content/common/all_messages.h b/content/common/all_messages.h index 106af5a..b102ec9 100644 --- a/content/common/all_messages.h +++ b/content/common/all_messages.h @@ -9,5 +9,6 @@ // included here. #include "content/common/content_message_generator.h" #if defined(ENABLE_PLUGINS) +#include "ppapi/proxy/pepper_file_messages.h" #include "ppapi/proxy/ppapi_messages.h" #endif diff --git a/content/common/pepper_plugin_registry.cc b/content/common/pepper_plugin_registry.cc index 457ee8f..6db31e7 100644 --- a/content/common/pepper_plugin_registry.cc +++ b/content/common/pepper_plugin_registry.cc @@ -70,10 +70,6 @@ void ComputePluginsFromCommandLine(std::vector<PepperPluginInfo>* plugins) { plugin.mime_types.push_back(mime_type); } - // If the plugin name is empty, use the filename. - if (plugin.name.empty()) - plugin.name = UTF16ToUTF8(plugin.path.BaseName().LossyDisplayName()); - // Command-line plugins get full permissions. plugin.permissions = ppapi::PERMISSION_ALL_BITS; diff --git a/content/content_browser.gypi b/content/content_browser.gypi index 5273ae4..0bcfa46 100644 --- a/content/content_browser.gypi +++ b/content/content_browser.gypi @@ -675,10 +675,10 @@ 'browser/renderer_host/pepper/browser_ppapi_host_impl.h', 'browser/renderer_host/pepper/content_browser_pepper_host_factory.cc', 'browser/renderer_host/pepper/content_browser_pepper_host_factory.h', + 'browser/renderer_host/pepper/pepper_file_message_filter.cc', + 'browser/renderer_host/pepper/pepper_file_message_filter.h', 'browser/renderer_host/pepper/pepper_flash_browser_host.cc', 'browser/renderer_host/pepper/pepper_flash_browser_host.h', - 'browser/renderer_host/pepper/pepper_flash_file_host.cc', - 'browser/renderer_host/pepper/pepper_flash_file_host.h', 'browser/renderer_host/pepper/pepper_gamepad_host.cc', 'browser/renderer_host/pepper/pepper_gamepad_host.h', 'browser/renderer_host/pepper/pepper_lookup_request.h', diff --git a/content/public/browser/browser_ppapi_host.h b/content/public/browser/browser_ppapi_host.h index 2dbdfe3..febd0ea 100644 --- a/content/public/browser/browser_ppapi_host.h +++ b/content/public/browser/browser_ppapi_host.h @@ -44,7 +44,6 @@ class CONTENT_EXPORT BrowserPpapiHost { IPC::Sender* sender, ppapi::PpapiPermissions permissions, base::ProcessHandle plugin_child_process, - int plugin_child_process_id, IPC::ChannelProxy* channel, net::HostResolver* host_resolver, int render_process_id, @@ -73,14 +72,6 @@ class CONTENT_EXPORT BrowserPpapiHost { virtual bool GetRenderViewIDsForInstance(PP_Instance instance, int* render_process_id, int* render_view_id) const = 0; - // Returns the name of the plugin. - virtual const std::string& GetPluginName() = 0; - - // Returns the user's profile data directory. - virtual const FilePath& GetProfileDataDirectory() = 0; - - // Returns the unique id of the child plugin process (this is NOT the pid). - virtual int GetPluginProcessID() = 0; }; } // namespace content diff --git a/content/public/browser/content_browser_client.cc b/content/public/browser/content_browser_client.cc index c01dc06..05ddc93 100644 --- a/content/public/browser/content_browser_client.cc +++ b/content/public/browser/content_browser_client.cc @@ -250,6 +250,10 @@ bool ContentBrowserClient::AllowPepperSocketAPI( return false; } +bool ContentBrowserClient::AllowPepperPrivateFileAPI() { + return false; +} + FilePath ContentBrowserClient::GetHyphenDictionaryDirectory() { return FilePath(); } diff --git a/content/public/browser/content_browser_client.h b/content/public/browser/content_browser_client.h index 373ec58..7368ebb 100644 --- a/content/public/browser/content_browser_client.h +++ b/content/public/browser/content_browser_client.h @@ -459,6 +459,9 @@ class CONTENT_EXPORT ContentBrowserClient { const GURL& url, const SocketPermissionRequest& params); + // Returns true if renderer processes can use private Pepper File APIs. + virtual bool AllowPepperPrivateFileAPI(); + // Returns the directory containing hyphenation dictionaries. virtual FilePath GetHyphenDictionaryDirectory(); diff --git a/content/renderer/pepper/pepper_plugin_delegate_impl.cc b/content/renderer/pepper/pepper_plugin_delegate_impl.cc index eba8ee3..b890100 100644 --- a/content/renderer/pepper/pepper_plugin_delegate_impl.cc +++ b/content/renderer/pepper/pepper_plugin_delegate_impl.cc @@ -63,6 +63,7 @@ #include "ppapi/c/private/ppb_flash.h" #include "ppapi/host/ppapi_host.h" #include "ppapi/proxy/host_dispatcher.h" +#include "ppapi/proxy/pepper_file_messages.h" #include "ppapi/proxy/ppapi_messages.h" #include "ppapi/shared_impl/file_path.h" #include "ppapi/shared_impl/platform_file.h" @@ -1089,6 +1090,86 @@ bool PepperPluginDelegateImpl::AsyncOpenFileSystemURL( base::Bind(&DoNotifyCloseFile, path))); } +base::PlatformFileError PepperPluginDelegateImpl::OpenFile( + const ppapi::PepperFilePath& path, + int flags, + base::PlatformFile* file) { + IPC::PlatformFileForTransit transit_file; + base::PlatformFileError error; + IPC::Message* msg = new PepperFileMsg_OpenFile( + path, flags, &error, &transit_file); + if (!render_view_->Send(msg)) { + *file = base::kInvalidPlatformFileValue; + return base::PLATFORM_FILE_ERROR_FAILED; + } + *file = IPC::PlatformFileForTransitToPlatformFile(transit_file); + return error; +} + +base::PlatformFileError PepperPluginDelegateImpl::RenameFile( + const ppapi::PepperFilePath& from_path, + const ppapi::PepperFilePath& to_path) { + base::PlatformFileError error; + IPC::Message* msg = new PepperFileMsg_RenameFile(from_path, to_path, &error); + if (!render_view_->Send(msg)) + return base::PLATFORM_FILE_ERROR_FAILED; + return error; +} + +base::PlatformFileError PepperPluginDelegateImpl::DeleteFileOrDir( + const ppapi::PepperFilePath& path, + bool recursive) { + base::PlatformFileError error; + IPC::Message* msg = new PepperFileMsg_DeleteFileOrDir( + path, recursive, &error); + if (!render_view_->Send(msg)) + return base::PLATFORM_FILE_ERROR_FAILED; + return error; +} + +base::PlatformFileError PepperPluginDelegateImpl::CreateDir( + const ppapi::PepperFilePath& path) { + base::PlatformFileError error; + IPC::Message* msg = new PepperFileMsg_CreateDir(path, &error); + if (!render_view_->Send(msg)) + return base::PLATFORM_FILE_ERROR_FAILED; + return error; +} + +base::PlatformFileError PepperPluginDelegateImpl::QueryFile( + const ppapi::PepperFilePath& path, + base::PlatformFileInfo* info) { + base::PlatformFileError error; + IPC::Message* msg = new PepperFileMsg_QueryFile(path, info, &error); + if (!render_view_->Send(msg)) + return base::PLATFORM_FILE_ERROR_FAILED; + return error; +} + +base::PlatformFileError PepperPluginDelegateImpl::GetDirContents( + const ppapi::PepperFilePath& path, + ppapi::DirContents* contents) { + base::PlatformFileError error; + IPC::Message* msg = new PepperFileMsg_GetDirContents(path, contents, &error); + if (!render_view_->Send(msg)) + return base::PLATFORM_FILE_ERROR_FAILED; + return error; +} + +base::PlatformFileError PepperPluginDelegateImpl::CreateTemporaryFile( + base::PlatformFile* file) { + IPC::PlatformFileForTransit transit_file; + base::PlatformFileError error; + IPC::Message* msg = new PepperFileMsg_CreateTemporaryFile(&error, + &transit_file); + if (!render_view_->Send(msg)) { + *file = base::kInvalidPlatformFileValue; + return base::PLATFORM_FILE_ERROR_FAILED; + } + *file = IPC::PlatformFileForTransitToPlatformFile(transit_file); + return error; +} + void PepperPluginDelegateImpl::SyncGetFileSystemPlatformPath( const GURL& url, FilePath* platform_path) { RenderThreadImpl::current()->Send(new FileSystemHostMsg_SyncGetPlatformPath( diff --git a/content/renderer/pepper/pepper_plugin_delegate_impl.h b/content/renderer/pepper/pepper_plugin_delegate_impl.h index 700bbef..d88a672 100644 --- a/content/renderer/pepper/pepper_plugin_delegate_impl.h +++ b/content/renderer/pepper/pepper_plugin_delegate_impl.h @@ -240,6 +240,26 @@ class PepperPluginDelegateImpl const AvailableSpaceCallback& callback) OVERRIDE; virtual void WillUpdateFile(const GURL& file_path) OVERRIDE; virtual void DidUpdateFile(const GURL& file_path, int64_t delta) OVERRIDE; + virtual base::PlatformFileError OpenFile( + const ppapi::PepperFilePath& path, + int flags, + base::PlatformFile* file) OVERRIDE; + virtual base::PlatformFileError RenameFile( + const ppapi::PepperFilePath& from_path, + const ppapi::PepperFilePath& to_path) OVERRIDE; + virtual base::PlatformFileError DeleteFileOrDir( + const ppapi::PepperFilePath& path, + bool recursive) OVERRIDE; + virtual base::PlatformFileError CreateDir( + const ppapi::PepperFilePath& path) OVERRIDE; + virtual base::PlatformFileError QueryFile( + const ppapi::PepperFilePath& path, + base::PlatformFileInfo* info) OVERRIDE; + virtual base::PlatformFileError GetDirContents( + const ppapi::PepperFilePath& path, + ppapi::DirContents* contents) OVERRIDE; + virtual base::PlatformFileError CreateTemporaryFile( + base::PlatformFile* file) OVERRIDE; virtual void SyncGetFileSystemPlatformPath( const GURL& url, FilePath* platform_path) OVERRIDE; diff --git a/ppapi/c/private/ppb_flash_file.h b/ppapi/c/private/ppb_flash_file.h index 807fc04..758056f 100644 --- a/ppapi/c/private/ppb_flash_file.h +++ b/ppapi/c/private/ppb_flash_file.h @@ -32,9 +32,18 @@ struct PP_DirContents_Dev { // Module-local file paths are '/'-separated UTF-8 strings, relative to a // module-specific root. struct PPB_Flash_File_ModuleLocal_3_0 { - // Deprecated. Returns true. + // Does initialization necessary for proxying this interface on background + // threads. You must always call this function before using any other + // function in this interface for a given instance ID. + // + // Returns true if multithreaded access is supported. In this case you can + // use the rest of the functions from background threads. You may not call + // GetInterface or do any other PPAPI operations on background threads at + // this time. bool (*CreateThreadAdapterForInstance)(PP_Instance instance); - // Deprecated. Does nothing. + + // Call when an instance is destroyed when you've previously called + // CreateThreadAdapterForInstance. void (*ClearThreadAdapterForInstance)(PP_Instance instance); // Opens a file, returning a file descriptor (posix) or a HANDLE (win32) into diff --git a/ppapi/cpp/private/flash_file.cc b/ppapi/cpp/private/flash_file.cc index a38f007..2aea2c3 100644 --- a/ppapi/cpp/private/flash_file.cc +++ b/ppapi/cpp/private/flash_file.cc @@ -40,6 +40,32 @@ bool FileModuleLocal::IsAvailable() { } // static +bool FileModuleLocal::CreateThreadAdapterForInstance( + const InstanceHandle& instance) { + bool rv = false; + if (has_interface<PPB_Flash_File_ModuleLocal_3_0>()) { + rv = get_interface<PPB_Flash_File_ModuleLocal_3_0>()-> + CreateThreadAdapterForInstance(instance.pp_instance()); + } else if (has_interface<PPB_Flash_File_ModuleLocal_2_0>()) { + rv = get_interface<PPB_Flash_File_ModuleLocal_2_0>()-> + CreateThreadAdapterForInstance( instance.pp_instance()); + } + return rv; +} + +// static +void FileModuleLocal::ClearThreadAdapterForInstance( + const InstanceHandle& instance) { + if (has_interface<PPB_Flash_File_ModuleLocal_3_0>()) { + get_interface<PPB_Flash_File_ModuleLocal_3_0>()-> + ClearThreadAdapterForInstance(instance.pp_instance()); + } else if (has_interface<PPB_Flash_File_ModuleLocal_2_0>()) { + get_interface<PPB_Flash_File_ModuleLocal_2_0>()-> + ClearThreadAdapterForInstance(instance.pp_instance()); + } +} + +// static PP_FileHandle FileModuleLocal::OpenFile(const InstanceHandle& instance, const std::string& path, int32_t mode) { @@ -153,6 +179,11 @@ bool FileModuleLocal::GetDirContents( } // static +bool FileModuleLocal::IsCreateTemporaryFileAvailable() { + return has_interface<PPB_Flash_File_ModuleLocal_3_0>(); +} + +// static PP_FileHandle FileModuleLocal::CreateTemporaryFile( const InstanceHandle& instance) { PP_FileHandle file_handle = PP_kInvalidFileHandle; diff --git a/ppapi/cpp/private/flash_file.h b/ppapi/cpp/private/flash_file.h index 04ab195..a7c655a 100644 --- a/ppapi/cpp/private/flash_file.h +++ b/ppapi/cpp/private/flash_file.h @@ -24,6 +24,9 @@ class FileModuleLocal { // Returns true if the required interface is available. static bool IsAvailable(); + static bool CreateThreadAdapterForInstance(const InstanceHandle& instance); + static void ClearThreadAdapterForInstance(const InstanceHandle& instance); + // Returns |PP_kInvalidFileHandle| on error. static PP_FileHandle OpenFile(const InstanceHandle& instance, const std::string& path, @@ -48,6 +51,9 @@ class FileModuleLocal { const std::string& path, std::vector<DirEntry>* dir_contents); + // Returns true if |CreateTemporaryFile()| is supported. + // TODO(viettrungluu): Remove this sometime after M21 ships to Stable? + static bool IsCreateTemporaryFileAvailable(); // Returns |PP_kInvalidFileHandle| on error. static PP_FileHandle CreateTemporaryFile(const InstanceHandle& instance); }; diff --git a/ppapi/ppapi_ipc.gypi b/ppapi/ppapi_ipc.gypi index 8e374b2..8c23bf2 100644 --- a/ppapi/ppapi_ipc.gypi +++ b/ppapi/ppapi_ipc.gypi @@ -12,6 +12,8 @@ # This part is shared between the targets defined below. ['ppapi_ipc_target==1', { 'sources': [ + 'proxy/pepper_file_messages.cc', + 'proxy/pepper_file_messages.h', 'proxy/ppapi_messages.cc', 'proxy/ppapi_messages.h', 'proxy/ppapi_param_traits.cc', diff --git a/ppapi/ppapi_proxy.gypi b/ppapi/ppapi_proxy.gypi index 81ec94f..f835ff2 100644 --- a/ppapi/ppapi_proxy.gypi +++ b/ppapi/ppapi_proxy.gypi @@ -39,8 +39,6 @@ 'proxy/flash_clipboard_resource.h', 'proxy/flash_device_id_resource.cc', 'proxy/flash_device_id_resource.h', - 'proxy/flash_file_resource.cc', - 'proxy/flash_file_resource.h', 'proxy/flash_font_file_resource.cc', 'proxy/flash_font_file_resource.h', 'proxy/flash_fullscreen_resource.cc', @@ -189,7 +187,6 @@ 'proxy/device_enumeration_resource_helper.cc', 'proxy/flash_clipboard_resource.cc', 'proxy/flash_device_id_resource.cc', - 'proxy/flash_file_resource.cc', 'proxy/flash_font_file_resource.cc', 'proxy/flash_fullscreen_resource.cc', 'proxy/flash_menu_resource.cc', diff --git a/ppapi/ppapi_shared.gypi b/ppapi/ppapi_shared.gypi index 9033612..da446ef 100644 --- a/ppapi/ppapi_shared.gypi +++ b/ppapi/ppapi_shared.gypi @@ -55,6 +55,8 @@ 'shared_impl/ppb_file_io_shared.h', 'shared_impl/ppb_file_ref_shared.cc', 'shared_impl/ppb_file_ref_shared.h', + 'shared_impl/ppb_flash_shared.cc', + 'shared_impl/ppb_flash_shared.h', 'shared_impl/ppb_gamepad_shared.cc', 'shared_impl/ppb_gamepad_shared.h', 'shared_impl/ppb_graphics_3d_shared.cc', diff --git a/ppapi/proxy/flash_file_resource.cc b/ppapi/proxy/flash_file_resource.cc deleted file mode 100644 index ac9e555..0000000 --- a/ppapi/proxy/flash_file_resource.cc +++ /dev/null @@ -1,231 +0,0 @@ -// Copyright (c) 2012 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 "ppapi/proxy/flash_file_resource.h" - -#include "base/file_path.h" -#include "ipc/ipc_message.h" -#include "ppapi/c/pp_errors.h" -#include "ppapi/proxy/ppapi_messages.h" -#include "ppapi/shared_impl/file_type_conversion.h" -#include "ppapi/shared_impl/scoped_pp_var.h" -#include "ppapi/shared_impl/time_conversion.h" -#include "ppapi/shared_impl/var.h" -#include "ppapi/thunk/enter.h" - -namespace ppapi { -namespace proxy { - -namespace { - -// Returns the path that a PPB_FileRef resource references as long as it is an -// PP_FILESYSTEMTYPE_EXTERNAL path. Returns an empty string on error. -std::string GetPathFromFileRef(PP_Resource file_ref) { - thunk::EnterResourceNoLock<thunk::PPB_FileRef_API> enter(file_ref, true); - if (enter.failed()) - return std::string(); - if (enter.object()->GetFileSystemType() != PP_FILESYSTEMTYPE_EXTERNAL) - return std::string(); - ScopedPPVar var(ScopedPPVar::PassRef(), enter.object()->GetAbsolutePath()); - StringVar* string_var = StringVar::FromPPVar(var.get()); - if (!string_var) - return std::string(); - return string_var->value(); -} - -} // namespace - -FlashFileResource::FlashFileResource(Connection connection, - PP_Instance instance) - : PluginResource(connection, instance) { - SendCreate(BROWSER, PpapiHostMsg_FlashFile_Create()); -} - -FlashFileResource::~FlashFileResource() { -} - -thunk::PPB_Flash_File_API* FlashFileResource::AsPPB_Flash_File_API() { - return this; -} - -int32_t FlashFileResource::OpenFile(PP_Instance /*instance*/, - const char* path, - int32_t mode, - PP_FileHandle* file) { - return OpenFileHelper(path, PepperFilePath::DOMAIN_MODULE_LOCAL, mode, file); -} - -int32_t FlashFileResource::RenameFile(PP_Instance /*instance*/, - const char* path_from, - const char* path_to) { - PepperFilePath pepper_from(PepperFilePath::DOMAIN_MODULE_LOCAL, - FilePath::FromUTF8Unsafe(path_from)); - PepperFilePath pepper_to(PepperFilePath::DOMAIN_MODULE_LOCAL, - FilePath::FromUTF8Unsafe(path_to)); - - int32_t error = SyncCall<IPC::Message>( - BROWSER, PpapiHostMsg_FlashFile_RenameFile(pepper_from, pepper_to)); - - return error; -} - -int32_t FlashFileResource::DeleteFileOrDir(PP_Instance /*instance*/, - const char* path, - PP_Bool recursive) { - PepperFilePath pepper_path(PepperFilePath::DOMAIN_MODULE_LOCAL, - FilePath::FromUTF8Unsafe(path)); - - int32_t error = SyncCall<IPC::Message>( - BROWSER, PpapiHostMsg_FlashFile_DeleteFileOrDir(pepper_path, - PP_ToBool(recursive))); - - return error; -} - -int32_t FlashFileResource::CreateDir(PP_Instance /*instance*/, - const char* path) { - PepperFilePath pepper_path(PepperFilePath::DOMAIN_MODULE_LOCAL, - FilePath::FromUTF8Unsafe(path)); - - int32_t error = SyncCall<IPC::Message>(BROWSER, - PpapiHostMsg_FlashFile_CreateDir(pepper_path)); - - return error; -} - -int32_t FlashFileResource::QueryFile(PP_Instance /*instance*/, - const char* path, - PP_FileInfo* info) { - return QueryFileHelper(path, PepperFilePath::DOMAIN_MODULE_LOCAL, info); -} - -int32_t FlashFileResource::GetDirContents(PP_Instance /*instance*/, - const char* path, - PP_DirContents_Dev** contents) { - ppapi::DirContents entries; - PepperFilePath pepper_path(PepperFilePath::DOMAIN_MODULE_LOCAL, - FilePath::FromUTF8Unsafe(path)); - - int32_t error = SyncCall<PpapiPluginMsg_FlashFile_GetDirContentsReply>( - BROWSER, PpapiHostMsg_FlashFile_GetDirContents(pepper_path), &entries); - - if (error == PP_OK) { - // Copy the serialized dir entries to the output struct. - *contents = new PP_DirContents_Dev; - (*contents)->count = static_cast<int32_t>(entries.size()); - (*contents)->entries = new PP_DirEntry_Dev[entries.size()]; - for (size_t i = 0; i < entries.size(); i++) { - const ppapi::DirEntry& source = entries[i]; - PP_DirEntry_Dev* dest = &(*contents)->entries[i]; - std::string name = source.name.AsUTF8Unsafe(); - char* name_copy = new char[name.size() + 1]; - memcpy(name_copy, name.c_str(), name.size() + 1); - dest->name = name_copy; - dest->is_dir = PP_FromBool(source.is_dir); - } - } - - return error; -} - -void FlashFileResource::FreeDirContents(PP_Instance /*instance*/, - PP_DirContents_Dev* contents) { - for (int32_t i = 0; i < contents->count; ++i) - delete[] contents->entries[i].name; - delete[] contents->entries; - delete contents; -} - -int32_t FlashFileResource::CreateTemporaryFile(PP_Instance /*instance*/, - PP_FileHandle* file) { - if (!file) - return PP_ERROR_BADARGUMENT; - - IPC::Message unused; - ResourceMessageReplyParams reply_params; - int32_t error = GenericSyncCall(BROWSER, - PpapiHostMsg_FlashFile_CreateTemporaryFile(), &unused, &reply_params); - if (error != PP_OK) - return error; - - IPC::PlatformFileForTransit transit_file; - if (!reply_params.TakeFileHandleAtIndex(0, &transit_file)) - return PP_ERROR_FAILED; - - *file = IPC::PlatformFileForTransitToPlatformFile(transit_file); - return PP_OK; -} - -int32_t FlashFileResource::OpenFileRef(PP_Instance /*instance*/, - PP_Resource file_ref, - int32_t mode, - PP_FileHandle* file) { - return OpenFileHelper(GetPathFromFileRef(file_ref), - PepperFilePath::DOMAIN_ABSOLUTE, mode, file); -} - -int32_t FlashFileResource::QueryFileRef(PP_Instance /*instance*/, - PP_Resource file_ref, - PP_FileInfo* info) { - return QueryFileHelper(GetPathFromFileRef(file_ref), - PepperFilePath::DOMAIN_ABSOLUTE, info); -} - -int32_t FlashFileResource::OpenFileHelper(const std::string& path, - PepperFilePath::Domain domain_type, - int32_t mode, - PP_FileHandle* file) { - int flags = 0; - if (path.empty() || - !ppapi::PepperFileOpenFlagsToPlatformFileFlags(mode, &flags) || - !file) - return PP_ERROR_BADARGUMENT; - - PepperFilePath pepper_path(domain_type, FilePath::FromUTF8Unsafe(path)); - - IPC::Message unused; - ResourceMessageReplyParams reply_params; - int32_t error = GenericSyncCall(BROWSER, - PpapiHostMsg_FlashFile_OpenFile(pepper_path, flags), &unused, - &reply_params); - if (error != PP_OK) - return error; - - IPC::PlatformFileForTransit transit_file; - if (!reply_params.TakeFileHandleAtIndex(0, &transit_file)) - return PP_ERROR_FAILED; - - *file = IPC::PlatformFileForTransitToPlatformFile(transit_file); - return PP_OK; -} - -int32_t FlashFileResource::QueryFileHelper(const std::string& path, - PepperFilePath::Domain domain_type, - PP_FileInfo* info) { - if (path.empty() || !info) - return PP_ERROR_BADARGUMENT; - - base::PlatformFileInfo file_info; - PepperFilePath pepper_path(domain_type, FilePath::FromUTF8Unsafe(path)); - - int32_t error = SyncCall<PpapiPluginMsg_FlashFile_QueryFileReply>(BROWSER, - PpapiHostMsg_FlashFile_QueryFile(pepper_path), &file_info); - - if (error == PP_OK) { - info->size = file_info.size; - info->creation_time = TimeToPPTime(file_info.creation_time); - info->last_access_time = TimeToPPTime(file_info.last_accessed); - info->last_modified_time = TimeToPPTime(file_info.last_modified); - info->system_type = PP_FILESYSTEMTYPE_EXTERNAL; - if (file_info.is_directory) - info->type = PP_FILETYPE_DIRECTORY; - else - info->type = PP_FILETYPE_REGULAR; - } - - return error; -} - -} // namespace proxy -} // namespace ppapi diff --git a/ppapi/proxy/flash_file_resource.h b/ppapi/proxy/flash_file_resource.h deleted file mode 100644 index f8c4b18..0000000 --- a/ppapi/proxy/flash_file_resource.h +++ /dev/null @@ -1,73 +0,0 @@ -// Copyright (c) 2012 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 PPAPI_PROXY_FLASH_FILE_RESOURCE_H_ -#define PPAPI_PROXY_FLASH_FILE_RESOURCE_H_ - -#include <string> - -#include "ppapi/proxy/connection.h" -#include "ppapi/proxy/plugin_resource.h" -#include "ppapi/shared_impl/file_path.h" -#include "ppapi/thunk/ppb_flash_file_api.h" - -namespace ppapi { -namespace proxy { - -class FlashFileResource - : public PluginResource, - public thunk::PPB_Flash_File_API { - public: - FlashFileResource(Connection connection, PP_Instance instance); - virtual ~FlashFileResource(); - - // Resource overrides. - virtual thunk::PPB_Flash_File_API* AsPPB_Flash_File_API() OVERRIDE; - - // PPB_Flash_Functions_API. - virtual int32_t OpenFile(PP_Instance instance, - const char* path, - int32_t mode, - PP_FileHandle* file) OVERRIDE; - virtual int32_t RenameFile(PP_Instance instance, - const char* path_from, - const char* path_to) OVERRIDE; - virtual int32_t DeleteFileOrDir(PP_Instance instance, - const char* path, - PP_Bool recursive) OVERRIDE; - virtual int32_t CreateDir(PP_Instance instance, const char* path) OVERRIDE; - virtual int32_t QueryFile(PP_Instance instance, - const char* path, - PP_FileInfo* info) OVERRIDE; - virtual int32_t GetDirContents(PP_Instance instance, - const char* path, - PP_DirContents_Dev** contents) OVERRIDE; - virtual void FreeDirContents(PP_Instance instance, - PP_DirContents_Dev* contents) OVERRIDE; - virtual int32_t CreateTemporaryFile(PP_Instance instance, - PP_FileHandle* file) OVERRIDE; - virtual int32_t OpenFileRef(PP_Instance instance, - PP_Resource file_ref, - int32_t mode, - PP_FileHandle* file) OVERRIDE; - virtual int32_t QueryFileRef(PP_Instance instance, - PP_Resource file_ref, - PP_FileInfo* info) OVERRIDE; - - private: - int32_t OpenFileHelper(const std::string& path, - PepperFilePath::Domain domain_type, - int32_t mode, - PP_FileHandle* file); - int32_t QueryFileHelper(const std::string& path, - PepperFilePath::Domain domain_type, - PP_FileInfo* info); - - DISALLOW_COPY_AND_ASSIGN(FlashFileResource); -}; - -} // namespace proxy -} // namespace ppapi - -#endif // PPAPI_PROXY_FLASH_FILE_RESOURCE_H_ diff --git a/ppapi/proxy/pepper_file_messages.cc b/ppapi/proxy/pepper_file_messages.cc new file mode 100644 index 0000000..53b4fcb --- /dev/null +++ b/ppapi/proxy/pepper_file_messages.cc @@ -0,0 +1,68 @@ +// Copyright (c) 2012 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. + + +// Get basic type definitions. +#define IPC_MESSAGE_IMPL +#include "ppapi/proxy/pepper_file_messages.h" + +// Generate constructors. +#include "ipc/struct_constructor_macros.h" +#include "ppapi/proxy/pepper_file_messages.h" + +// Generate destructors. +#include "ipc/struct_destructor_macros.h" +#include "ppapi/proxy/pepper_file_messages.h" + +// Generate param traits write methods. +#include "ipc/param_traits_write_macros.h" +namespace IPC { +#include "ppapi/proxy/pepper_file_messages.h" +} // namespace IPC + +// Generate param traits read methods. +#include "ipc/param_traits_read_macros.h" +namespace IPC { +#include "ppapi/proxy/pepper_file_messages.h" +} // namespace IPC + +// Generate param traits log methods. +#include "ipc/param_traits_log_macros.h" +namespace IPC { +#include "ppapi/proxy/pepper_file_messages.h" +} // namespace IPC + +namespace IPC { + +void ParamTraits<ppapi::PepperFilePath>::Write(Message* m, + const param_type& p) { + WriteParam(m, static_cast<unsigned>(p.domain())); + WriteParam(m, p.path()); +} + +bool ParamTraits<ppapi::PepperFilePath>::Read(const Message* m, + PickleIterator* iter, + param_type* p) { + unsigned domain; + FilePath path; + if (!ReadParam(m, iter, &domain) || !ReadParam(m, iter, &path)) + return false; + if (domain > ppapi::PepperFilePath::DOMAIN_MAX_VALID) + return false; + + *p = ppapi::PepperFilePath( + static_cast<ppapi::PepperFilePath::Domain>(domain), path); + return true; +} + +void ParamTraits<ppapi::PepperFilePath>::Log(const param_type& p, + std::string* l) { + l->append("("); + LogParam(static_cast<unsigned>(p.domain()), l); + l->append(", "); + LogParam(p.path(), l); + l->append(")"); +} + +} // namespace IPC diff --git a/ppapi/proxy/pepper_file_messages.h b/ppapi/proxy/pepper_file_messages.h new file mode 100644 index 0000000..3edd490 --- /dev/null +++ b/ppapi/proxy/pepper_file_messages.h @@ -0,0 +1,82 @@ +// Copyright (c) 2012 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. + +// Multiply-included message file, no traditional include guard. +#include "ipc/ipc_message_macros.h" +#include "ipc/ipc_param_traits.h" +#include "ipc/ipc_platform_file.h" +#include "ppapi/proxy/ppapi_proxy_export.h" +#include "ppapi/shared_impl/dir_contents.h" +#include "ppapi/shared_impl/file_path.h" + +// Singly-included section since need custom serialization. +#ifndef PPAPI_SHARED_IMPL_PEPPER_FILE_MESSAGES_H_ +#define PPAPI_SHARED_IMPL_PEPPER_FILE_MESSAGES_H_ + +namespace IPC { + +template <> +struct ParamTraits<ppapi::PepperFilePath> { + typedef ppapi::PepperFilePath param_type; + static void Write(Message* m, const param_type& p); + static bool Read(const Message* m, PickleIterator* iter, param_type* p); + static void Log(const param_type& p, std::string* l); +}; + +} // namespace IPC + +#endif // PPAPI_SHARED_IMPL_PEPPER_FILE_MESSAGES_H_ + +#undef IPC_MESSAGE_EXPORT +#define IPC_MESSAGE_EXPORT PPAPI_PROXY_EXPORT + +#define IPC_MESSAGE_START PepperFileMsgStart + +IPC_STRUCT_TRAITS_BEGIN(ppapi::DirEntry) + IPC_STRUCT_TRAITS_MEMBER(name) + IPC_STRUCT_TRAITS_MEMBER(is_dir) +IPC_STRUCT_TRAITS_END() + +// Trusted Pepper Filesystem messages from the renderer to the browser. + +// Open the file. +IPC_SYNC_MESSAGE_CONTROL2_2(PepperFileMsg_OpenFile, + ppapi::PepperFilePath /* path */, + int /* flags */, + base::PlatformFileError /* error_code */, + IPC::PlatformFileForTransit /* result */) + +// Rename the file. +IPC_SYNC_MESSAGE_CONTROL2_1(PepperFileMsg_RenameFile, + ppapi::PepperFilePath /* from_path */, + ppapi::PepperFilePath /* to_path */, + base::PlatformFileError /* error_code */) + +// Delete the file. +IPC_SYNC_MESSAGE_CONTROL2_1(PepperFileMsg_DeleteFileOrDir, + ppapi::PepperFilePath /* path */, + bool /* recursive */, + base::PlatformFileError /* error_code */) + +// Create the directory. +IPC_SYNC_MESSAGE_CONTROL1_1(PepperFileMsg_CreateDir, + ppapi::PepperFilePath /* path */, + base::PlatformFileError /* error_code */) + +// Query the file's info. +IPC_SYNC_MESSAGE_CONTROL1_2(PepperFileMsg_QueryFile, + ppapi::PepperFilePath /* path */, + base::PlatformFileInfo, /* info */ + base::PlatformFileError /* error_code */) + +// Get the directory's contents. +IPC_SYNC_MESSAGE_CONTROL1_2(PepperFileMsg_GetDirContents, + ppapi::PepperFilePath /* path */, + ppapi::DirContents, /* contents */ + base::PlatformFileError /* error_code */) + +// Create a temporary file. +IPC_SYNC_MESSAGE_CONTROL0_2(PepperFileMsg_CreateTemporaryFile, + base::PlatformFileError /* error_code */, + IPC::PlatformFileForTransit /* file */) diff --git a/ppapi/proxy/plugin_dispatcher.cc b/ppapi/proxy/plugin_dispatcher.cc index b864d99..939327b 100644 --- a/ppapi/proxy/plugin_dispatcher.cc +++ b/ppapi/proxy/plugin_dispatcher.cc @@ -16,7 +16,6 @@ #include "ppapi/c/ppp_instance.h" #include "ppapi/proxy/flash_resource.h" #include "ppapi/proxy/flash_clipboard_resource.h" -#include "ppapi/proxy/flash_file_resource.h" #include "ppapi/proxy/gamepad_resource.h" #include "ppapi/proxy/interface_list.h" #include "ppapi/proxy/interface_proxy.h" diff --git a/ppapi/proxy/plugin_dispatcher.h b/ppapi/proxy/plugin_dispatcher.h index 8d12e39d..98f43a6 100644 --- a/ppapi/proxy/plugin_dispatcher.h +++ b/ppapi/proxy/plugin_dispatcher.h @@ -35,6 +35,9 @@ class ResourceCreationAPI; namespace proxy { +class FlashClipboardResource; +class FlashResource; +class GamepadResource; class ResourceMessageReplyParams; // Used to keep track of per-instance data. diff --git a/ppapi/proxy/plugin_resource.cc b/ppapi/proxy/plugin_resource.cc index 3dd47ba..fca0630 100644 --- a/ppapi/proxy/plugin_resource.cc +++ b/ppapi/proxy/plugin_resource.cc @@ -108,17 +108,16 @@ bool PluginResource::SendResourceCall( new PpapiHostMsg_ResourceCall(call_params, nested_msg)); } -int32_t PluginResource::GenericSyncCall( - Destination dest, - const IPC::Message& msg, - IPC::Message* reply, - ResourceMessageReplyParams* reply_params) { +int32_t PluginResource::GenericSyncCall(Destination dest, + const IPC::Message& msg, + IPC::Message* reply) { ResourceMessageCallParams params(pp_resource(), GetNextSequence()); params.set_has_callback(); + ResourceMessageReplyParams reply_params; bool success = GetSender(dest)->Send(new PpapiHostMsg_ResourceSyncCall( - params, msg, reply_params, reply)); + params, msg, &reply_params, reply)); if (success) - return reply_params->result(); + return reply_params.result(); return PP_ERROR_FAILED; } diff --git a/ppapi/proxy/plugin_resource.h b/ppapi/proxy/plugin_resource.h index 2e2e10f..2363c8c 100644 --- a/ppapi/proxy/plugin_resource.h +++ b/ppapi/proxy/plugin_resource.h @@ -126,11 +126,6 @@ class PPAPI_PROXY_EXPORT PluginResource : public Resource { int32_t SyncCall( Destination dest, const IPC::Message& msg, A* a, B* b, C* c, D* d, E* e); - int32_t GenericSyncCall(Destination dest, - const IPC::Message& msg, - IPC::Message* reply_msg, - ResourceMessageReplyParams* reply_params); - private: IPC::Sender* GetSender(Destination dest) { return dest == RENDERER ? connection_.renderer_sender : @@ -143,6 +138,10 @@ class PPAPI_PROXY_EXPORT PluginResource : public Resource { const ResourceMessageCallParams& call_params, const IPC::Message& nested_msg); + int32_t GenericSyncCall(Destination dest, + const IPC::Message& msg, + IPC::Message* reply_msg); + int32_t GetNextSequence(); Connection connection_; @@ -178,16 +177,14 @@ int32_t PluginResource::Call(Destination dest, template <class ReplyMsgClass> int32_t PluginResource::SyncCall(Destination dest, const IPC::Message& msg) { IPC::Message reply; - ResourceMessageReplyParams reply_params; - return GenericSyncCall(dest, msg, &reply, &reply_params); + return GenericSyncCall(dest, msg, &reply); } template <class ReplyMsgClass, class A> int32_t PluginResource::SyncCall( Destination dest, const IPC::Message& msg, A* a) { IPC::Message reply; - ResourceMessageReplyParams reply_params; - int32_t result = GenericSyncCall(dest, msg, &reply, &reply_params); + int32_t result = GenericSyncCall(dest, msg, &reply); if (UnpackMessage<ReplyMsgClass>(reply, a)) return result; @@ -198,8 +195,7 @@ template <class ReplyMsgClass, class A, class B> int32_t PluginResource::SyncCall( Destination dest, const IPC::Message& msg, A* a, B* b) { IPC::Message reply; - ResourceMessageReplyParams reply_params; - int32_t result = GenericSyncCall(dest, msg, &reply, &reply_params); + int32_t result = GenericSyncCall(dest, msg, &reply); if (UnpackMessage<ReplyMsgClass>(reply, a, b)) return result; @@ -210,8 +206,7 @@ template <class ReplyMsgClass, class A, class B, class C> int32_t PluginResource::SyncCall( Destination dest, const IPC::Message& msg, A* a, B* b, C* c) { IPC::Message reply; - ResourceMessageReplyParams reply_params; - int32_t result = GenericSyncCall(dest, msg, &reply, &reply_params); + int32_t result = GenericSyncCall(dest, msg, &reply); if (UnpackMessage<ReplyMsgClass>(reply, a, b, c)) return result; @@ -222,8 +217,7 @@ template <class ReplyMsgClass, class A, class B, class C, class D> int32_t PluginResource::SyncCall( Destination dest, const IPC::Message& msg, A* a, B* b, C* c, D* d) { IPC::Message reply; - ResourceMessageReplyParams reply_params; - int32_t result = GenericSyncCall(dest, msg, &reply, &reply_params); + int32_t result = GenericSyncCall(dest, msg, &reply); if (UnpackMessage<ReplyMsgClass>(reply, a, b, c, d)) return result; @@ -234,8 +228,7 @@ template <class ReplyMsgClass, class A, class B, class C, class D, class E> int32_t PluginResource::SyncCall( Destination dest, const IPC::Message& msg, A* a, B* b, C* c, D* d, E* e) { IPC::Message reply; - ResourceMessageReplyParams reply_params; - int32_t result = GenericSyncCall(dest, msg, &reply, &reply_params); + int32_t result = GenericSyncCall(dest, msg, &reply); if (UnpackMessage<ReplyMsgClass>(reply, a, b, c, d, e)) return result; diff --git a/ppapi/proxy/ppapi_messages.h b/ppapi/proxy/ppapi_messages.h index b5e04de..959b93c 100644 --- a/ppapi/proxy/ppapi_messages.h +++ b/ppapi/proxy/ppapi_messages.h @@ -47,8 +47,6 @@ #include "ppapi/proxy/serialized_flash_menu.h" #include "ppapi/proxy/serialized_structs.h" #include "ppapi/proxy/serialized_var.h" -#include "ppapi/shared_impl/dir_contents.h" -#include "ppapi/shared_impl/file_path.h" #include "ppapi/shared_impl/ppapi_preferences.h" #include "ppapi/shared_impl/ppb_device_ref_shared.h" #include "ppapi/shared_impl/ppb_input_event_shared.h" @@ -164,11 +162,6 @@ IPC_STRUCT_TRAITS_BEGIN(ppapi::DeviceRefData) IPC_STRUCT_TRAITS_MEMBER(id) IPC_STRUCT_TRAITS_END() -IPC_STRUCT_TRAITS_BEGIN(ppapi::DirEntry) - IPC_STRUCT_TRAITS_MEMBER(name) - IPC_STRUCT_TRAITS_MEMBER(is_dir) -IPC_STRUCT_TRAITS_END() - IPC_STRUCT_TRAITS_BEGIN(ppapi::FlashSiteSetting) IPC_STRUCT_TRAITS_MEMBER(site) IPC_STRUCT_TRAITS_MEMBER(permission) @@ -1281,6 +1274,17 @@ IPC_SYNC_MESSAGE_ROUTED2_1(PpapiHostMsg_PPBFlash_IsRectTopmost, PP_Instance /* instance */, PP_Rect /* rect */, PP_Bool /* result */) +IPC_SYNC_MESSAGE_ROUTED3_2(PpapiHostMsg_PPBFlash_OpenFileRef, + PP_Instance /* instance */, + ppapi::HostResource /* file_ref */, + int32_t /* mode */, + IPC::PlatformFileForTransit /* file_handle */, + int32_t /* result */) +IPC_SYNC_MESSAGE_ROUTED2_2(PpapiHostMsg_PPBFlash_QueryFileRef, + PP_Instance /* instance */, + ppapi::HostResource /* file_ref */, + PP_FileInfo /* info */, + int32_t /* result */) IPC_SYNC_MESSAGE_ROUTED2_1(PpapiHostMsg_PPBFlash_GetSetting, PP_Instance /* instance */, PP_FlashSetting /* setting */, @@ -1635,29 +1639,6 @@ IPC_MESSAGE_CONTROL3(PpapiHostMsg_FlashClipboard_WriteData, std::vector<uint32_t> /* formats */, std::vector<std::string> /* data */) -// Flash file. -IPC_MESSAGE_CONTROL0(PpapiHostMsg_FlashFile_Create) -IPC_MESSAGE_CONTROL2(PpapiHostMsg_FlashFile_OpenFile, - ppapi::PepperFilePath /* path */, - int /* flags */) -IPC_MESSAGE_CONTROL2(PpapiHostMsg_FlashFile_RenameFile, - ppapi::PepperFilePath /* from_path */, - ppapi::PepperFilePath /* to_path */) -IPC_MESSAGE_CONTROL2(PpapiHostMsg_FlashFile_DeleteFileOrDir, - ppapi::PepperFilePath /* path */, - bool /* recursive */) -IPC_MESSAGE_CONTROL1(PpapiHostMsg_FlashFile_CreateDir, - ppapi::PepperFilePath /* path */) -IPC_MESSAGE_CONTROL1(PpapiHostMsg_FlashFile_QueryFile, - ppapi::PepperFilePath /* path */) -IPC_MESSAGE_CONTROL1(PpapiPluginMsg_FlashFile_QueryFileReply, - base::PlatformFileInfo /* file_info */) -IPC_MESSAGE_CONTROL1(PpapiHostMsg_FlashFile_GetDirContents, - ppapi::PepperFilePath /* path */) -IPC_MESSAGE_CONTROL1(PpapiPluginMsg_FlashFile_GetDirContentsReply, - ppapi::DirContents /* entries */) -IPC_MESSAGE_CONTROL0(PpapiHostMsg_FlashFile_CreateTemporaryFile) - // Flash font file. IPC_MESSAGE_CONTROL2(PpapiHostMsg_FlashFontFile_Create, ppapi::proxy::SerializedFontDescription /* description */, diff --git a/ppapi/proxy/ppapi_param_traits.cc b/ppapi/proxy/ppapi_param_traits.cc index ea792e6..763d05c 100644 --- a/ppapi/proxy/ppapi_param_traits.cc +++ b/ppapi/proxy/ppapi_param_traits.cc @@ -346,7 +346,6 @@ void ParamTraits<ppapi::proxy::SerializedHandle>::Write(Message* m, break; case ppapi::proxy::SerializedHandle::SOCKET: case ppapi::proxy::SerializedHandle::CHANNEL_HANDLE: - case ppapi::proxy::SerializedHandle::FILE: ParamTraits<IPC::PlatformFileForTransit>::Write(m, p.descriptor()); break; case ppapi::proxy::SerializedHandle::INVALID: @@ -387,14 +386,6 @@ bool ParamTraits<ppapi::proxy::SerializedHandle>::Read(const Message* m, } break; } - case ppapi::proxy::SerializedHandle::FILE: { - IPC::PlatformFileForTransit desc; - if (ParamTraits<IPC::PlatformFileForTransit>::Read(m, iter, &desc)) { - r->set_file_handle(desc); - return true; - } - break; - } case ppapi::proxy::SerializedHandle::INVALID: return true; // No default so the compiler will warn us if a new type is added. @@ -561,41 +552,6 @@ void ParamTraits<ppapi::proxy::SerializedFontDescription>::Log( std::string* l) { } -// ppapi::PepperFilePath ------------------------------------------------------- - -// static -void ParamTraits<ppapi::PepperFilePath>::Write(Message* m, - const param_type& p) { - WriteParam(m, static_cast<unsigned>(p.domain())); - WriteParam(m, p.path()); -} - -// static -bool ParamTraits<ppapi::PepperFilePath>::Read(const Message* m, - PickleIterator* iter, - param_type* p) { - unsigned domain; - FilePath path; - if (!ReadParam(m, iter, &domain) || !ReadParam(m, iter, &path)) - return false; - if (domain > ppapi::PepperFilePath::DOMAIN_MAX_VALID) - return false; - - *p = ppapi::PepperFilePath( - static_cast<ppapi::PepperFilePath::Domain>(domain), path); - return true; -} - -// static -void ParamTraits<ppapi::PepperFilePath>::Log(const param_type& p, - std::string* l) { - l->append("("); - LogParam(static_cast<unsigned>(p.domain()), l); - l->append(", "); - LogParam(p.path(), l); - l->append(")"); -} - // SerializedFlashMenu --------------------------------------------------------- // static diff --git a/ppapi/proxy/ppapi_param_traits.h b/ppapi/proxy/ppapi_param_traits.h index 7556e35..13f7351 100644 --- a/ppapi/proxy/ppapi_param_traits.h +++ b/ppapi/proxy/ppapi_param_traits.h @@ -14,7 +14,6 @@ #include "ppapi/c/pp_rect.h" #include "ppapi/c/pp_var.h" #include "ppapi/proxy/ppapi_proxy_export.h" -#include "ppapi/shared_impl/file_path.h" #include "ppapi/shared_impl/ppapi_permissions.h" #include "ppapi/shared_impl/ppb_file_ref_shared.h" @@ -167,14 +166,6 @@ struct PPAPI_PROXY_EXPORT ParamTraits<ppapi::PpapiPermissions> { }; #if !defined(OS_NACL) && !defined(NACL_WIN64) -template <> -struct ParamTraits<ppapi::PepperFilePath> { - typedef ppapi::PepperFilePath param_type; - static void Write(Message* m, const param_type& p); - static bool Read(const Message* m, PickleIterator* iter, param_type* p); - static void Log(const param_type& p, std::string* l); -}; - template<> struct PPAPI_PROXY_EXPORT ParamTraits<ppapi::proxy::SerializedFlashMenu> { typedef ppapi::proxy::SerializedFlashMenu param_type; diff --git a/ppapi/proxy/ppb_flash_proxy.cc b/ppapi/proxy/ppb_flash_proxy.cc index 919dd3a..4a9cd8f 100644 --- a/ppapi/proxy/ppb_flash_proxy.cc +++ b/ppapi/proxy/ppb_flash_proxy.cc @@ -19,11 +19,14 @@ #include "ppapi/c/private/ppb_flash.h" #include "ppapi/c/private/ppb_flash_print.h" #include "ppapi/proxy/host_dispatcher.h" +#include "ppapi/proxy/pepper_file_messages.h" #include "ppapi/proxy/plugin_dispatcher.h" #include "ppapi/proxy/plugin_globals.h" #include "ppapi/proxy/ppapi_messages.h" #include "ppapi/proxy/proxy_module.h" #include "ppapi/proxy/serialized_var.h" +#include "ppapi/shared_impl/dir_contents.h" +#include "ppapi/shared_impl/file_type_conversion.h" #include "ppapi/shared_impl/ppapi_globals.h" #include "ppapi/shared_impl/proxy_lock.h" #include "ppapi/shared_impl/resource.h" @@ -50,6 +53,19 @@ bool InSameMinute(PP_Time t1, PP_Time t2) { return floor(t1 / 60.0) == floor(t2 / 60.0); } +IPC::PlatformFileForTransit PlatformFileToPlatformFileForTransit( + Dispatcher* dispatcher, + int32_t* error, + base::PlatformFile file) { + if (*error != PP_OK) + return IPC::InvalidPlatformFileForTransit(); + IPC::PlatformFileForTransit out_handle = + dispatcher->ShareHandleWithRemote(file, true); + if (out_handle == IPC::InvalidPlatformFileForTransit()) + *error = PP_ERROR_NOACCESS; + return out_handle; +} + void InvokePrinting(PP_Instance instance) { ProxyAutoLock lock; @@ -95,6 +111,10 @@ bool PPB_Flash_Proxy::OnMessageReceived(const IPC::Message& msg) { OnHostMsgGetLocalTimeZoneOffset) IPC_MESSAGE_HANDLER(PpapiHostMsg_PPBFlash_IsRectTopmost, OnHostMsgIsRectTopmost) + IPC_MESSAGE_HANDLER(PpapiHostMsg_PPBFlash_OpenFileRef, + OnHostMsgOpenFileRef) + IPC_MESSAGE_HANDLER(PpapiHostMsg_PPBFlash_QueryFileRef, + OnHostMsgQueryFileRef) IPC_MESSAGE_HANDLER(PpapiHostMsg_PPBFlash_InvokePrinting, OnHostMsgInvokePrinting) IPC_MESSAGE_HANDLER(PpapiHostMsg_PPBFlash_GetSetting, @@ -260,6 +280,187 @@ PP_Var PPB_Flash_Proxy::GetSetting(PP_Instance instance, return PP_MakeUndefined(); } +bool PPB_Flash_Proxy::CreateThreadAdapterForInstance(PP_Instance instance) { + return true; +} + +void PPB_Flash_Proxy::ClearThreadAdapterForInstance(PP_Instance instance) { +} + +int32_t PPB_Flash_Proxy::OpenFile(PP_Instance, + const char* path, + int32_t mode, + PP_FileHandle* file) { + int flags = 0; + if (!path || + !ppapi::PepperFileOpenFlagsToPlatformFileFlags(mode, &flags) || + !file) + return PP_ERROR_BADARGUMENT; + + base::PlatformFileError error; + IPC::PlatformFileForTransit transit_file; + ppapi::PepperFilePath pepper_path(ppapi::PepperFilePath::DOMAIN_MODULE_LOCAL, + FilePath::FromUTF8Unsafe(path)); + + if (PluginGlobals::Get()->GetBrowserSender()->Send( + new PepperFileMsg_OpenFile(pepper_path, flags, + &error, &transit_file))) { + *file = IPC::PlatformFileForTransitToPlatformFile(transit_file); + } else { + *file = base::kInvalidPlatformFileValue; + error = base::PLATFORM_FILE_ERROR_FAILED; + } + + return ppapi::PlatformFileErrorToPepperError(error); +} + +int32_t PPB_Flash_Proxy::RenameFile(PP_Instance, + const char* from_path, + const char* to_path) { + base::PlatformFileError error = base::PLATFORM_FILE_ERROR_FAILED; + ppapi::PepperFilePath pepper_from(ppapi::PepperFilePath::DOMAIN_MODULE_LOCAL, + FilePath::FromUTF8Unsafe(from_path)); + ppapi::PepperFilePath pepper_to(ppapi::PepperFilePath::DOMAIN_MODULE_LOCAL, + FilePath::FromUTF8Unsafe(to_path)); + + PluginGlobals::Get()->GetBrowserSender()->Send( + new PepperFileMsg_RenameFile(pepper_from, pepper_to, &error)); + + return ppapi::PlatformFileErrorToPepperError(error); +} + +int32_t PPB_Flash_Proxy::DeleteFileOrDir(PP_Instance, + const char* path, + PP_Bool recursive) { + base::PlatformFileError error = base::PLATFORM_FILE_ERROR_FAILED; + ppapi::PepperFilePath pepper_path(ppapi::PepperFilePath::DOMAIN_MODULE_LOCAL, + FilePath::FromUTF8Unsafe(path)); + + PluginGlobals::Get()->GetBrowserSender()->Send( + new PepperFileMsg_DeleteFileOrDir(pepper_path, + PP_ToBool(recursive), + &error)); + + return ppapi::PlatformFileErrorToPepperError(error); +} + +int32_t PPB_Flash_Proxy::CreateDir(PP_Instance, const char* path) { + base::PlatformFileError error = base::PLATFORM_FILE_ERROR_FAILED; + ppapi::PepperFilePath pepper_path(ppapi::PepperFilePath::DOMAIN_MODULE_LOCAL, + FilePath::FromUTF8Unsafe(path)); + + PluginGlobals::Get()->GetBrowserSender()->Send( + new PepperFileMsg_CreateDir(pepper_path, &error)); + + return ppapi::PlatformFileErrorToPepperError(error); +} + +int32_t PPB_Flash_Proxy::QueryFile(PP_Instance, + const char* path, + PP_FileInfo* info) { + base::PlatformFileInfo file_info; + base::PlatformFileError error = base::PLATFORM_FILE_ERROR_FAILED; + ppapi::PepperFilePath pepper_path(ppapi::PepperFilePath::DOMAIN_MODULE_LOCAL, + FilePath::FromUTF8Unsafe(path)); + + PluginGlobals::Get()->GetBrowserSender()->Send( + new PepperFileMsg_QueryFile(pepper_path, &file_info, &error)); + + if (error == base::PLATFORM_FILE_OK) { + info->size = file_info.size; + info->creation_time = TimeToPPTime(file_info.creation_time); + info->last_access_time = TimeToPPTime(file_info.last_accessed); + info->last_modified_time = TimeToPPTime(file_info.last_modified); + info->system_type = PP_FILESYSTEMTYPE_EXTERNAL; + if (file_info.is_directory) + info->type = PP_FILETYPE_DIRECTORY; + else + info->type = PP_FILETYPE_REGULAR; + } + + return ppapi::PlatformFileErrorToPepperError(error); +} + +int32_t PPB_Flash_Proxy::GetDirContents(PP_Instance, + const char* path, + PP_DirContents_Dev** contents) { + ppapi::DirContents entries; + base::PlatformFileError error = base::PLATFORM_FILE_ERROR_FAILED; + ppapi::PepperFilePath pepper_path(ppapi::PepperFilePath::DOMAIN_MODULE_LOCAL, + FilePath::FromUTF8Unsafe(path)); + + PluginGlobals::Get()->GetBrowserSender()->Send( + new PepperFileMsg_GetDirContents(pepper_path, &entries, &error)); + + if (error == base::PLATFORM_FILE_OK) { + // Copy the serialized dir entries to the output struct. + *contents = new PP_DirContents_Dev; + (*contents)->count = static_cast<int32_t>(entries.size()); + (*contents)->entries = new PP_DirEntry_Dev[entries.size()]; + for (size_t i = 0; i < entries.size(); i++) { + const ppapi::DirEntry& source = entries[i]; + PP_DirEntry_Dev* dest = &(*contents)->entries[i]; + std::string name = source.name.AsUTF8Unsafe(); + char* name_copy = new char[name.size() + 1]; + memcpy(name_copy, name.c_str(), name.size() + 1); + dest->name = name_copy; + dest->is_dir = PP_FromBool(source.is_dir); + } + } + + return ppapi::PlatformFileErrorToPepperError(error); +} + +int32_t PPB_Flash_Proxy::CreateTemporaryFile(PP_Instance instance, + PP_FileHandle* file) { + if (!file) + return PP_ERROR_BADARGUMENT; + + base::PlatformFileError error; + IPC::PlatformFileForTransit transit_file; + + if (PluginGlobals::Get()->GetBrowserSender()->Send( + new PepperFileMsg_CreateTemporaryFile(&error, &transit_file))) { + *file = IPC::PlatformFileForTransitToPlatformFile(transit_file); + } else { + error = base::PLATFORM_FILE_ERROR_FAILED; + *file = base::kInvalidPlatformFileValue; + } + + return ppapi::PlatformFileErrorToPepperError(error); +} + +int32_t PPB_Flash_Proxy::OpenFileRef(PP_Instance instance, + PP_Resource file_ref_id, + int32_t mode, + PP_FileHandle* file) { + EnterResourceNoLock<thunk::PPB_FileRef_API> enter(file_ref_id, true); + if (enter.failed()) + return PP_ERROR_BADRESOURCE; + + int32_t result = PP_ERROR_FAILED; + IPC::PlatformFileForTransit transit; + dispatcher()->Send(new PpapiHostMsg_PPBFlash_OpenFileRef( + API_ID_PPB_FLASH, instance, enter.resource()->host_resource(), mode, + &transit, &result)); + *file = IPC::PlatformFileForTransitToPlatformFile(transit); + return result; +} + +int32_t PPB_Flash_Proxy::QueryFileRef(PP_Instance instance, + PP_Resource file_ref_id, + PP_FileInfo* info) { + EnterResourceNoLock<thunk::PPB_FileRef_API> enter(file_ref_id, true); + if (enter.failed()) + return PP_ERROR_BADRESOURCE; + + int32_t result = PP_ERROR_FAILED; + dispatcher()->Send(new PpapiHostMsg_PPBFlash_QueryFileRef( + API_ID_PPB_FLASH, instance, enter.resource()->host_resource(), info, + &result)); + return result; +} + void PPB_Flash_Proxy::OnHostMsgSetInstanceAlwaysOnTop(PP_Instance instance, PP_Bool on_top) { EnterInstanceNoLock enter(instance); @@ -350,6 +551,39 @@ void PPB_Flash_Proxy::OnHostMsgIsRectTopmost(PP_Instance instance, *result = PP_FALSE; } +void PPB_Flash_Proxy::OnHostMsgOpenFileRef( + PP_Instance instance, + const HostResource& host_resource, + int32_t mode, + IPC::PlatformFileForTransit* file_handle, + int32_t* result) { + EnterInstanceNoLock enter(instance); + if (enter.failed()) { + *result = PP_ERROR_BADARGUMENT; + return; + } + + base::PlatformFile file; + *result = enter.functions()->GetFlashAPI()->OpenFileRef( + instance, host_resource.host_resource(), mode, &file); + *file_handle = PlatformFileToPlatformFileForTransit(dispatcher(), + result, file); +} + +void PPB_Flash_Proxy::OnHostMsgQueryFileRef( + PP_Instance instance, + const HostResource& host_resource, + PP_FileInfo* info, + int32_t* result) { + EnterInstanceNoLock enter(instance); + if (enter.failed()) { + *result = PP_ERROR_BADARGUMENT; + return; + } + *result = enter.functions()->GetFlashAPI()->QueryFileRef( + instance, host_resource.host_resource(), info); +} + void PPB_Flash_Proxy::OnHostMsgGetSetting(PP_Instance instance, PP_FlashSetting setting, SerializedVarReturnValue id) { diff --git a/ppapi/proxy/ppb_flash_proxy.h b/ppapi/proxy/ppb_flash_proxy.h index 37f9175..6043d2c 100644 --- a/ppapi/proxy/ppb_flash_proxy.h +++ b/ppapi/proxy/ppb_flash_proxy.h @@ -6,8 +6,10 @@ #define PPAPI_PROXY_PPB_FLASH_PROXY_H_ #include <string> +#include <vector> #include "base/compiler_specific.h" +#include "ipc/ipc_platform_file.h" #include "ppapi/c/pp_bool.h" #include "ppapi/c/pp_instance.h" #include "ppapi/c/pp_module.h" @@ -16,7 +18,7 @@ #include "ppapi/proxy/interface_proxy.h" #include "ppapi/proxy/serialized_var.h" #include "ppapi/shared_impl/host_resource.h" -#include "ppapi/thunk/ppb_flash_api.h" +#include "ppapi/shared_impl/ppb_flash_shared.h" struct PPB_Flash_Print_1_0; @@ -35,7 +37,7 @@ class SerializedVarReturnValue; // implemented in the new-style resource proxy (see flash_resource.h). // TODO(raymes): All of these functions should be moved to the new-style proxy. //////////////////////////////////////////////////////////////////////////////// -class PPB_Flash_Proxy : public InterfaceProxy, public thunk::PPB_Flash_API { +class PPB_Flash_Proxy : public InterfaceProxy, public PPB_Flash_Shared { public: explicit PPB_Flash_Proxy(Dispatcher* dispatcher); virtual ~PPB_Flash_Proxy(); @@ -76,6 +78,34 @@ class PPB_Flash_Proxy : public InterfaceProxy, public thunk::PPB_Flash_API { const PP_Rect* rect) OVERRIDE; virtual PP_Var GetSetting(PP_Instance instance, PP_FlashSetting setting) OVERRIDE; + virtual bool CreateThreadAdapterForInstance(PP_Instance instance) OVERRIDE; + virtual void ClearThreadAdapterForInstance(PP_Instance instance) OVERRIDE; + virtual int32_t OpenFile(PP_Instance instance, + const char* path, + int32_t mode, + PP_FileHandle* file) OVERRIDE; + virtual int32_t RenameFile(PP_Instance instance, + const char* path_from, + const char* path_to) OVERRIDE; + virtual int32_t DeleteFileOrDir(PP_Instance instance, + const char* path, + PP_Bool recursive) OVERRIDE; + virtual int32_t CreateDir(PP_Instance instance, const char* path) OVERRIDE; + virtual int32_t QueryFile(PP_Instance instance, + const char* path, + PP_FileInfo* info) OVERRIDE; + virtual int32_t GetDirContents(PP_Instance instance, + const char* path, + PP_DirContents_Dev** contents) OVERRIDE; + virtual int32_t CreateTemporaryFile(PP_Instance instance, + PP_FileHandle* file) OVERRIDE; + virtual int32_t OpenFileRef(PP_Instance instance, + PP_Resource file_ref, + int32_t mode, + PP_FileHandle* file) OVERRIDE; + virtual int32_t QueryFileRef(PP_Instance instance, + PP_Resource file_ref, + PP_FileInfo* info) OVERRIDE; static const ApiID kApiID = API_ID_PPB_FLASH; @@ -96,6 +126,15 @@ class PPB_Flash_Proxy : public InterfaceProxy, public thunk::PPB_Flash_API { void OnHostMsgIsRectTopmost(PP_Instance instance, PP_Rect rect, PP_Bool* result); + void OnHostMsgOpenFileRef(PP_Instance instance, + const ppapi::HostResource& host_resource, + int32_t mode, + IPC::PlatformFileForTransit* file_handle, + int32_t* result); + void OnHostMsgQueryFileRef(PP_Instance instance, + const ppapi::HostResource& host_resource, + PP_FileInfo* info, + int32_t* result); void OnHostMsgGetSetting(PP_Instance instance, PP_FlashSetting setting, SerializedVarReturnValue result); diff --git a/ppapi/proxy/ppb_instance_proxy.cc b/ppapi/proxy/ppb_instance_proxy.cc index d81fb8e..4e32822 100644 --- a/ppapi/proxy/ppb_instance_proxy.cc +++ b/ppapi/proxy/ppb_instance_proxy.cc @@ -17,7 +17,6 @@ #include "ppapi/proxy/content_decryptor_private_serializer.h" #include "ppapi/proxy/enter_proxy.h" #include "ppapi/proxy/flash_clipboard_resource.h" -#include "ppapi/proxy/flash_file_resource.h" #include "ppapi/proxy/flash_fullscreen_resource.h" #include "ppapi/proxy/flash_resource.h" #include "ppapi/proxy/gamepad_resource.h" @@ -383,9 +382,6 @@ Resource* PPB_Instance_Proxy::GetSingletonResource(PP_Instance instance, case FLASH_CLIPBOARD_SINGLETON_ID: new_singleton = new FlashClipboardResource(connection, instance); break; - case FLASH_FILE_SINGLETON_ID: - new_singleton = new FlashFileResource(connection, instance); - break; case FLASH_FULLSCREEN_SINGLETON_ID: new_singleton = new FlashFullscreenResource(connection, instance); break; @@ -394,7 +390,6 @@ Resource* PPB_Instance_Proxy::GetSingletonResource(PP_Instance instance, break; #else case FLASH_CLIPBOARD_SINGLETON_ID: - case FLASH_FILE_SINGLETON_ID: case FLASH_FULLSCREEN_SINGLETON_ID: case FLASH_SINGLETON_ID: NOTREACHED(); diff --git a/ppapi/proxy/resource_message_params.cc b/ppapi/proxy/resource_message_params.cc index 49b6328..aaca8c9 100644 --- a/ppapi/proxy/resource_message_params.cc +++ b/ppapi/proxy/resource_message_params.cc @@ -91,17 +91,6 @@ bool ResourceMessageParams::TakeSocketHandleAtIndex( return true; } -bool ResourceMessageParams::TakeFileHandleAtIndex( - size_t index, - IPC::PlatformFileForTransit* handle) const { - SerializedHandle serialized = TakeHandleOfTypeAtIndex( - index, SerializedHandle::FILE); - if (!serialized.is_file()) - return false; - *handle = serialized.descriptor(); - return true; -} - void ResourceMessageParams::TakeAllSharedMemoryHandles( std::vector<base::SharedMemoryHandle>* handles) const { for (size_t i = 0; i < handles_->data().size(); ++i) { diff --git a/ppapi/proxy/resource_message_params.h b/ppapi/proxy/resource_message_params.h index 663d35e..d8e4e9d 100644 --- a/ppapi/proxy/resource_message_params.h +++ b/ppapi/proxy/resource_message_params.h @@ -38,8 +38,8 @@ class PPAPI_PROXY_EXPORT ResourceMessageParams { SerializedHandle TakeHandleOfTypeAtIndex(size_t index, SerializedHandle::Type type) const; - // Helper functions to return shared memory, socket or file handles passed in - // the params struct. + // Helper functions to return shared memory or socket handles passed in the + // params struct. // If the index has a valid handle of the given type, it will be placed in the // output parameter, the corresponding slot in the list will be set to an // invalid handle, and the function will return true. If the handle doesn't @@ -54,8 +54,6 @@ class PPAPI_PROXY_EXPORT ResourceMessageParams { base::SharedMemoryHandle* handle) const; bool TakeSocketHandleAtIndex(size_t index, IPC::PlatformFileForTransit* handle) const; - bool TakeFileHandleAtIndex(size_t index, - IPC::PlatformFileForTransit* handle) const; void TakeAllSharedMemoryHandles( std::vector<base::SharedMemoryHandle>* handles) const; diff --git a/ppapi/proxy/serialized_structs.cc b/ppapi/proxy/serialized_structs.cc index 2ddf325..f83ae0b 100644 --- a/ppapi/proxy/serialized_structs.cc +++ b/ppapi/proxy/serialized_structs.cc @@ -107,17 +107,10 @@ SerializedHandle::SerializedHandle( } bool SerializedHandle::IsHandleValid() const { - switch (type_) { - case SHARED_MEMORY: - return base::SharedMemory::IsHandleValid(shm_handle_); - case SOCKET: - case CHANNEL_HANDLE: - case FILE: - return !(IPC::InvalidPlatformFileForTransit() == descriptor_); - case INVALID: - return false; - // No default so the compiler will warn us if a new type is added. - } + if (type_ == SHARED_MEMORY) + return base::SharedMemory::IsHandleValid(shm_handle_); + else if (type_ == SOCKET || type_ == CHANNEL_HANDLE) + return !(IPC::InvalidPlatformFileForTransit() == descriptor_); return false; } @@ -132,7 +125,6 @@ void SerializedHandle::Close() { break; case SOCKET: case CHANNEL_HANDLE: - case FILE: base::PlatformFile file = IPC::PlatformFileForTransitToPlatformFile(descriptor_); #if !defined(OS_NACL) @@ -176,7 +168,6 @@ bool SerializedHandle::ReadHeader(PickleIterator* iter, Header* hdr) { } case SOCKET: case CHANNEL_HANDLE: - case FILE: case INVALID: valid_type = true; break; diff --git a/ppapi/proxy/serialized_structs.h b/ppapi/proxy/serialized_structs.h index def852f..d27b52c 100644 --- a/ppapi/proxy/serialized_structs.h +++ b/ppapi/proxy/serialized_structs.h @@ -85,7 +85,7 @@ struct PPBURLLoader_UpdateProgress_Params { // them in NaClIPCAdapter for use in NaCl. class PPAPI_PROXY_EXPORT SerializedHandle { public: - enum Type { INVALID, SHARED_MEMORY, SOCKET, CHANNEL_HANDLE, FILE }; + enum Type { INVALID, SHARED_MEMORY, SOCKET, CHANNEL_HANDLE }; struct Header { Header() : type(INVALID), size(0) {} Header(Type type_arg, uint32_t size_arg) @@ -102,7 +102,7 @@ class PPAPI_PROXY_EXPORT SerializedHandle { // Create a shared memory handle. SerializedHandle(const base::SharedMemoryHandle& handle, uint32_t size); - // Create a socket, channel or file handle. + // Create a socket or channel handle. SerializedHandle(const Type type, const IPC::PlatformFileForTransit& descriptor); @@ -110,7 +110,6 @@ class PPAPI_PROXY_EXPORT SerializedHandle { bool is_shmem() const { return type_ == SHARED_MEMORY; } bool is_socket() const { return type_ == SOCKET; } bool is_channel_handle() const { return type_ == CHANNEL_HANDLE; } - bool is_file() const { return type_ == FILE; } const base::SharedMemoryHandle& shmem() const { DCHECK(is_shmem()); return shm_handle_; @@ -120,7 +119,7 @@ class PPAPI_PROXY_EXPORT SerializedHandle { return size_; } const IPC::PlatformFileForTransit& descriptor() const { - DCHECK(is_socket() || is_channel_handle() || is_file()); + DCHECK(is_socket() || is_channel_handle()); return descriptor_; } void set_shmem(const base::SharedMemoryHandle& handle, uint32_t size) { @@ -144,13 +143,6 @@ class PPAPI_PROXY_EXPORT SerializedHandle { shm_handle_ = base::SharedMemory::NULLHandle(); size_ = 0; } - void set_file_handle(const IPC::PlatformFileForTransit& descriptor) { - type_ = FILE; - - descriptor_ = descriptor; - shm_handle_ = base::SharedMemory::NULLHandle(); - size_ = 0; - } void set_null_shmem() { set_shmem(base::SharedMemory::NULLHandle(), 0); } @@ -160,9 +152,6 @@ class PPAPI_PROXY_EXPORT SerializedHandle { void set_null_channel_handle() { set_channel_handle(IPC::InvalidPlatformFileForTransit()); } - void set_null_file_handle() { - set_file_handle(IPC::InvalidPlatformFileForTransit()); - } bool IsHandleValid() const; Header header() const { diff --git a/ppapi/shared_impl/file_path.cc b/ppapi/shared_impl/file_path.cc index 1502d89..1208b08 100644 --- a/ppapi/shared_impl/file_path.cc +++ b/ppapi/shared_impl/file_path.cc @@ -4,8 +4,26 @@ #include "ppapi/shared_impl/file_path.h" +#include <string> + +#if defined(OS_WIN) +#include "base/utf_string_conversions.h" +#endif + namespace ppapi { +namespace { + +FilePath GetFilePathFromUTF8(const std::string& utf8_path) { +#if defined(OS_WIN) + return FilePath(UTF8ToUTF16(utf8_path)); +#else + return FilePath(utf8_path); +#endif +} + +} // namespace + PepperFilePath::PepperFilePath() : domain_(DOMAIN_INVALID), path_() { @@ -17,4 +35,17 @@ PepperFilePath::PepperFilePath(Domain domain, const FilePath& path) // TODO(viettrungluu): Should we DCHECK() some things here? } +// static +PepperFilePath PepperFilePath::MakeAbsolute(const FilePath& path) { + return PepperFilePath(DOMAIN_ABSOLUTE, path); +} + +// static +PepperFilePath PepperFilePath::MakeModuleLocal(const std::string& name, + const char* utf8_path) { + FilePath full_path = GetFilePathFromUTF8(name).Append( + GetFilePathFromUTF8(utf8_path)); + return PepperFilePath(DOMAIN_MODULE_LOCAL, full_path); +} + } // namespace ppapi diff --git a/ppapi/shared_impl/file_path.h b/ppapi/shared_impl/file_path.h index 3d850f9..bcec9f8 100644 --- a/ppapi/shared_impl/file_path.h +++ b/ppapi/shared_impl/file_path.h @@ -5,6 +5,8 @@ #ifndef PPAPI_SHARED_IMPL_FILE_PATH_H_ #define PPAPI_SHARED_IMPL_FILE_PATH_H_ +#include <string> + #include "base/file_path.h" #include "ppapi/shared_impl/ppapi_shared_export.h" @@ -28,6 +30,10 @@ class PPAPI_SHARED_EXPORT PepperFilePath { PepperFilePath(); PepperFilePath(Domain d, const FilePath& p); + static PepperFilePath MakeAbsolute(const FilePath& path); + static PepperFilePath MakeModuleLocal(const std::string& name, + const char* utf8_path); + Domain domain() const { return domain_; } const FilePath& path() const { return path_; } diff --git a/ppapi/shared_impl/ppb_flash_shared.cc b/ppapi/shared_impl/ppb_flash_shared.cc new file mode 100644 index 0000000..c310e0e --- /dev/null +++ b/ppapi/shared_impl/ppb_flash_shared.cc @@ -0,0 +1,23 @@ +// Copyright (c) 2012 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 "ppapi/shared_impl/ppb_flash_shared.h" + +namespace ppapi { + +PPB_Flash_Shared::PPB_Flash_Shared() { +} + +PPB_Flash_Shared::~PPB_Flash_Shared() { +} + +void PPB_Flash_Shared::FreeDirContents(PP_Instance instance, + PP_DirContents_Dev* contents) { + for (int32_t i = 0; i < contents->count; ++i) + delete[] contents->entries[i].name; + delete[] contents->entries; + delete contents; +} + +} // namespace ppapi diff --git a/ppapi/shared_impl/ppb_flash_shared.h b/ppapi/shared_impl/ppb_flash_shared.h new file mode 100644 index 0000000..29f8973 --- /dev/null +++ b/ppapi/shared_impl/ppb_flash_shared.h @@ -0,0 +1,30 @@ +// Copyright (c) 2012 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 PPAPI_SHARED_IMPL_PPB_FLASH_SHARED_H_ +#define PPAPI_SHARED_IMPL_PPB_FLASH_SHARED_H_ + +#include "base/basictypes.h" +#include "base/compiler_specific.h" +#include "ppapi/shared_impl/ppapi_shared_export.h" +#include "ppapi/thunk/ppb_flash_api.h" + +namespace ppapi { + +class PPAPI_SHARED_EXPORT PPB_Flash_Shared : public thunk::PPB_Flash_API { + public: + PPB_Flash_Shared(); + virtual ~PPB_Flash_Shared(); + + // Shared implementation of PPB_Flash_API. + virtual void FreeDirContents(PP_Instance instance, + PP_DirContents_Dev* contents) OVERRIDE; + + private: + DISALLOW_COPY_AND_ASSIGN(PPB_Flash_Shared); +}; + +} // namespace ppapi + +#endif // PPAPI_SHARED_IMPL_PPB_FLASH_SHARED_H_ diff --git a/ppapi/shared_impl/resource.h b/ppapi/shared_impl/resource.h index 6c86868..dc1bf3f 100644 --- a/ppapi/shared_impl/resource.h +++ b/ppapi/shared_impl/resource.h @@ -36,7 +36,6 @@ F(PPB_Find_API) \ F(PPB_Flash_Clipboard_API) \ F(PPB_Flash_DeviceID_API) \ - F(PPB_Flash_File_API) \ F(PPB_Flash_FontFile_API) \ F(PPB_Flash_Fullscreen_API) \ F(PPB_Flash_Functions_API) \ diff --git a/ppapi/shared_impl/singleton_resource_id.h b/ppapi/shared_impl/singleton_resource_id.h index 442611a..9558db6 100644 --- a/ppapi/shared_impl/singleton_resource_id.h +++ b/ppapi/shared_impl/singleton_resource_id.h @@ -11,7 +11,6 @@ namespace ppapi { // PPB_Instance_API.GetSingletonResource. enum SingletonResourceID { FLASH_CLIPBOARD_SINGLETON_ID, - FLASH_FILE_SINGLETON_ID, FLASH_FULLSCREEN_SINGLETON_ID, FLASH_SINGLETON_ID, GAMEPAD_SINGLETON_ID, diff --git a/ppapi/tests/test_flash_file.cc b/ppapi/tests/test_flash_file.cc index 86100d9..ac88b34 100644 --- a/ppapi/tests/test_flash_file.cc +++ b/ppapi/tests/test_flash_file.cc @@ -4,11 +4,6 @@ #include "ppapi/tests/test_flash_file.h" -#include <algorithm> -#include <vector> - -#include "ppapi/c/pp_file_info.h" -#include "ppapi/c/ppb_file_io.h" #include "ppapi/cpp/module.h" #include "ppapi/cpp/private/flash_file.h" #include "ppapi/tests/testing_instance.h" @@ -79,18 +74,6 @@ bool ReadFile(PP_FileHandle file_handle, std::string* contents) { return result; } -bool DirEntryEqual(FileModuleLocal::DirEntry i, - FileModuleLocal::DirEntry j) { - return i.name == j.name && i.is_dir == j.is_dir; -} - -bool DirEntryLessThan(FileModuleLocal::DirEntry i, - FileModuleLocal::DirEntry j) { - if (i.name == j.name) - return i.is_dir < j.is_dir; - return i.name < j.name; -} - } // namespace REGISTER_TEST_CASE(FlashFile); @@ -107,204 +90,15 @@ bool TestFlashFile::Init() { } void TestFlashFile::RunTests(const std::string& filter) { - RUN_TEST(OpenFile, filter); - RUN_TEST(RenameFile, filter); - RUN_TEST(DeleteFileOrDir, filter); - RUN_TEST(CreateDir, filter); - RUN_TEST(QueryFile, filter); - RUN_TEST(GetDirContents, filter); RUN_TEST(CreateTemporaryFile, filter); } -void TestFlashFile::SetUp() { - // Clear out existing test data. - FileModuleLocal::DeleteFileOrDir(instance_, std::string(), true); +std::string TestFlashFile::TestCreateTemporaryFile() { + ASSERT_TRUE(FileModuleLocal::IsCreateTemporaryFileAvailable()); + // Make sure that the root directory exists. FileModuleLocal::CreateDir(instance_, std::string()); -} - -std::string TestFlashFile::TestOpenFile() { - SetUp(); - std::string filename = "abc.txt"; - PP_FileHandle file_handle = FileModuleLocal::OpenFile(instance_, - filename, - PP_FILEOPENFLAG_WRITE | - PP_FILEOPENFLAG_CREATE); - ASSERT_NE(PP_kInvalidFileHandle, file_handle); - - std::string contents = "This is file."; - std::string read_contents; - ASSERT_TRUE(WriteFile(file_handle, contents)); - ASSERT_FALSE(ReadFile(file_handle, &read_contents)); - CloseFileHandle(file_handle); - - file_handle = FileModuleLocal::OpenFile(instance_, - filename, - PP_FILEOPENFLAG_READ); - ASSERT_NE(PP_kInvalidFileHandle, file_handle); - - ASSERT_FALSE(WriteFile(file_handle, contents)); - ASSERT_TRUE(ReadFile(file_handle, &read_contents)); - ASSERT_EQ(contents, read_contents); - CloseFileHandle(file_handle); - - PASS(); -} - -std::string TestFlashFile::TestRenameFile() { - SetUp(); - std::string filename = "abc.txt"; - std::string new_filename = "abc_new.txt"; - std::string contents = "This is file."; - std::string read_contents; - - PP_FileHandle file_handle = FileModuleLocal::OpenFile(instance_, - filename, - PP_FILEOPENFLAG_WRITE | - PP_FILEOPENFLAG_CREATE); - ASSERT_NE(PP_kInvalidFileHandle, file_handle); - ASSERT_TRUE(WriteFile(file_handle, contents)); - CloseFileHandle(file_handle); - - ASSERT_TRUE(FileModuleLocal::RenameFile(instance_, filename, new_filename)); - - file_handle = FileModuleLocal::OpenFile(instance_, - new_filename, - PP_FILEOPENFLAG_READ); - ASSERT_NE(PP_kInvalidFileHandle, file_handle); - ASSERT_TRUE(ReadFile(file_handle, &read_contents)); - ASSERT_EQ(contents, read_contents); - CloseFileHandle(file_handle); - - // Check that the old file no longer exists. - PP_FileInfo unused; - ASSERT_FALSE(FileModuleLocal::QueryFile(instance_, filename, &unused)); - - PASS(); -} -std::string TestFlashFile::TestDeleteFileOrDir() { - SetUp(); - std::string filename = "abc.txt"; - std::string dirname = "def"; - std::string contents = "This is file."; - - // Test file deletion. - PP_FileHandle file_handle = FileModuleLocal::OpenFile(instance_, - filename, - PP_FILEOPENFLAG_WRITE | - PP_FILEOPENFLAG_CREATE); - ASSERT_NE(PP_kInvalidFileHandle, file_handle); - ASSERT_TRUE(WriteFile(file_handle, contents)); - CloseFileHandle(file_handle); - ASSERT_TRUE(FileModuleLocal::DeleteFileOrDir(instance_, filename, false)); - PP_FileInfo unused; - ASSERT_FALSE(FileModuleLocal::QueryFile(instance_, filename, &unused)); - - // Test directory deletion. - ASSERT_TRUE(FileModuleLocal::CreateDir(instance_, dirname)); - ASSERT_TRUE(FileModuleLocal::DeleteFileOrDir(instance_, dirname, false)); - ASSERT_FALSE(FileModuleLocal::QueryFile(instance_, dirname, &unused)); - - // Test recursive directory deletion. - ASSERT_TRUE(FileModuleLocal::CreateDir(instance_, dirname)); - file_handle = FileModuleLocal::OpenFile( - instance_, dirname + "/" + filename, - PP_FILEOPENFLAG_WRITE | PP_FILEOPENFLAG_CREATE); - ASSERT_NE(PP_kInvalidFileHandle, file_handle); - ASSERT_TRUE(WriteFile(file_handle, contents)); - CloseFileHandle(file_handle); - ASSERT_FALSE(FileModuleLocal::DeleteFileOrDir(instance_, dirname, false)); - ASSERT_TRUE(FileModuleLocal::DeleteFileOrDir(instance_, dirname, true)); - ASSERT_FALSE(FileModuleLocal::QueryFile(instance_, filename, &unused)); - - PASS(); -} - -std::string TestFlashFile::TestCreateDir() { - SetUp(); - std::string dirname = "abc"; - PP_FileInfo info; - ASSERT_FALSE(FileModuleLocal::QueryFile(instance_, dirname, &info)); - ASSERT_TRUE(FileModuleLocal::CreateDir(instance_, dirname)); - ASSERT_TRUE(FileModuleLocal::QueryFile(instance_, dirname, &info)); - ASSERT_EQ(info.type, PP_FILETYPE_DIRECTORY); - - PASS(); -} - -std::string TestFlashFile::TestQueryFile() { - std::string filename = "abc.txt"; - std::string dirname = "def"; - std::string contents = "This is file."; - PP_FileInfo info; - - // Test querying a file. - PP_FileHandle file_handle = FileModuleLocal::OpenFile(instance_, - filename, - PP_FILEOPENFLAG_WRITE | - PP_FILEOPENFLAG_CREATE); - ASSERT_NE(PP_kInvalidFileHandle, file_handle); - ASSERT_TRUE(WriteFile(file_handle, contents)); - CloseFileHandle(file_handle); - ASSERT_TRUE(FileModuleLocal::QueryFile(instance_, filename, &info)); - ASSERT_EQ(static_cast<size_t>(info.size), contents.size()); - ASSERT_EQ(info.type, PP_FILETYPE_REGULAR); - // TODO(raymes): Test the other fields. - - // Test querying a directory. - ASSERT_TRUE(FileModuleLocal::CreateDir(instance_, dirname)); - ASSERT_TRUE(FileModuleLocal::QueryFile(instance_, dirname, &info)); - ASSERT_EQ(info.type, PP_FILETYPE_DIRECTORY); - // TODO(raymes): Test the other fields. - - // Test querying a non-existent file. - ASSERT_FALSE(FileModuleLocal::QueryFile(instance_, "xx", &info)); - - PASS(); -} - -std::string TestFlashFile::TestGetDirContents() { - SetUp(); - std::vector<FileModuleLocal::DirEntry> result; - ASSERT_TRUE(FileModuleLocal::GetDirContents(instance_, std::string(), - &result)); - ASSERT_EQ(result.size(), 1); - ASSERT_EQ(result[0].name, ".."); - ASSERT_EQ(result[0].is_dir, true); - - std::string filename = "abc.txt"; - std::string dirname = "def"; - std::string contents = "This is file."; - PP_FileHandle file_handle = FileModuleLocal::OpenFile(instance_, - filename, - PP_FILEOPENFLAG_WRITE | - PP_FILEOPENFLAG_CREATE); - ASSERT_NE(PP_kInvalidFileHandle, file_handle); - ASSERT_TRUE(WriteFile(file_handle, contents)); - CloseFileHandle(file_handle); - ASSERT_TRUE(FileModuleLocal::CreateDir(instance_, dirname)); - - ASSERT_TRUE(FileModuleLocal::GetDirContents(instance_, "", &result)); - FileModuleLocal::DirEntry expected[] = - { {"..", true}, - {filename, false}, - {dirname, true} - }; - size_t expected_size = sizeof(expected) / sizeof(expected[0]); - - std::sort(expected, expected + expected_size, DirEntryLessThan); - std::sort(result.begin(), result.end(), DirEntryLessThan); - - ASSERT_EQ(expected_size, result.size()); - ASSERT_TRUE(std::equal(expected, expected + expected_size, result.begin(), - DirEntryEqual)); - - PASS(); -} - -std::string TestFlashFile::TestCreateTemporaryFile() { - SetUp(); size_t before_create = 0; ASSERT_SUBTEST_SUCCESS(GetItemCountUnderModuleLocalRoot(&before_create)); diff --git a/ppapi/tests/test_flash_file.h b/ppapi/tests/test_flash_file.h index 86055db..b58890d 100644 --- a/ppapi/tests/test_flash_file.h +++ b/ppapi/tests/test_flash_file.h @@ -19,21 +19,10 @@ class TestFlashFile: public TestCase { virtual void RunTests(const std::string& filter); private: - // TODO(raymes): We should have SetUp/TearDown methods for ppapi tests. - void SetUp(); - - std::string TestOpenFile(); - std::string TestRenameFile(); - std::string TestDeleteFileOrDir(); - std::string TestCreateDir(); - std::string TestQueryFile(); - std::string TestGetDirContents(); + // TODO(yzshen): Add more test cases for PPB_Flash_File_ModuleLocal and + // PPB_Flash_File_FileRef. std::string TestCreateTemporaryFile(); - // TODO(raymes): Add these when we can test file chooser properly. - // std::string TestOpenFileRef(); - // std::string TestQueryFileRef(); - // Gets the number of files and directories under the module-local root // directory. std::string GetItemCountUnderModuleLocalRoot(size_t* item_count); diff --git a/ppapi/thunk/ppb_file_ref_api.h b/ppapi/thunk/ppb_file_ref_api.h index 0f9bbaa..ed46098 100644 --- a/ppapi/thunk/ppb_file_ref_api.h +++ b/ppapi/thunk/ppb_file_ref_api.h @@ -33,7 +33,7 @@ class PPAPI_THUNK_EXPORT PPB_FileRef_API { virtual int32_t Rename(PP_Resource new_file_ref, scoped_refptr<TrackedCallback> callback) = 0; - // Internal function for use in proxying. Returns the internal CreateInfo + // Intermal function for use in proxying. Returns the internal CreateInfo // (the contained resource does not carry a ref on behalf of the caller). virtual const PPB_FileRef_CreateInfo& GetCreateInfo() const = 0; diff --git a/ppapi/thunk/ppb_flash_api.h b/ppapi/thunk/ppb_flash_api.h index b787e1d..fad0600 100644 --- a/ppapi/thunk/ppb_flash_api.h +++ b/ppapi/thunk/ppb_flash_api.h @@ -56,6 +56,40 @@ class PPAPI_THUNK_EXPORT PPB_Flash_API { virtual double GetLocalTimeZoneOffset(PP_Instance instance, PP_Time t) = 0; virtual PP_Bool IsRectTopmost(PP_Instance instance, const PP_Rect* rect) = 0; virtual PP_Var GetSetting(PP_Instance instance, PP_FlashSetting setting) = 0; + + // FlashFile_ModuleLocal. + virtual bool CreateThreadAdapterForInstance(PP_Instance instance) = 0; + virtual void ClearThreadAdapterForInstance(PP_Instance instance) = 0; + virtual int32_t OpenFile(PP_Instance instance, + const char* path, + int32_t mode, + PP_FileHandle* file) = 0; + virtual int32_t RenameFile(PP_Instance instance, + const char* path_from, + const char* path_to) = 0; + virtual int32_t DeleteFileOrDir(PP_Instance instance, + const char* path, + PP_Bool recursive) = 0; + virtual int32_t CreateDir(PP_Instance instance, const char* path) = 0; + virtual int32_t QueryFile(PP_Instance instance, + const char* path, + PP_FileInfo* info) = 0; + virtual int32_t GetDirContents(PP_Instance instance, + const char* path, + PP_DirContents_Dev** contents) = 0; + virtual void FreeDirContents(PP_Instance instance, + PP_DirContents_Dev* contents) = 0; + virtual int32_t CreateTemporaryFile(PP_Instance instance, + PP_FileHandle* file) = 0; + + // FlashFile_FileRef. + virtual int32_t OpenFileRef(PP_Instance instance, + PP_Resource file_ref, + int32_t mode, + PP_FileHandle* file) = 0; + virtual int32_t QueryFileRef(PP_Instance instance, + PP_Resource file_ref, + PP_FileInfo* info) = 0; }; } // namespace thunk diff --git a/ppapi/thunk/ppb_flash_file_api.h b/ppapi/thunk/ppb_flash_file_api.h deleted file mode 100644 index d757253..0000000 --- a/ppapi/thunk/ppb_flash_file_api.h +++ /dev/null @@ -1,63 +0,0 @@ -// Copyright (c) 2012 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 PPAPI_THUNK_PPB_FLASH_FILE_API_H_ -#define PPAPI_THUNK_PPB_FLASH_FILE_API_H_ - -#include "ppapi/c/pp_bool.h" -#include "ppapi/c/pp_stdint.h" -#include "ppapi/c/private/pp_file_handle.h" -#include "ppapi/c/private/ppb_flash_file.h" -#include "ppapi/shared_impl/singleton_resource_id.h" -#include "ppapi/thunk/ppapi_thunk_export.h" - -struct PP_FileInfo; - -namespace ppapi { -namespace thunk { - -class PPAPI_THUNK_EXPORT PPB_Flash_File_API { - public: - virtual ~PPB_Flash_File_API() {} - - // FlashFile_ModuleLocal. - virtual int32_t OpenFile(PP_Instance instance, - const char* path, - int32_t mode, - PP_FileHandle* file) = 0; - virtual int32_t RenameFile(PP_Instance instance, - const char* path_from, - const char* path_to) = 0; - virtual int32_t DeleteFileOrDir(PP_Instance instance, - const char* path, - PP_Bool recursive) = 0; - virtual int32_t CreateDir(PP_Instance instance, const char* path) = 0; - virtual int32_t QueryFile(PP_Instance instance, - const char* path, - PP_FileInfo* info) = 0; - virtual int32_t GetDirContents(PP_Instance instance, - const char* path, - PP_DirContents_Dev** contents) = 0; - virtual void FreeDirContents(PP_Instance instance, - PP_DirContents_Dev* contents) = 0; - virtual int32_t CreateTemporaryFile(PP_Instance instance, - PP_FileHandle* file) = 0; - - // FlashFile_FileRef. - virtual int32_t OpenFileRef(PP_Instance instance, - PP_Resource file_ref, - int32_t mode, - PP_FileHandle* file) = 0; - virtual int32_t QueryFileRef(PP_Instance instance, - PP_Resource file_ref, - PP_FileInfo* info) = 0; - - static const SingletonResourceID kSingletonResourceID = - FLASH_FILE_SINGLETON_ID; -}; - -} // namespace thunk -} // namespace ppapi - -#endif // PPAPI_THUNK_PPB_FLASH_FILE_API_H_ diff --git a/ppapi/thunk/ppb_flash_file_fileref_thunk.cc b/ppapi/thunk/ppb_flash_file_fileref_thunk.cc index 8ea0f24..2b380c7 100644 --- a/ppapi/thunk/ppb_flash_file_fileref_thunk.cc +++ b/ppapi/thunk/ppb_flash_file_fileref_thunk.cc @@ -6,7 +6,8 @@ #include "ppapi/c/private/ppb_flash_file.h" #include "ppapi/thunk/enter.h" #include "ppapi/thunk/ppb_file_ref_api.h" -#include "ppapi/thunk/ppb_flash_file_api.h" +#include "ppapi/thunk/ppb_flash_api.h" +#include "ppapi/thunk/ppb_instance_api.h" #include "ppapi/thunk/thunk.h" namespace ppapi { @@ -26,20 +27,22 @@ int32_t OpenFile(PP_Resource file_ref_id, int32_t mode, PP_FileHandle* file) { // TODO(brettw): this function should take an instance. // To work around this, use the PP_Instance from the resource. PP_Instance instance = GetInstanceFromFileRef(file_ref_id); - EnterInstanceAPI<PPB_Flash_File_API> enter(instance); + EnterInstance enter(instance); if (enter.failed()) return PP_ERROR_BADARGUMENT; - return enter.functions()->OpenFileRef(instance, file_ref_id, mode, file); + return enter.functions()->GetFlashAPI()->OpenFileRef(instance, file_ref_id, + mode, file); } int32_t QueryFile(PP_Resource file_ref_id, struct PP_FileInfo* info) { // TODO(brettw): this function should take an instance. // To work around this, use the PP_Instance from the resource. PP_Instance instance = GetInstanceFromFileRef(file_ref_id); - EnterInstanceAPI<PPB_Flash_File_API> enter(instance); + EnterInstance enter(instance); if (enter.failed()) return PP_ERROR_BADARGUMENT; - return enter.functions()->QueryFileRef(instance, file_ref_id, info); + return enter.functions()->GetFlashAPI()->QueryFileRef(instance, file_ref_id, + info); } const PPB_Flash_File_FileRef g_ppb_flash_file_fileref_thunk = { diff --git a/ppapi/thunk/ppb_flash_file_modulelocal_thunk.cc b/ppapi/thunk/ppb_flash_file_modulelocal_thunk.cc index 03d9032..7e9678a 100644 --- a/ppapi/thunk/ppb_flash_file_modulelocal_thunk.cc +++ b/ppapi/thunk/ppb_flash_file_modulelocal_thunk.cc @@ -5,7 +5,8 @@ #include "ppapi/c/pp_errors.h" #include "ppapi/c/private/ppb_flash_file.h" #include "ppapi/thunk/enter.h" -#include "ppapi/thunk/ppb_flash_file_api.h" +#include "ppapi/thunk/ppb_flash_api.h" +#include "ppapi/thunk/ppb_instance_api.h" #include "ppapi/thunk/thunk.h" namespace ppapi { @@ -14,77 +15,89 @@ namespace thunk { namespace { bool CreateThreadAdapterForInstance(PP_Instance instance) { - return true; + EnterInstance enter(instance); + if (enter.failed()) + return false; + return enter.functions()->GetFlashAPI()->CreateThreadAdapterForInstance( + instance); } void ClearThreadAdapterForInstance(PP_Instance instance) { + EnterInstance enter(instance); + if (enter.succeeded()) { + return enter.functions()->GetFlashAPI()->ClearThreadAdapterForInstance( + instance); + } } int32_t OpenFile(PP_Instance instance, const char* path, int32_t mode, PP_FileHandle* file) { - EnterInstanceAPI<PPB_Flash_File_API> enter(instance); + EnterInstance enter(instance); if (enter.failed()) return PP_ERROR_BADARGUMENT; - return enter.functions()->OpenFile(instance, path, mode, file); + return enter.functions()->GetFlashAPI()->OpenFile(instance, path, mode, file); } int32_t RenameFile(PP_Instance instance, const char* path_from, const char* path_to) { - EnterInstanceAPI<PPB_Flash_File_API> enter(instance); + EnterInstance enter(instance); if (enter.failed()) return PP_ERROR_BADARGUMENT; - return enter.functions()->RenameFile(instance, path_from, path_to); + return enter.functions()->GetFlashAPI()->RenameFile(instance, + path_from, path_to); } int32_t DeleteFileOrDir(PP_Instance instance, const char* path, PP_Bool recursive) { - EnterInstanceAPI<PPB_Flash_File_API> enter(instance); + EnterInstance enter(instance); if (enter.failed()) return PP_ERROR_BADARGUMENT; - return enter.functions()->DeleteFileOrDir(instance, path, recursive); + return enter.functions()->GetFlashAPI()->DeleteFileOrDir(instance, path, + recursive); } int32_t CreateDir(PP_Instance instance, const char* path) { - EnterInstanceAPI<PPB_Flash_File_API> enter(instance); + EnterInstance enter(instance); if (enter.failed()) return PP_ERROR_BADARGUMENT; - return enter.functions()->CreateDir(instance, path); + return enter.functions()->GetFlashAPI()->CreateDir(instance, path); } int32_t QueryFile(PP_Instance instance, const char* path, PP_FileInfo* info) { - EnterInstanceAPI<PPB_Flash_File_API> enter(instance); + EnterInstance enter(instance); if (enter.failed()) return PP_ERROR_BADARGUMENT; - return enter.functions()->QueryFile(instance, path, info); + return enter.functions()->GetFlashAPI()->QueryFile(instance, path, info); } int32_t GetDirContents(PP_Instance instance, const char* path, PP_DirContents_Dev** contents) { - EnterInstanceAPI<PPB_Flash_File_API> enter(instance); + EnterInstance enter(instance); if (enter.failed()) return PP_ERROR_BADARGUMENT; - return enter.functions()->GetDirContents(instance, path, contents); + return enter.functions()->GetFlashAPI()->GetDirContents(instance, path, + contents); } void FreeDirContents(PP_Instance instance, PP_DirContents_Dev* contents) { - EnterInstanceAPI<PPB_Flash_File_API> enter(instance); + EnterInstance enter(instance); if (enter.succeeded()) - enter.functions()->FreeDirContents(instance, contents); + enter.functions()->GetFlashAPI()->FreeDirContents(instance, contents); } int32_t CreateTemporaryFile(PP_Instance instance, PP_FileHandle* file) { - EnterInstanceAPI<PPB_Flash_File_API> enter(instance); + EnterInstance enter(instance); if (enter.failed()) return PP_ERROR_BADARGUMENT; *file = PP_kInvalidFileHandle; - return enter.functions()->CreateTemporaryFile(instance, file); + return enter.functions()->GetFlashAPI()->CreateTemporaryFile(instance, file); } const PPB_Flash_File_ModuleLocal_2_0 g_ppb_flash_file_modulelocal_thunk_2_0 = { diff --git a/webkit/plugins/ppapi/mock_plugin_delegate.cc b/webkit/plugins/ppapi/mock_plugin_delegate.cc index eec48da..54947e7 100644 --- a/webkit/plugins/ppapi/mock_plugin_delegate.cc +++ b/webkit/plugins/ppapi/mock_plugin_delegate.cc @@ -220,6 +220,47 @@ void MockPluginDelegate::WillUpdateFile(const GURL& file_path) { void MockPluginDelegate::DidUpdateFile(const GURL& file_path, int64_t delta) { } +base::PlatformFileError MockPluginDelegate::OpenFile( + const ::ppapi::PepperFilePath& path, + int flags, + base::PlatformFile* file) { + return base::PLATFORM_FILE_ERROR_FAILED; +} + +base::PlatformFileError MockPluginDelegate::RenameFile( + const ::ppapi::PepperFilePath& from_path, + const ::ppapi::PepperFilePath& to_path) { + return base::PLATFORM_FILE_ERROR_FAILED; +} + +base::PlatformFileError MockPluginDelegate::DeleteFileOrDir( + const ::ppapi::PepperFilePath& path, + bool recursive) { + return base::PLATFORM_FILE_ERROR_FAILED; +} + +base::PlatformFileError MockPluginDelegate::CreateDir( + const ::ppapi::PepperFilePath& path) { + return base::PLATFORM_FILE_ERROR_FAILED; +} + +base::PlatformFileError MockPluginDelegate::QueryFile( + const ::ppapi::PepperFilePath& path, + base::PlatformFileInfo* info) { + return base::PLATFORM_FILE_ERROR_FAILED; +} + +base::PlatformFileError MockPluginDelegate::GetDirContents( + const ::ppapi::PepperFilePath& path, + ::ppapi::DirContents* contents) { + return base::PLATFORM_FILE_ERROR_FAILED; +} + +base::PlatformFileError MockPluginDelegate::CreateTemporaryFile( + base::PlatformFile* file) { + return base::PLATFORM_FILE_ERROR_FAILED; +} + void MockPluginDelegate::SyncGetFileSystemPlatformPath( const GURL& url, FilePath* platform_path) { diff --git a/webkit/plugins/ppapi/mock_plugin_delegate.h b/webkit/plugins/ppapi/mock_plugin_delegate.h index f2f3407..5ce5819 100644 --- a/webkit/plugins/ppapi/mock_plugin_delegate.h +++ b/webkit/plugins/ppapi/mock_plugin_delegate.h @@ -101,6 +101,26 @@ class MockPluginDelegate : public PluginDelegate { const AvailableSpaceCallback& callback); virtual void WillUpdateFile(const GURL& file_path); virtual void DidUpdateFile(const GURL& file_path, int64_t delta); + virtual base::PlatformFileError OpenFile( + const ::ppapi::PepperFilePath& path, + int flags, + base::PlatformFile* file); + virtual base::PlatformFileError RenameFile( + const ::ppapi::PepperFilePath& from_path, + const ::ppapi::PepperFilePath& to_path); + virtual base::PlatformFileError DeleteFileOrDir( + const ::ppapi::PepperFilePath& path, + bool recursive); + virtual base::PlatformFileError CreateDir( + const ::ppapi::PepperFilePath& path); + virtual base::PlatformFileError QueryFile( + const ::ppapi::PepperFilePath& path, + base::PlatformFileInfo* info); + virtual base::PlatformFileError GetDirContents( + const ::ppapi::PepperFilePath& path, + ::ppapi::DirContents* contents); + virtual base::PlatformFileError CreateTemporaryFile( + base::PlatformFile* file); virtual void SyncGetFileSystemPlatformPath(const GURL& url, FilePath* platform_path); virtual scoped_refptr<base::MessageLoopProxy> diff --git a/webkit/plugins/ppapi/plugin_delegate.h b/webkit/plugins/ppapi/plugin_delegate.h index 695b0f7..a3cbd89 100644 --- a/webkit/plugins/ppapi/plugin_delegate.h +++ b/webkit/plugins/ppapi/plugin_delegate.h @@ -507,6 +507,27 @@ class PluginDelegate { virtual void WillUpdateFile(const GURL& file_path) = 0; virtual void DidUpdateFile(const GURL& file_path, int64_t delta) = 0; + virtual base::PlatformFileError OpenFile( + const ::ppapi::PepperFilePath& path, + int flags, + base::PlatformFile* file) = 0; + virtual base::PlatformFileError RenameFile( + const ::ppapi::PepperFilePath& from_path, + const ::ppapi::PepperFilePath& to_path) = 0; + virtual base::PlatformFileError DeleteFileOrDir( + const ::ppapi::PepperFilePath& path, + bool recursive) = 0; + virtual base::PlatformFileError CreateDir( + const ::ppapi::PepperFilePath& path) = 0; + virtual base::PlatformFileError QueryFile( + const ::ppapi::PepperFilePath& path, + base::PlatformFileInfo* info) = 0; + virtual base::PlatformFileError GetDirContents( + const ::ppapi::PepperFilePath& path, + ::ppapi::DirContents* contents) = 0; + virtual base::PlatformFileError CreateTemporaryFile( + base::PlatformFile* file) = 0; + // Synchronously returns the platform file path for a filesystem URL. virtual void SyncGetFileSystemPlatformPath(const GURL& url, FilePath* platform_path) = 0; diff --git a/webkit/plugins/ppapi/ppapi_plugin_instance.cc b/webkit/plugins/ppapi/ppapi_plugin_instance.cc index 5bdacb0..3cae57c 100644 --- a/webkit/plugins/ppapi/ppapi_plugin_instance.cc +++ b/webkit/plugins/ppapi/ppapi_plugin_instance.cc @@ -2133,7 +2133,6 @@ PP_Bool PluginInstance::GetScreenSize(PP_Instance instance, PP_Size* size) { // Flash APIs aren't implemented in-process. switch (id) { case ::ppapi::FLASH_CLIPBOARD_SINGLETON_ID: - case ::ppapi::FLASH_FILE_SINGLETON_ID: case ::ppapi::FLASH_FULLSCREEN_SINGLETON_ID: case ::ppapi::FLASH_SINGLETON_ID: NOTIMPLEMENTED(); diff --git a/webkit/plugins/ppapi/ppb_flash_impl.cc b/webkit/plugins/ppapi/ppb_flash_impl.cc index f1f72ab..237caf3 100644 --- a/webkit/plugins/ppapi/ppb_flash_impl.cc +++ b/webkit/plugins/ppapi/ppb_flash_impl.cc @@ -7,12 +7,17 @@ #include <string> #include <vector> +#include "base/time.h" +#include "base/utf_string_conversions.h" #include "googleurl/src/gurl.h" #include "ppapi/c/dev/ppb_font_dev.h" #include "ppapi/c/private/ppb_flash.h" +#include "ppapi/shared_impl/file_path.h" +#include "ppapi/shared_impl/file_type_conversion.h" #include "ppapi/shared_impl/time_conversion.h" #include "ppapi/shared_impl/var.h" #include "ppapi/thunk/enter.h" +#include "ppapi/thunk/ppb_file_ref_api.h" #include "ppapi/thunk/ppb_image_data_api.h" #include "ppapi/thunk/ppb_url_request_info_api.h" #include "skia/ext/platform_canvas.h" @@ -31,12 +36,16 @@ #include "webkit/plugins/ppapi/plugin_delegate.h" #include "webkit/plugins/ppapi/plugin_module.h" #include "webkit/plugins/ppapi/ppapi_plugin_instance.h" +#include "webkit/plugins/ppapi/ppb_file_ref_impl.h" #include "webkit/plugins/ppapi/resource_helper.h" #include "webkit/plugins/ppapi/ppb_image_data_impl.h" using ppapi::PPTimeToTime; using ppapi::StringVar; +using ppapi::TimeToPPTime; +using ppapi::thunk::EnterResource; using ppapi::thunk::EnterResourceNoLock; +using ppapi::thunk::PPB_FileRef_API; using ppapi::thunk::PPB_ImageData_API; using ppapi::thunk::PPB_URLRequestInfo_API; @@ -204,5 +213,225 @@ PP_Var PPB_Flash_Impl::GetSetting(PP_Instance instance, } } +bool PPB_Flash_Impl::CreateThreadAdapterForInstance(PP_Instance instance) { + return false; // No multithreaded access allowed. +} + +void PPB_Flash_Impl::ClearThreadAdapterForInstance(PP_Instance instance) { +} + +int32_t PPB_Flash_Impl::OpenFile(PP_Instance pp_instance, + const char* path, + int32_t mode, + PP_FileHandle* file) { + int flags = 0; + if (!path || + !::ppapi::PepperFileOpenFlagsToPlatformFileFlags(mode, &flags) || + !file) + return PP_ERROR_BADARGUMENT; + + PluginInstance* instance = HostGlobals::Get()->GetInstance(pp_instance); + if (!instance) + return PP_ERROR_FAILED; + + base::PlatformFile base_file; + base::PlatformFileError result = instance->delegate()->OpenFile( + ::ppapi::PepperFilePath::MakeModuleLocal( + instance->module()->name(), path), + flags, + &base_file); + *file = base_file; + return ::ppapi::PlatformFileErrorToPepperError(result); +} + +int32_t PPB_Flash_Impl::RenameFile(PP_Instance pp_instance, + const char* path_from, + const char* path_to) { + if (!path_from || !path_to) + return PP_ERROR_BADARGUMENT; + + PluginInstance* instance = HostGlobals::Get()->GetInstance(pp_instance); + if (!instance) + return PP_ERROR_FAILED; + + base::PlatformFileError result = instance->delegate()->RenameFile( + ::ppapi::PepperFilePath::MakeModuleLocal( + instance->module()->name(), path_from), + ::ppapi::PepperFilePath::MakeModuleLocal( + instance->module()->name(), path_to)); + return ::ppapi::PlatformFileErrorToPepperError(result); +} + +int32_t PPB_Flash_Impl::DeleteFileOrDir(PP_Instance pp_instance, + const char* path, + PP_Bool recursive) { + if (!path) + return PP_ERROR_BADARGUMENT; + + PluginInstance* instance = HostGlobals::Get()->GetInstance(pp_instance); + if (!instance) + return PP_ERROR_FAILED; + + base::PlatformFileError result = instance->delegate()->DeleteFileOrDir( + ::ppapi::PepperFilePath::MakeModuleLocal( + instance->module()->name(), path), + PPBoolToBool(recursive)); + return ::ppapi::PlatformFileErrorToPepperError(result); +} + +int32_t PPB_Flash_Impl::CreateDir(PP_Instance pp_instance, const char* path) { + if (!path) + return PP_ERROR_BADARGUMENT; + + PluginInstance* instance = HostGlobals::Get()->GetInstance(pp_instance); + if (!instance) + return PP_ERROR_FAILED; + + base::PlatformFileError result = instance->delegate()->CreateDir( + ::ppapi::PepperFilePath::MakeModuleLocal( + instance->module()->name(), path)); + return ::ppapi::PlatformFileErrorToPepperError(result); +} + +int32_t PPB_Flash_Impl::QueryFile(PP_Instance pp_instance, + const char* path, + PP_FileInfo* info) { + if (!path || !info) + return PP_ERROR_BADARGUMENT; + + PluginInstance* instance = HostGlobals::Get()->GetInstance(pp_instance); + if (!instance) + return PP_ERROR_FAILED; + + base::PlatformFileInfo file_info; + base::PlatformFileError result = instance->delegate()->QueryFile( + ::ppapi::PepperFilePath::MakeModuleLocal( + instance->module()->name(), path), + &file_info); + if (result == base::PLATFORM_FILE_OK) { + info->size = file_info.size; + info->creation_time = TimeToPPTime(file_info.creation_time); + info->last_access_time = TimeToPPTime(file_info.last_accessed); + info->last_modified_time = TimeToPPTime(file_info.last_modified); + info->system_type = PP_FILESYSTEMTYPE_EXTERNAL; + if (file_info.is_directory) + info->type = PP_FILETYPE_DIRECTORY; + else + info->type = PP_FILETYPE_REGULAR; + } + return ::ppapi::PlatformFileErrorToPepperError(result); +} + +int32_t PPB_Flash_Impl::GetDirContents(PP_Instance pp_instance, + const char* path, + PP_DirContents_Dev** contents) { + if (!path || !contents) + return PP_ERROR_BADARGUMENT; + PluginInstance* instance = HostGlobals::Get()->GetInstance(pp_instance); + if (!instance) + return PP_ERROR_FAILED; + + *contents = NULL; + ::ppapi::DirContents pepper_contents; + base::PlatformFileError result = instance->delegate()->GetDirContents( + ::ppapi::PepperFilePath::MakeModuleLocal( + instance->module()->name(), path), + &pepper_contents); + + if (result != base::PLATFORM_FILE_OK) + return ::ppapi::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 = BoolToPPBool(pepper_contents[i].is_dir); + } + return PP_OK; +} + +int32_t PPB_Flash_Impl::CreateTemporaryFile(PP_Instance instance, + PP_FileHandle* file) { + if (!file) + return PP_ERROR_BADARGUMENT; + + PluginInstance* plugin_instance = HostGlobals::Get()->GetInstance(instance); + if (!plugin_instance) { + *file = PP_kInvalidFileHandle; + return PP_ERROR_FAILED; + } + + base::PlatformFileError result = + plugin_instance->delegate()->CreateTemporaryFile(file); + return ::ppapi::PlatformFileErrorToPepperError(result); +} + +int32_t PPB_Flash_Impl::OpenFileRef(PP_Instance pp_instance, + PP_Resource file_ref_id, + int32_t mode, + PP_FileHandle* file) { + int flags = 0; + if (!::ppapi::PepperFileOpenFlagsToPlatformFileFlags(mode, &flags) || !file) + return PP_ERROR_BADARGUMENT; + + EnterResourceNoLock<PPB_FileRef_API> enter(file_ref_id, true); + if (enter.failed()) + return PP_ERROR_BADRESOURCE; + PPB_FileRef_Impl* file_ref = static_cast<PPB_FileRef_Impl*>(enter.object()); + + PluginInstance* instance = HostGlobals::Get()->GetInstance(pp_instance); + if (!instance) + return PP_ERROR_FAILED; + + base::PlatformFile base_file; + base::PlatformFileError result = instance->delegate()->OpenFile( + ::ppapi::PepperFilePath::MakeAbsolute(file_ref->GetSystemPath()), + flags, + &base_file); + *file = base_file; + return ::ppapi::PlatformFileErrorToPepperError(result); +} + +int32_t PPB_Flash_Impl::QueryFileRef(PP_Instance pp_instance, + PP_Resource file_ref_id, + PP_FileInfo* info) { + EnterResource<PPB_FileRef_API> enter(file_ref_id, true); + if (enter.failed()) + return PP_ERROR_BADRESOURCE; + PPB_FileRef_Impl* file_ref = static_cast<PPB_FileRef_Impl*>(enter.object()); + + PluginInstance* instance = HostGlobals::Get()->GetInstance(pp_instance); + if (!instance) + return PP_ERROR_FAILED; + + base::PlatformFileInfo file_info; + base::PlatformFileError result = instance->delegate()->QueryFile( + ::ppapi::PepperFilePath::MakeAbsolute(file_ref->GetSystemPath()), + &file_info); + if (result == base::PLATFORM_FILE_OK) { + info->size = file_info.size; + info->creation_time = TimeToPPTime(file_info.creation_time); + info->last_access_time = TimeToPPTime(file_info.last_accessed); + info->last_modified_time = TimeToPPTime(file_info.last_modified); + info->system_type = PP_FILESYSTEMTYPE_EXTERNAL; + if (file_info.is_directory) + info->type = PP_FILETYPE_DIRECTORY; + else + info->type = PP_FILETYPE_REGULAR; + } + return ::ppapi::PlatformFileErrorToPepperError(result); +} + } // namespace ppapi } // namespace webkit diff --git a/webkit/plugins/ppapi/ppb_flash_impl.h b/webkit/plugins/ppapi/ppb_flash_impl.h index ad1871b..f13130c 100644 --- a/webkit/plugins/ppapi/ppb_flash_impl.h +++ b/webkit/plugins/ppapi/ppb_flash_impl.h @@ -9,14 +9,14 @@ #include "base/compiler_specific.h" #include "base/memory/scoped_ptr.h" #include "build/build_config.h" -#include "ppapi/thunk/ppb_flash_api.h" +#include "ppapi/shared_impl/ppb_flash_shared.h" namespace webkit { namespace ppapi { class PluginInstance; -class PPB_Flash_Impl : public ::ppapi::thunk::PPB_Flash_API { +class PPB_Flash_Impl : public ::ppapi::PPB_Flash_Shared { public: explicit PPB_Flash_Impl(PluginInstance* instance); virtual ~PPB_Flash_Impl(); @@ -49,6 +49,34 @@ class PPB_Flash_Impl : public ::ppapi::thunk::PPB_Flash_API { const PP_Rect* rect) OVERRIDE; virtual PP_Var GetSetting(PP_Instance instance, PP_FlashSetting setting) OVERRIDE; + virtual bool CreateThreadAdapterForInstance(PP_Instance instance) OVERRIDE; + virtual void ClearThreadAdapterForInstance(PP_Instance instance) OVERRIDE; + virtual int32_t OpenFile(PP_Instance instance, + const char* path, + int32_t mode, + PP_FileHandle* file) OVERRIDE; + virtual int32_t RenameFile(PP_Instance instance, + const char* path_from, + const char* path_to) OVERRIDE; + virtual int32_t DeleteFileOrDir(PP_Instance instance, + const char* path, + PP_Bool recursive) OVERRIDE; + virtual int32_t CreateDir(PP_Instance instance, const char* path) OVERRIDE; + virtual int32_t QueryFile(PP_Instance instance, + const char* path, + PP_FileInfo* info) OVERRIDE; + virtual int32_t GetDirContents(PP_Instance instance, + const char* path, + PP_DirContents_Dev** contents) OVERRIDE; + virtual int32_t CreateTemporaryFile(PP_Instance instance, + PP_FileHandle* file) OVERRIDE; + virtual int32_t OpenFileRef(PP_Instance instance, + PP_Resource file_ref, + int32_t mode, + PP_FileHandle* file) OVERRIDE; + virtual int32_t QueryFileRef(PP_Instance instance, + PP_Resource file_ref, + PP_FileInfo* info) OVERRIDE; private: PluginInstance* instance_; |