Home | History | Annotate | Download | only in pepper
      1 // Copyright (c) 2012 The Chromium Authors. All rights reserved.
      2 // Use of this source code is governed by a BSD-style license that can be
      3 // found in the LICENSE file.
      4 
      5 #include "chrome/browser/renderer_host/pepper/pepper_flash_browser_host.h"
      6 
      7 #include "base/time/time.h"
      8 #include "chrome/browser/content_settings/cookie_settings.h"
      9 #include "chrome/browser/profiles/profile.h"
     10 #include "content/public/browser/browser_context.h"
     11 #include "content/public/browser/browser_ppapi_host.h"
     12 #include "content/public/browser/browser_thread.h"
     13 #include "content/public/browser/render_process_host.h"
     14 #include "ipc/ipc_message_macros.h"
     15 #include "ppapi/c/pp_errors.h"
     16 #include "ppapi/c/private/ppb_flash.h"
     17 #include "ppapi/host/dispatch_host_message.h"
     18 #include "ppapi/proxy/ppapi_messages.h"
     19 #include "ppapi/proxy/resource_message_params.h"
     20 #include "ppapi/shared_impl/time_conversion.h"
     21 #include "url/gurl.h"
     22 
     23 #if defined(OS_WIN)
     24 #include <windows.h>
     25 #elif defined(OS_MACOSX)
     26 #include <CoreServices/CoreServices.h>
     27 #endif
     28 
     29 using content::BrowserPpapiHost;
     30 using content::BrowserThread;
     31 using content::RenderProcessHost;
     32 
     33 namespace chrome {
     34 
     35 namespace {
     36 
     37 // Get the CookieSettings on the UI thread for the given render process ID.
     38 scoped_refptr<CookieSettings> GetCookieSettings(int render_process_id) {
     39   DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI));
     40   RenderProcessHost* render_process_host = RenderProcessHost::FromID(
     41       render_process_id);
     42   if (render_process_host && render_process_host->GetBrowserContext()) {
     43     Profile* profile =
     44         Profile::FromBrowserContext(render_process_host->GetBrowserContext());
     45     return CookieSettings::Factory::GetForProfile(profile);
     46   }
     47   return NULL;
     48 }
     49 
     50 }  // namespace
     51 
     52 PepperFlashBrowserHost::PepperFlashBrowserHost(
     53     BrowserPpapiHost* host,
     54     PP_Instance instance,
     55     PP_Resource resource)
     56     : ResourceHost(host->GetPpapiHost(), instance, resource),
     57       host_(host),
     58       weak_factory_(this) {
     59   int unused;
     60   host->GetRenderViewIDsForInstance(instance, &render_process_id_, &unused);
     61 }
     62 
     63 PepperFlashBrowserHost::~PepperFlashBrowserHost() {
     64 }
     65 
     66 int32_t PepperFlashBrowserHost::OnResourceMessageReceived(
     67     const IPC::Message& msg,
     68     ppapi::host::HostMessageContext* context) {
     69   IPC_BEGIN_MESSAGE_MAP(PepperFlashBrowserHost, msg)
     70     PPAPI_DISPATCH_HOST_RESOURCE_CALL_0(PpapiHostMsg_Flash_UpdateActivity,
     71                                         OnUpdateActivity);
     72     PPAPI_DISPATCH_HOST_RESOURCE_CALL(PpapiHostMsg_Flash_GetLocalTimeZoneOffset,
     73                                       OnGetLocalTimeZoneOffset);
     74     PPAPI_DISPATCH_HOST_RESOURCE_CALL_0(
     75         PpapiHostMsg_Flash_GetLocalDataRestrictions,
     76         OnGetLocalDataRestrictions);
     77   IPC_END_MESSAGE_MAP()
     78   return PP_ERROR_FAILED;
     79 }
     80 
     81 int32_t PepperFlashBrowserHost::OnUpdateActivity(
     82     ppapi::host::HostMessageContext* host_context) {
     83 #if defined(OS_WIN)
     84   // Reading then writing back the same value to the screensaver timeout system
     85   // setting resets the countdown which prevents the screensaver from turning
     86   // on "for a while". As long as the plugin pings us with this message faster
     87   // than the screensaver timeout, it won't go on.
     88   int value = 0;
     89   if (SystemParametersInfo(SPI_GETSCREENSAVETIMEOUT, 0, &value, 0))
     90     SystemParametersInfo(SPI_SETSCREENSAVETIMEOUT, value, NULL, 0);
     91 #elif defined(OS_MACOSX)
     92   UpdateSystemActivity(OverallAct);
     93 #else
     94   // TODO(brettw) implement this for other platforms.
     95 #endif
     96   return PP_OK;
     97 }
     98 
     99 int32_t PepperFlashBrowserHost::OnGetLocalTimeZoneOffset(
    100     ppapi::host::HostMessageContext* host_context,
    101     const base::Time& t) {
    102   // The reason for this processing being in the browser process is that on
    103   // Linux, the localtime calls require filesystem access prohibited by the
    104   // sandbox.
    105   host_context->reply_msg = PpapiPluginMsg_Flash_GetLocalTimeZoneOffsetReply(
    106       ppapi::PPGetLocalTimeZoneOffset(t));
    107   return PP_OK;
    108 }
    109 
    110 int32_t PepperFlashBrowserHost::OnGetLocalDataRestrictions(
    111     ppapi::host::HostMessageContext* context) {
    112   // Getting the Flash LSO settings requires using the CookieSettings which
    113   // belong to the profile which lives on the UI thread. We lazily initialize
    114   // |cookie_settings_| by grabbing the reference from the UI thread and then
    115   // call |GetLocalDataRestrictions| with it.
    116   GURL document_url = host_->GetDocumentURLForInstance(pp_instance());
    117   GURL plugin_url = host_->GetPluginURLForInstance(pp_instance());
    118   if (cookie_settings_.get()) {
    119     GetLocalDataRestrictions(context->MakeReplyMessageContext(), document_url,
    120                              plugin_url, cookie_settings_);
    121   } else {
    122     BrowserThread::PostTaskAndReplyWithResult(BrowserThread::UI, FROM_HERE,
    123         base::Bind(&GetCookieSettings, render_process_id_),
    124         base::Bind(&PepperFlashBrowserHost::GetLocalDataRestrictions,
    125                    weak_factory_.GetWeakPtr(),
    126                    context->MakeReplyMessageContext(),
    127                    document_url, plugin_url));
    128   }
    129   return PP_OK_COMPLETIONPENDING;
    130 }
    131 
    132 void PepperFlashBrowserHost::GetLocalDataRestrictions(
    133     ppapi::host::ReplyMessageContext reply_context,
    134     const GURL& document_url,
    135     const GURL& plugin_url,
    136     scoped_refptr<CookieSettings> cookie_settings) {
    137   DCHECK(BrowserThread::CurrentlyOn(BrowserThread::IO));
    138 
    139   // Lazily initialize |cookie_settings_|. The cookie settings are thread-safe
    140   // ref-counted so as long as we hold a reference to them we can safely access
    141   // them on the IO thread.
    142   if (!cookie_settings_.get()) {
    143     cookie_settings_ = cookie_settings;
    144   } else {
    145     DCHECK(cookie_settings_.get() == cookie_settings.get());
    146   }
    147 
    148   PP_FlashLSORestrictions restrictions = PP_FLASHLSORESTRICTIONS_NONE;
    149   if (cookie_settings_.get() && document_url.is_valid() &&
    150       plugin_url.is_valid()) {
    151     if (!cookie_settings_->IsReadingCookieAllowed(document_url, plugin_url))
    152       restrictions = PP_FLASHLSORESTRICTIONS_BLOCK;
    153     else if (cookie_settings_->IsCookieSessionOnly(plugin_url))
    154       restrictions = PP_FLASHLSORESTRICTIONS_IN_MEMORY;
    155   }
    156   SendReply(reply_context, PpapiPluginMsg_Flash_GetLocalDataRestrictionsReply(
    157       static_cast<int32_t>(restrictions)));
    158 }
    159 
    160 }  // namespace chrome
    161