root/content/browser/renderer_host/pepper/pepper_file_ref_host.cc

/* [<][>][^][v][top][bottom][index][help] */

DEFINITIONS

This source file includes following definitions.
  1. fs_type_
  2. fs_type_
  3. IsFileRefHost
  4. GetFileSystemType
  5. GetFileSystemURL
  6. GetExternalFilePath
  7. GetFileSystemHost
  8. CanRead
  9. CanWrite
  10. CanCreate
  11. CanReadWrite
  12. OnResourceMessageReceived
  13. OnMakeDirectory
  14. OnTouch
  15. OnDelete
  16. OnRename
  17. OnQuery
  18. OnReadDirectoryEntries
  19. OnGetAbsolutePath

// Copyright 2013 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_ref_host.h"

#include <string>

#include "content/browser/renderer_host/pepper/pepper_external_file_ref_backend.h"
#include "content/browser/renderer_host/pepper/pepper_file_system_browser_host.h"
#include "content/browser/renderer_host/pepper/pepper_internal_file_ref_backend.h"
#include "ppapi/c/pp_errors.h"
#include "ppapi/c/pp_file_info.h"
#include "ppapi/c/pp_instance.h"
#include "ppapi/c/pp_resource.h"
#include "ppapi/host/dispatch_host_message.h"
#include "ppapi/host/ppapi_host.h"
#include "ppapi/proxy/ppapi_messages.h"
#include "ppapi/shared_impl/file_ref_util.h"
#include "webkit/browser/fileapi/file_permission_policy.h"

using ppapi::host::ResourceHost;

namespace content {

PepperFileRefBackend::~PepperFileRefBackend() {
}

PepperFileRefHost::PepperFileRefHost(BrowserPpapiHost* host,
                                     PP_Instance instance,
                                     PP_Resource resource,
                                     PP_Resource file_system,
                                     const std::string& path)
    : ResourceHost(host->GetPpapiHost(), instance, resource),
      host_(host),
      fs_type_(PP_FILESYSTEMTYPE_INVALID) {
  if (!ppapi::IsValidInternalPath(path))
    return;

  int render_process_id;
  int unused;
  if (!host->GetRenderFrameIDsForInstance(instance,
                                          &render_process_id,
                                          &unused)) {
    return;
  }

  ResourceHost* fs_resource_host =
      host->GetPpapiHost()->GetResourceHost(file_system);
  if (fs_resource_host == NULL) {
    DLOG(ERROR) << "Couldn't find FileSystem host: " << resource
                << " path: " << path;
    return;
  }

  if (!fs_resource_host->IsFileSystemHost()) {
    DLOG(ERROR) << "Filesystem PP_Resource is not PepperFileSystemBrowserHost";
    return;
  }

  PepperFileSystemBrowserHost* file_system_host =
      static_cast<PepperFileSystemBrowserHost*>(fs_resource_host);
  file_system_host_ = file_system_host->AsWeakPtr();
  fs_type_ = file_system_host->GetType();
  if ((fs_type_ != PP_FILESYSTEMTYPE_LOCALPERSISTENT) &&
      (fs_type_ != PP_FILESYSTEMTYPE_LOCALTEMPORARY) &&
      (fs_type_ != PP_FILESYSTEMTYPE_ISOLATED)) {
    DLOG(ERROR) << "Unsupported filesystem type: " << fs_type_;
    return;
  }

  backend_.reset(new PepperInternalFileRefBackend(
      host->GetPpapiHost(),
      render_process_id,
      file_system_host->AsWeakPtr(),
      path));
}

PepperFileRefHost::PepperFileRefHost(BrowserPpapiHost* host,
                                     PP_Instance instance,
                                     PP_Resource resource,
                                     const base::FilePath& external_path)
    : ResourceHost(host->GetPpapiHost(), instance, resource),
      host_(host),
      fs_type_(PP_FILESYSTEMTYPE_EXTERNAL) {
  if (!ppapi::IsValidExternalPath(external_path))
    return;

  int render_process_id;
  int unused;
  if (!host->GetRenderFrameIDsForInstance(instance,
                                          &render_process_id,
                                          &unused)) {
    return;
  }

  backend_.reset(new PepperExternalFileRefBackend(host->GetPpapiHost(),
                                                  render_process_id,
                                                  external_path));
}

PepperFileRefHost::~PepperFileRefHost() {
}

bool PepperFileRefHost::IsFileRefHost() {
  return true;
}

PP_FileSystemType PepperFileRefHost::GetFileSystemType() const {
  return fs_type_;
}

fileapi::FileSystemURL PepperFileRefHost::GetFileSystemURL() const {
  if (backend_)
    return backend_->GetFileSystemURL();
  return fileapi::FileSystemURL();
}

base::FilePath PepperFileRefHost::GetExternalFilePath() const {
  if (backend_)
    return backend_->GetExternalFilePath();
  return base::FilePath();
}

base::WeakPtr<PepperFileSystemBrowserHost>
PepperFileRefHost::GetFileSystemHost() const {
  return file_system_host_;
}

int32_t PepperFileRefHost::CanRead() const {
  if (backend_)
    return backend_->CanRead();
  return PP_ERROR_FAILED;
}

int32_t PepperFileRefHost::CanWrite() const {
  if (backend_)
    return backend_->CanWrite();
  return PP_ERROR_FAILED;
}

int32_t PepperFileRefHost::CanCreate() const {
  if (backend_)
    return backend_->CanCreate();
  return PP_ERROR_FAILED;
}

int32_t PepperFileRefHost::CanReadWrite() const {
  if (backend_)
    return backend_->CanReadWrite();
  return PP_ERROR_FAILED;
}

int32_t PepperFileRefHost::OnResourceMessageReceived(
    const IPC::Message& msg,
    ppapi::host::HostMessageContext* context) {
  if (!backend_)
    return PP_ERROR_FAILED;

  IPC_BEGIN_MESSAGE_MAP(PepperFileRefHost, msg)
    PPAPI_DISPATCH_HOST_RESOURCE_CALL(PpapiHostMsg_FileRef_MakeDirectory,
                                      OnMakeDirectory);
    PPAPI_DISPATCH_HOST_RESOURCE_CALL(PpapiHostMsg_FileRef_Touch,
                                      OnTouch);
    PPAPI_DISPATCH_HOST_RESOURCE_CALL_0(PpapiHostMsg_FileRef_Delete,
                                        OnDelete);
    PPAPI_DISPATCH_HOST_RESOURCE_CALL(PpapiHostMsg_FileRef_Rename,
                                      OnRename);
    PPAPI_DISPATCH_HOST_RESOURCE_CALL_0(PpapiHostMsg_FileRef_Query,
                                        OnQuery);
    PPAPI_DISPATCH_HOST_RESOURCE_CALL_0(
        PpapiHostMsg_FileRef_ReadDirectoryEntries,
        OnReadDirectoryEntries);
    PPAPI_DISPATCH_HOST_RESOURCE_CALL_0(PpapiHostMsg_FileRef_GetAbsolutePath,
                                        OnGetAbsolutePath);

  IPC_END_MESSAGE_MAP()
  return PP_ERROR_FAILED;
}

int32_t PepperFileRefHost::OnMakeDirectory(
    ppapi::host::HostMessageContext* context,
    int32_t make_directory_flags) {
  int32_t rv = CanCreate();
  if (rv != PP_OK)
    return rv;
  return backend_->MakeDirectory(
      context->MakeReplyMessageContext(), make_directory_flags);
}

int32_t PepperFileRefHost::OnTouch(ppapi::host::HostMessageContext* context,
                                   PP_Time last_access_time,
                                   PP_Time last_modified_time) {
  // TODO(teravest): Change this to be kWriteFilePermissions here and in
  // fileapi_message_filter.
  int32_t rv = CanCreate();
  if (rv != PP_OK)
    return rv;
  return backend_->Touch(context->MakeReplyMessageContext(),
                         last_access_time,
                         last_modified_time);
}

int32_t PepperFileRefHost::OnDelete(ppapi::host::HostMessageContext* context) {
  int32_t rv = CanWrite();
  if (rv != PP_OK)
    return rv;
  return backend_->Delete(context->MakeReplyMessageContext());
}

int32_t PepperFileRefHost::OnRename(ppapi::host::HostMessageContext* context,
                                    PP_Resource new_file_ref) {
  int32_t rv = CanReadWrite();
  if (rv != PP_OK)
    return rv;

  ResourceHost* resource_host =
      host_->GetPpapiHost()->GetResourceHost(new_file_ref);
  if (!resource_host)
    return PP_ERROR_BADRESOURCE;

  PepperFileRefHost* file_ref_host = NULL;
  if (resource_host->IsFileRefHost())
    file_ref_host = static_cast<PepperFileRefHost*>(resource_host);
  if (!file_ref_host)
    return PP_ERROR_BADRESOURCE;

  rv = file_ref_host->CanCreate();
  if (rv != PP_OK)
    return rv;

  return backend_->Rename(context->MakeReplyMessageContext(),
                          file_ref_host);
}

int32_t PepperFileRefHost::OnQuery(ppapi::host::HostMessageContext* context) {
  int32_t rv = CanRead();
  if (rv != PP_OK)
    return rv;
  return backend_->Query(context->MakeReplyMessageContext());
}

int32_t PepperFileRefHost::OnReadDirectoryEntries(
    ppapi::host::HostMessageContext* context) {
  int32_t rv = CanRead();
  if (rv != PP_OK)
    return rv;
  return backend_->ReadDirectoryEntries(context->MakeReplyMessageContext());
}

int32_t PepperFileRefHost::OnGetAbsolutePath(
    ppapi::host::HostMessageContext* context) {
  if (!host_->GetPpapiHost()->permissions().HasPermission(
      ppapi::PERMISSION_PRIVATE))
    return PP_ERROR_NOACCESS;
  return backend_->GetAbsolutePath(context->MakeReplyMessageContext());
}

}  // namespace content

/* [<][>][^][v][top][bottom][index][help] */