| Index: ppapi/native_client/src/trusted/plugin/service_runtime.cc
|
| diff --git a/ppapi/native_client/src/trusted/plugin/service_runtime.cc b/ppapi/native_client/src/trusted/plugin/service_runtime.cc
|
| index e9eba183482bfb1e79484ddcf0d4079107602b77..3a8a1f81b9a6329fa5791dcd91ae38af8a23ff9c 100644
|
| --- a/ppapi/native_client/src/trusted/plugin/service_runtime.cc
|
| +++ b/ppapi/native_client/src/trusted/plugin/service_runtime.cc
|
| @@ -64,6 +64,41 @@ namespace {
|
| // should be plenty for static data
|
| const int64_t kMaxTempQuota = 0x8000000;
|
|
|
| +class OpenManifestEntryAsyncCallback {
|
| + public:
|
| + OpenManifestEntryAsyncCallback(PP_FileHandle* file_handle,
|
| + const pp::CompletionCallback& callback)
|
| + : file_handle_(file_handle),
|
| + callback_(callback) {
|
| + }
|
| +
|
| + ~OpenManifestEntryAsyncCallback() {
|
| + if (callback_.pp_completion_callback().func)
|
| + callback_.RunAndClear(PP_ERROR_ABORTED);
|
| + }
|
| +
|
| + void Run(int32_t pp_error) {
|
| + *file_handle_ = (pp_error == PP_OK) ? info_.desc : -1;
|
| + callback_.RunAndClear(pp_error);
|
| + delete this;
|
| + }
|
| +
|
| + NaClFileInfo* mutable_info() { return &info_; }
|
| + pp::CompletionCallback pp_completion_callback() {
|
| + return pp::CompletionCallback(&RunTrampoline, this);
|
| + }
|
| +
|
| + private:
|
| + static void RunTrampoline(void* user_data, int32_t pp_error) {
|
| + static_cast<OpenManifestEntryAsyncCallback*>(user_data)->Run(pp_error);
|
| + }
|
| +
|
| + PP_FileHandle* file_handle_;
|
| + NaClFileInfo info_;
|
| + pp::CompletionCallback callback_;
|
| + DISALLOW_COPY_AND_ASSIGN(OpenManifestEntryAsyncCallback);
|
| +};
|
| +
|
| class ManifestService {
|
| public:
|
| ManifestService(nacl::WeakRefAnchor* anchor,
|
| @@ -92,6 +127,23 @@ class ManifestService {
|
| return true;
|
| }
|
|
|
| + bool OpenResource(const char* entry_key, PP_FileHandle* file,
|
| + const pp::CompletionCallback& callback) {
|
| + // Release this instance if the ServiceRuntime is already destructed.
|
| + if (anchor_->is_abandoned()) {
|
| + delete this;
|
| + return false;
|
| + }
|
| +
|
| + OpenManifestEntryAsyncCallback* open_manifest_callback =
|
| + new OpenManifestEntryAsyncCallback(file, callback);
|
| + plugin_reverse_->OpenManifestEntryAsync(
|
| + entry_key,
|
| + open_manifest_callback->mutable_info(),
|
| + open_manifest_callback->pp_completion_callback());
|
| + return true;
|
| + }
|
| +
|
| static PP_Bool QuitTrampoline(void* user_data) {
|
| return PP_FromBool(static_cast<ManifestService*>(user_data)->Quit());
|
| }
|
| @@ -101,6 +153,15 @@ class ManifestService {
|
| StartupInitializationComplete());
|
| }
|
|
|
| + static PP_Bool OpenResourceTrampoline(
|
| + void* user_data, const char* entry_key, PP_FileHandle* file,
|
| + struct PP_CompletionCallback callback) {
|
| + return PP_FromBool(
|
| + static_cast<ManifestService*>(user_data)->OpenResource(
|
| + entry_key, file,
|
| + pp::CompletionCallback(callback.func, callback.user_data)));
|
| + }
|
| +
|
| private:
|
| // Weak reference to check if plugin_reverse is legally accessible or not.
|
| nacl::WeakRefAnchor* anchor_;
|
| @@ -110,9 +171,10 @@ class ManifestService {
|
| };
|
|
|
| // Vtable to pass functions to LaunchSelLdr.
|
| -const PP_ManifestService kManifestServiceVTable = {
|
| +const PPB_ManifestService kManifestServiceVTable = {
|
| &ManifestService::QuitTrampoline,
|
| &ManifestService::StartupInitializationCompleteTrampoline,
|
| + &ManifestService::OpenResourceTrampoline,
|
| };
|
|
|
| } // namespace
|
| @@ -200,7 +262,8 @@ bool PluginReverseInterface::OpenManifestEntry(nacl::string url_key,
|
| // the main thread before this function can return. The pointers it contains
|
| // to stack variables will not leak.
|
| OpenManifestEntryResource* to_open =
|
| - new OpenManifestEntryResource(url_key, info, &op_complete);
|
| + new OpenManifestEntryResource(url_key, info, &op_complete,
|
| + pp::CompletionCallback());
|
| CHECK(to_open != NULL);
|
| NaClLog(4, "PluginReverseInterface::OpenManifestEntry: %s\n",
|
| url_key.c_str());
|
| @@ -250,6 +313,16 @@ bool PluginReverseInterface::OpenManifestEntry(nacl::string url_key,
|
| return true;
|
| }
|
|
|
| +void PluginReverseInterface::OpenManifestEntryAsync(
|
| + const nacl::string& entry_key,
|
| + struct NaClFileInfo* info,
|
| + const pp::CompletionCallback& callback) {
|
| + bool op_complete = false;
|
| + OpenManifestEntryResource to_open(
|
| + entry_key, info, &op_complete, callback);
|
| + OpenManifestEntry_MainThreadContinuation(&to_open, PP_OK);
|
| +}
|
| +
|
| // Transfer point from OpenManifestEntry() which runs on the main thread
|
| // (Some PPAPI actions -- like StreamAsFile -- can only run on the main thread).
|
| // OpenManifestEntry() is waiting on a condvar for this continuation to
|
| @@ -276,10 +349,14 @@ void PluginReverseInterface::OpenManifestEntry_MainThreadContinuation(
|
| error_info.message().c_str());
|
| // Failed, and error_info has the details on what happened. Wake
|
| // up requesting thread -- we are done.
|
| - nacl::MutexLocker take(&mu_);
|
| - *p->op_complete_ptr = true; // done...
|
| - p->file_info->desc = -1; // but failed.
|
| - NaClXCondVarBroadcast(&cv_);
|
| + {
|
| + nacl::MutexLocker take(&mu_);
|
| + *p->op_complete_ptr = true; // done...
|
| + p->file_info->desc = -1; // but failed.
|
| + NaClXCondVarBroadcast(&cv_);
|
| + }
|
| + if (p->callback.pp_completion_callback().func)
|
| + p->callback.RunAndClear(PP_OK);
|
| return;
|
| }
|
| NaClLog(4,
|
| @@ -292,10 +369,14 @@ void PluginReverseInterface::OpenManifestEntry_MainThreadContinuation(
|
| NaClLog(4,
|
| "OpenManifestEntry_MainThreadContinuation: "
|
| "Requires PNaCl translation -- not supported\n");
|
| - nacl::MutexLocker take(&mu_);
|
| - *p->op_complete_ptr = true; // done...
|
| - p->file_info->desc = -1; // but failed.
|
| - NaClXCondVarBroadcast(&cv_);
|
| + {
|
| + nacl::MutexLocker take(&mu_);
|
| + *p->op_complete_ptr = true; // done...
|
| + p->file_info->desc = -1; // but failed.
|
| + NaClXCondVarBroadcast(&cv_);
|
| + }
|
| + if (p->callback.pp_completion_callback().func)
|
| + p->callback.RunAndClear(PP_OK);
|
| return;
|
| }
|
|
|
| @@ -313,14 +394,18 @@ void PluginReverseInterface::OpenManifestEntry_MainThreadContinuation(
|
| "OpenManifestEntry_MainThreadContinuation: "
|
| "GetReadonlyPnaclFd failed\n");
|
| }
|
| - nacl::MutexLocker take(&mu_);
|
| - *p->op_complete_ptr = true; // done!
|
| - // TODO(ncbray): enable the fast loading and validation paths for this
|
| - // type of file.
|
| - p->file_info->desc = fd;
|
| - NaClXCondVarBroadcast(&cv_);
|
| + {
|
| + nacl::MutexLocker take(&mu_);
|
| + *p->op_complete_ptr = true; // done!
|
| + // TODO(ncbray): enable the fast loading and validation paths for this
|
| + // type of file.
|
| + p->file_info->desc = fd;
|
| + NaClXCondVarBroadcast(&cv_);
|
| + }
|
| NaClLog(4,
|
| "OpenManifestEntry_MainThreadContinuation: GetPnaclFd okay\n");
|
| + if (p->callback.pp_completion_callback().func)
|
| + p->callback.RunAndClear(PP_OK);
|
| return;
|
| }
|
|
|
| @@ -330,6 +415,9 @@ void PluginReverseInterface::OpenManifestEntry_MainThreadContinuation(
|
| // to create another instance.
|
| OpenManifestEntryResource* open_cont = new OpenManifestEntryResource(*p);
|
| open_cont->url = mapped_url;
|
| + // Callback is now delegated from p to open_cont. So, here we manually clear
|
| + // complete callback.
|
| + p->callback = pp::CompletionCallback();
|
| pp::CompletionCallback stream_cc = WeakRefNewCallback(
|
| anchor_,
|
| this,
|
| @@ -357,22 +445,27 @@ void PluginReverseInterface::StreamAsFile_MainThreadContinuation(
|
| NaClLog(4,
|
| "Entered StreamAsFile_MainThreadContinuation\n");
|
|
|
| - nacl::MutexLocker take(&mu_);
|
| - if (result == PP_OK) {
|
| - NaClLog(4, "StreamAsFile_MainThreadContinuation: GetFileInfo(%s)\n",
|
| - p->url.c_str());
|
| - *p->file_info = plugin_->GetFileInfo(p->url);
|
| + {
|
| + nacl::MutexLocker take(&mu_);
|
| + if (result == PP_OK) {
|
| + NaClLog(4, "StreamAsFile_MainThreadContinuation: GetFileInfo(%s)\n",
|
| + p->url.c_str());
|
| + *p->file_info = plugin_->GetFileInfo(p->url);
|
|
|
| - NaClLog(4,
|
| - "StreamAsFile_MainThreadContinuation: PP_OK, desc %d\n",
|
| - p->file_info->desc);
|
| - } else {
|
| - NaClLog(4,
|
| - "StreamAsFile_MainThreadContinuation: !PP_OK, setting desc -1\n");
|
| - p->file_info->desc = -1;
|
| + NaClLog(4,
|
| + "StreamAsFile_MainThreadContinuation: PP_OK, desc %d\n",
|
| + p->file_info->desc);
|
| + } else {
|
| + NaClLog(
|
| + 4,
|
| + "StreamAsFile_MainThreadContinuation: !PP_OK, setting desc -1\n");
|
| + p->file_info->desc = -1;
|
| + }
|
| + *p->op_complete_ptr = true;
|
| + NaClXCondVarBroadcast(&cv_);
|
| }
|
| - *p->op_complete_ptr = true;
|
| - NaClXCondVarBroadcast(&cv_);
|
| + if (p->callback.pp_completion_callback().func)
|
| + p->callback.RunAndClear(PP_OK);
|
| }
|
|
|
| bool PluginReverseInterface::CloseManifestEntry(int32_t desc) {
|
|
|