Commit ce3ea567 authored by wfh's avatar wfh Committed by Commit bot

Register system Pepper Flash plugin if no packaged Pepper plugin is found.

With the NPAPI deprecation, Adobe have now made a supported, automatically updating version of Pepper Flash available on Windows and OS X.

This CL moves the code previously added in https://codereview.chromium.org/203993004 into chrome/common so the system plugin is added on all Chromium builds.

To manually override bundled PepperFlash on Chrome (e.g. to load a Debug version), use --disable-bundled-ppapi-flash

BUG=345886,454131
TEST=Install PPAPI Flash from Adobe site (link in bug)
TEST=For Chromium builds: Check Chromium now automatically uses system version of Flash in chrome://plugins.
TEST=For Chrome builds: Check Chrome still uses bundled Flash by default.  Check if --disable-bundled-ppapi-flash it uses system flash.
TEST=Check an old version of System flash will pop out of date plugin warning.

Review URL: https://codereview.chromium.org/893823002

Cr-Commit-Position: refs/heads/master@{#317656}
parent e6f7a58b
......@@ -19,11 +19,6 @@ class ComponentUpdateService;
// The first part is IO intensive so we do it asynchronously in the file thread.
void RegisterPepperFlashComponent(ComponentUpdateService* cus);
// Returns true if this browser is compatible with the given Pepper Flash
// manifest, with the version specified in the manifest in |version_out|.
bool CheckPepperFlashManifest(const base::DictionaryValue& manifest,
base::Version* version_out);
} // namespace component_updater
#endif // CHROME_BROWSER_COMPONENT_UPDATER_FLASH_COMPONENT_INSTALLER_H_
......@@ -13,6 +13,7 @@
#include "base/version.h"
#include "build/build_config.h"
#include "chrome/common/chrome_paths.h"
#include "chrome/common/pepper_flash.h"
#include "content/public/test/test_browser_thread.h"
#include "ppapi/shared_impl/test_globals.h"
......@@ -81,7 +82,7 @@ TEST(ComponentInstallerTest, PepperFlashCheck) {
// This checks that the whole manifest is compatible.
Version version;
EXPECT_TRUE(CheckPepperFlashManifest(*root, &version));
EXPECT_TRUE(chrome::CheckPepperFlashManifest(*root, &version));
EXPECT_TRUE(version.IsValid());
}
......
......@@ -372,16 +372,24 @@ void PluginsDOMHandler::PluginsLoaded(
plugin_file->SetString("name", group_plugin.name);
// If this plugin is Pepper Flash, and the plugin path is the same as the
// path for the Pepper Flash Debugger plugin, then mark this plugin
// description as the debugger plugin to help the user disambiguate the
// path for the Pepper Flash System plugin, then mark this plugin
// description as the system plugin to help the user disambiguate the
// two plugins.
base::string16 desc = group_plugin.desc;
if (group_plugin.is_pepper_plugin() &&
group_plugin.name == base::ASCIIToUTF16(content::kFlashPluginName)) {
base::FilePath debug_path;
PathService::Get(chrome::DIR_PEPPER_FLASH_DEBUGGER_PLUGIN, &debug_path);
if (group_plugin.path.DirName() == debug_path)
base::FilePath system_path;
PathService::Get(chrome::DIR_PEPPER_FLASH_SYSTEM_PLUGIN, &system_path);
if (group_plugin.path.DirName() == system_path) {
#if defined(GOOGLE_CHROME_BUILD)
// Existing documentation for debugging Flash describe this plugin as
// "Debug" so preserve this nomenclature here.
desc += base::ASCIIToUTF16(" Debug");
#else
// On Chromium, we can name it what it really is; the system plugin.
desc += base::ASCIIToUTF16(" System");
#endif
}
}
plugin_file->SetString("description", desc);
......
......@@ -1897,8 +1897,6 @@
'browser/browsing_data/browsing_data_flash_lso_helper.h',
'browser/component_updater/flash_component_installer.h',
'browser/component_updater/pepper_flash_component_installer.cc',
'browser/component_updater/ppapi_utils.cc',
'browser/component_updater/ppapi_utils.h',
'browser/metrics/plugin_metrics_provider.cc',
'browser/metrics/plugin_metrics_provider.h',
'browser/pepper_broker_infobar_delegate.cc',
......
......@@ -416,6 +416,8 @@
'sources': [
'common/pepper_flash.cc',
'common/pepper_flash.h',
'common/ppapi_utils.cc',
'common/ppapi_utils.h',
],
}],
['enable_plugins==1 and enable_extensions==1', {
......
......@@ -208,6 +208,8 @@ static_library("common") {
sources += [
"pepper_flash.cc",
"pepper_flash.h",
"ppapi_utils.cc",
"ppapi_utils.h",
]
deps += [ "//third_party/adobe/flash:flapper_version_h" ]
}
......
......@@ -23,7 +23,9 @@ include_rules = [
"+google_apis/gaia", # For gaia_switches.h
"+grit", # For generated headers. TODO(thestig): Remove.
"+media",
"+ppapi/c",
"+ppapi/shared_impl",
"+ppapi/thunk",
# FIXME - refactor code and remove these dependencies
"+chrome/installer",
......
......@@ -7,6 +7,7 @@
#include "base/command_line.h"
#include "base/debug/crash_logging.h"
#include "base/files/file_util.h"
#include "base/json/json_reader.h"
#include "base/path_service.h"
#include "base/strings/string16.h"
#include "base/strings/string_number_conversions.h"
......@@ -16,10 +17,12 @@
#include "base/strings/utf_string_conversions.h"
#include "build/build_config.h"
#include "chrome/common/child_process_logging.h"
#include "chrome/common/chrome_constants.h"
#include "chrome/common/chrome_paths.h"
#include "chrome/common/chrome_switches.h"
#include "chrome/common/chrome_version_info.h"
#include "chrome/common/crash_keys.h"
#include "chrome/common/pepper_flash.h"
#include "chrome/common/render_messages.h"
#include "chrome/common/url_constants.h"
#include "chrome/grit/common_resources.h"
......@@ -314,7 +317,7 @@ content::PepperPluginInfo CreatePepperFlashInfo(const base::FilePath& path,
plugin.is_out_of_process = true;
plugin.name = content::kFlashPluginName;
plugin.path = path;
plugin.permissions = kPepperFlashPermissions;
plugin.permissions = chrome::kPepperFlashPermissions;
std::vector<std::string> flash_version_numbers;
base::SplitString(version, '.', &flash_version_numbers);
......@@ -387,7 +390,76 @@ bool GetBundledPepperFlash(content::PepperPluginInfo* plugin) {
return false;
#endif // FLAPPER_AVAILABLE
}
#endif // defined(ENABLE_PLUGINS)
#if defined(OS_WIN)
const char kPepperFlashDLLBaseName[] =
#if defined(ARCH_CPU_X86)
"pepflashplayer32_";
#elif defined(ARCH_CPU_X86_64)
"pepflashplayer64_";
#else
#error Unsupported Windows CPU architecture.
#endif // defined(ARCH_CPU_X86)
#endif // defined(OS_WIN)
bool GetSystemPepperFlash(content::PepperPluginInfo* plugin) {
base::CommandLine* command_line = base::CommandLine::ForCurrentProcess();
#if defined(FLAPPER_AVAILABLE)
// If flapper is available, only try system plugin if
// --disable-bundled-ppapi-flash is specified.
if (!command_line->HasSwitch(switches::kDisableBundledPpapiFlash))
return false;
#endif // defined(FLAPPER_AVAILABLE)
// Do not try and find System Pepper Flash if there is a specific path on
// the commmand-line.
if (command_line->HasSwitch(switches::kPpapiFlashPath))
return false;
base::FilePath flash_path;
if (!PathService::Get(chrome::DIR_PEPPER_FLASH_SYSTEM_PLUGIN, &flash_path))
return false;
if (!base::PathExists(flash_path))
return false;
base::FilePath manifest_path(flash_path.AppendASCII("manifest.json"));
std::string manifest_data;
if (!base::ReadFileToString(manifest_path, &manifest_data))
return false;
scoped_ptr<base::Value> manifest_value(
base::JSONReader::Read(manifest_data, base::JSON_ALLOW_TRAILING_COMMAS));
if (!manifest_value.get())
return false;
base::DictionaryValue* manifest = NULL;
if (!manifest_value->GetAsDictionary(&manifest))
return false;
Version version;
if (!chrome::CheckPepperFlashManifest(*manifest, &version))
return false;
#if defined(OS_WIN)
// PepperFlash DLLs on Windows look like basename_v_x_y_z.dll.
std::string filename(kPepperFlashDLLBaseName);
filename.append(version.GetString());
base::ReplaceChars(filename, ".", "_", &filename);
filename.append(".dll");
base::FilePath path(flash_path.Append(base::ASCIIToUTF16(filename)));
#else
// PepperFlash on OS X is called PepperFlashPlayer.plugin
base::FilePath path(flash_path.Append(chrome::kPepperFlashPluginFilename));
#endif
if (!base::PathExists(path))
return false;
*plugin = CreatePepperFlashInfo(path, version.GetString());
return true;
}
#endif // defined(ENABLE_PLUGINS)
std::string GetProduct() {
chrome::VersionInfo version_info;
......@@ -483,6 +555,8 @@ void ChromeContentClient::AddPepperPlugins(
content::PepperPluginInfo plugin;
if (GetBundledPepperFlash(&plugin))
plugins->push_back(plugin);
if (GetSystemPepperFlash(&plugin))
plugins->push_back(plugin);
#endif
}
......
......@@ -27,10 +27,20 @@
#include "base/mac/foundation_util.h"
#endif
#if defined(OS_WIN)
#include "base/win/registry.h"
#endif
#include "widevine_cdm_version.h" // In SHARED_INTERMEDIATE_DIR.
namespace {
#if defined(OS_WIN)
const wchar_t kFlashRegistryRoot[] = L"SOFTWARE\\Macromedia\\FlashPlayerPepper";
const wchar_t kFlashPlayerPathValueName[] = L"PlayerPath";
#endif
// File name of the internal Flash plugin on different platforms.
const base::FilePath::CharType kInternalFlashPluginFileName[] =
#if defined(OS_MACOSX)
......@@ -46,8 +56,11 @@ const base::FilePath::CharType kPepperFlashBaseDirectory[] =
FILE_PATH_LITERAL("PepperFlash");
#if defined(OS_WIN)
const base::FilePath::CharType kPepperFlashDebuggerBaseDirectory[] =
const base::FilePath::CharType kPepperFlashSystemBaseDirectory[] =
FILE_PATH_LITERAL("Macromed\\Flash");
#elif defined(OS_MACOSX)
const base::FilePath::CharType kPepperFlashSystemBaseDirectory[] =
FILE_PATH_LITERAL("Internet Plug-Ins/PepperFlashPlayer");
#endif
const base::FilePath::CharType kInternalNaClPluginFileName[] =
......@@ -104,6 +117,23 @@ bool GetInternalPluginsDirectory(base::FilePath* result) {
return PathService::Get(base::DIR_MODULE, result);
}
#if defined(OS_WIN)
// Gets the Flash path if installed on the system.
bool GetSystemFlashDirectory(base::FilePath* out_path) {
base::win::RegKey path_key(HKEY_LOCAL_MACHINE, kFlashRegistryRoot, KEY_READ);
base::string16 path_str;
if (FAILED(path_key.ReadValue(kFlashPlayerPathValueName, &path_str)))
return false;
base::FilePath plugin_path = base::FilePath(path_str).DirName();
if (!base::PathExists(plugin_path))
return false;
*out_path = plugin_path;
return true;
}
#endif
} // namespace
namespace chrome {
......@@ -261,16 +291,16 @@ bool PathProvider(int key, base::FilePath* result) {
return false;
cur = cur.Append(kPepperFlashBaseDirectory);
break;
case chrome::DIR_PEPPER_FLASH_DEBUGGER_PLUGIN:
case chrome::DIR_PEPPER_FLASH_SYSTEM_PLUGIN:
#if defined(OS_WIN)
if (!PathService::Get(base::DIR_SYSTEM, &cur))
if (!GetSystemFlashDirectory(&cur))
return false;
cur = cur.Append(kPepperFlashDebuggerBaseDirectory);
#elif defined(OS_MACOSX)
// TODO(luken): finalize Mac OS directory paths, current consensus is
// around /Library/Internet Plug-Ins/PepperFlashPlayer/
return false;
if (!GetLocalLibraryDirectory(&cur))
return false;
cur = cur.Append(kPepperFlashSystemBaseDirectory);
#else
// TODO(wfh): If Adobe release PPAPI binaries for Linux, add support here.
return false;
#endif
break;
......
......@@ -72,8 +72,9 @@ enum {
DIR_COMPONENT_UPDATED_PEPPER_FLASH_PLUGIN, // Base directory of the Pepper
// Flash plugins downloaded by the
// component updater.
DIR_PEPPER_FLASH_DEBUGGER_PLUGIN, // Base directory of the debugging version
// of the Pepper Flash plugin.
DIR_PEPPER_FLASH_SYSTEM_PLUGIN, // Base directory of the system version of
// the Pepper Flash plugin, downloadable
// from Adobe website.
FILE_RESOURCE_MODULE, // Full path and filename of the module that
// contains embedded resources (version,
// strings, images, etc.).
......
......@@ -2,12 +2,128 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#include "base/strings/string_split.h"
#include "base/values.h"
#include "base/version.h"
#include "chrome/common/pepper_flash.h"
#include "chrome/common/ppapi_utils.h"
#include "ppapi/c/private/ppb_pdf.h"
#include "ppapi/shared_impl/ppapi_permissions.h"
namespace chrome {
const int32 kPepperFlashPermissions = ppapi::PERMISSION_DEV |
ppapi::PERMISSION_PRIVATE |
ppapi::PERMISSION_BYPASS_USER_GESTURE |
ppapi::PERMISSION_FLASH;
namespace {
// File name of the Pepper Flash component manifest on different platforms.
const char kPepperFlashManifestName[] = "Flapper";
// Name of the Pepper Flash OS in the component manifest.
const char kPepperFlashOperatingSystem[] =
#if defined(OS_MACOSX)
"mac";
#elif defined(OS_WIN)
"win";
#else // OS_LINUX, etc. TODO(viettrungluu): Separate out Chrome OS and Android?
"linux";
#endif
// Name of the Pepper Flash architecture in the component manifest.
const char kPepperFlashArch[] =
#if defined(ARCH_CPU_X86)
"ia32";
#elif defined(ARCH_CPU_X86_64)
"x64";
#else // TODO(viettrungluu): Support an ARM check?
"???";
#endif
// Returns true if the Pepper |interface_name| is implemented by this browser.
// It does not check if the interface is proxied.
bool SupportsPepperInterface(const char* interface_name) {
if (IsSupportedPepperInterface(interface_name))
return true;
// The PDF interface is invisible to SupportsInterface() on the browser
// process because it is provided using PpapiInterfaceFactoryManager. We need
// to check for that as well.
// TODO(cpu): make this more sane.
return (strcmp(interface_name, PPB_PDF_INTERFACE) == 0);
}
// Returns true if this browser implements one of the interfaces given in
// |interface_string|, which is a '|'-separated string of interface names.
bool CheckPepperFlashInterfaceString(const std::string& interface_string) {
std::vector<std::string> interface_names;
base::SplitString(interface_string, '|', &interface_names);
for (size_t i = 0; i < interface_names.size(); i++) {
if (SupportsPepperInterface(interface_names[i].c_str()))
return true;
}
return false;
}
// Returns true if this browser implements all the interfaces that Flash
// specifies in its component installer manifest.
bool CheckPepperFlashInterfaces(const base::DictionaryValue& manifest) {
const base::ListValue* interface_list = NULL;
// We don't *require* an interface list, apparently.
if (!manifest.GetList("x-ppapi-required-interfaces", &interface_list))
return true;
for (size_t i = 0; i < interface_list->GetSize(); i++) {
std::string interface_string;
if (!interface_list->GetString(i, &interface_string))
return false;
if (!CheckPepperFlashInterfaceString(interface_string))
return false;
}
return true;
}
} // namespace
bool CheckPepperFlashManifest(const base::DictionaryValue& manifest,
Version* version_out) {
std::string name;
manifest.GetStringASCII("name", &name);
// TODO(viettrungluu): Support WinFlapper for now, while we change the format
// of the manifest. (Should be safe to remove checks for "WinFlapper" in, say,
// Nov. 2011.) crbug.com/98458
if (name != kPepperFlashManifestName && name != "WinFlapper")
return false;
std::string proposed_version;
manifest.GetStringASCII("version", &proposed_version);
Version version(proposed_version.c_str());
if (!version.IsValid())
return false;
if (!CheckPepperFlashInterfaces(manifest))
return false;
// TODO(viettrungluu): See above TODO.
if (name == "WinFlapper") {
*version_out = version;
return true;
}
std::string os;
manifest.GetStringASCII("x-ppapi-os", &os);
if (os != kPepperFlashOperatingSystem)
return false;
std::string arch;
manifest.GetStringASCII("x-ppapi-arch", &arch);
if (arch != kPepperFlashArch)
return false;
*version_out = version;
return true;
}
} // namespace chrome
......@@ -6,8 +6,17 @@
#define CHROME_COMMON_PEPPER_FLASH_H_
#include "base/basictypes.h"
#include "base/values.h"
#include "base/version.h"
namespace chrome {
// Permission bits for Pepper Flash.
extern const int32 kPepperFlashPermissions;
// Returns true if this browser is compatible with the given Pepper Flash
// manifest, with the version specified in the manifest in |version_out|.
bool CheckPepperFlashManifest(const base::DictionaryValue& manifest,
base::Version* version_out);
} // namespace chrome
#endif // CHROME_COMMON_PEPPER_FLASH_H_
// Copyright (c) 2013 The Chromium Authors. All rights reserved.
// Copyright (c) 2015 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 "chrome/browser/component_updater/ppapi_utils.h"
#include "chrome/common/ppapi_utils.h"
#include <cstring>
......
// Copyright (c) 2013 The Chromium Authors. All rights reserved.
// Copyright (c) 2015 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 CHROME_BROWSER_COMPONENT_UPDATER_PPAPI_UTILS_H_
#define CHROME_BROWSER_COMPONENT_UPDATER_PPAPI_UTILS_H_
#ifndef CHROME_COMMON_PPAPI_UTILS_H_
#define CHROME_COMMON_PPAPI_UTILS_H_
// Returns true if the interface name passed in is supported by the
// browser.
bool IsSupportedPepperInterface(const char* name);
#endif // CHROME_BROWSER_COMPONENT_UPDATER_PPAPI_UTILS_H_
#endif // CHROME_COMMON_PPAPI_UTILS_H_
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment