Home | History | Annotate | Download | only in web
      1 /*
      2  * Copyright (C) 2013 Google Inc. All rights reserved.
      3  *
      4  * Redistribution and use in source and binary forms, with or without
      5  * modification, are permitted provided that the following conditions are
      6  * met:
      7  *
      8  *     * Redistributions of source code must retain the above copyright
      9  * notice, this list of conditions and the following disclaimer.
     10  *     * Redistributions in binary form must reproduce the above
     11  * copyright notice, this list of conditions and the following disclaimer
     12  * in the documentation and/or other materials provided with the
     13  * distribution.
     14  *     * Neither the name of Google Inc. nor the names of its
     15  * contributors may be used to endorse or promote products derived from
     16  * this software without specific prior written permission.
     17  *
     18  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
     19  * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
     20  * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
     21  * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
     22  * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
     23  * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
     24  * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
     25  * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
     26  * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
     27  * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
     28  * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
     29  */
     30 
     31 #include "config.h"
     32 #include "WorkerFileSystemClient.h"
     33 
     34 #include "WebFileSystemCallbacksImpl.h"
     35 #include "WebWorkerBase.h"
     36 #include "WorkerAllowMainThreadBridgeBase.h"
     37 #include "WorkerFileSystemCallbacksBridge.h"
     38 #include "core/dom/ScriptExecutionContext.h"
     39 #include "core/platform/AsyncFileSystemCallbacks.h"
     40 #include "core/workers/WorkerGlobalScope.h"
     41 #include "core/workers/WorkerThread.h"
     42 #include "public/platform/WebFileError.h"
     43 #include "public/platform/WebFileSystem.h"
     44 #include "public/platform/WebFileSystemType.h"
     45 #include "wtf/MainThread.h"
     46 #include "wtf/Threading.h"
     47 #include "wtf/text/WTFString.h"
     48 
     49 using namespace WebCore;
     50 
     51 namespace WebKit {
     52 
     53 namespace {
     54 
     55 // This class is used to route the result of the WebWorkerBase::allowFileSystem
     56 // call back to the worker context.
     57 class AllowFileSystemMainThreadBridge : public WorkerAllowMainThreadBridgeBase {
     58 public:
     59     static PassRefPtr<AllowFileSystemMainThreadBridge> create(WebCore::WorkerGlobalScope* workerGlobalScope, WebWorkerBase* webWorkerBase, const String& mode)
     60     {
     61         return adoptRef(new AllowFileSystemMainThreadBridge(workerGlobalScope, webWorkerBase, mode));
     62     }
     63 
     64 private:
     65     AllowFileSystemMainThreadBridge(WebCore::WorkerGlobalScope* workerGlobalScope, WebWorkerBase* webWorkerBase, const String& mode)
     66         : WorkerAllowMainThreadBridgeBase(workerGlobalScope, webWorkerBase)
     67     {
     68         postTaskToMainThread(adoptPtr(new AllowParams(mode)));
     69     }
     70 
     71     virtual bool allowOnMainThread(WebCommonWorkerClient* commonClient, AllowParams*)
     72     {
     73         ASSERT(isMainThread());
     74         return commonClient->allowFileSystem();
     75     }
     76 };
     77 
     78 } // namespace
     79 
     80 PassOwnPtr<FileSystemClient> WorkerFileSystemClient::create()
     81 {
     82     return adoptPtr(static_cast<FileSystemClient*>(new WorkerFileSystemClient()));
     83 }
     84 
     85 WorkerFileSystemClient::~WorkerFileSystemClient()
     86 {
     87 }
     88 
     89 bool WorkerFileSystemClient::allowFileSystem(ScriptExecutionContext* context)
     90 {
     91     WorkerGlobalScope* workerGlobalScope = toWorkerGlobalScope(context);
     92     WebCore::WorkerThread* workerThread = workerGlobalScope->thread();
     93     WorkerRunLoop& runLoop = workerThread->runLoop();
     94     WebCore::WorkerLoaderProxy* workerLoaderProxy = &workerThread->workerLoaderProxy();
     95 
     96     String mode = "allowFileSystemMode";
     97     mode.append(String::number(runLoop.createUniqueId()));
     98 
     99     RefPtr<AllowFileSystemMainThreadBridge> bridge = AllowFileSystemMainThreadBridge::create(workerGlobalScope, workerLoaderProxy->toWebWorkerBase(), mode);
    100 
    101     // Either the bridge returns, or the queue gets terminated.
    102     // FIXME: This synchoronous execution should be replaced with better model.
    103     if (runLoop.runInMode(workerGlobalScope, mode) == MessageQueueTerminated) {
    104         bridge->cancel();
    105         return false;
    106     }
    107 
    108     return bridge->result();
    109 }
    110 
    111 void WorkerFileSystemClient::openFileSystem(ScriptExecutionContext* context, WebCore::FileSystemType type, PassOwnPtr<AsyncFileSystemCallbacks> callbacks, FileSystemSynchronousType synchronousType, long long size, OpenFileSystemMode openMode)
    112 {
    113     WorkerGlobalScope* workerGlobalScope = toWorkerGlobalScope(context);
    114     WebWorkerBase* webWorker = static_cast<WebWorkerBase*>(workerGlobalScope->thread()->workerLoaderProxy().toWebWorkerBase());
    115     WebCore::WorkerThread* workerThread = workerGlobalScope->thread();
    116     WorkerRunLoop& runLoop = workerThread->runLoop();
    117     WebCore::WorkerLoaderProxy* workerLoaderProxy =  &workerThread->workerLoaderProxy();
    118 
    119     String mode = "openFileSystemMode";
    120     mode.append(String::number(runLoop.createUniqueId()));
    121 
    122     RefPtr<WorkerFileSystemCallbacksBridge> bridge = WorkerFileSystemCallbacksBridge::create(workerLoaderProxy, workerGlobalScope, new WebFileSystemCallbacksImpl(callbacks, context, synchronousType));
    123     bridge->postOpenFileSystemToMainThread(webWorker->commonClient(), static_cast<WebFileSystemType>(type), size, openMode == CreateFileSystemIfNotPresent, mode);
    124 
    125     if (synchronousType == SynchronousFileSystem) {
    126         // FIXME: This synchoronous execution should be replaced with better model.
    127         if (runLoop.runInMode(workerGlobalScope, mode) == MessageQueueTerminated)
    128             bridge->stop();
    129     }
    130 }
    131 
    132 void WorkerFileSystemClient::deleteFileSystem(WebCore::ScriptExecutionContext*, WebCore::FileSystemType, PassOwnPtr<WebCore::AsyncFileSystemCallbacks>)
    133 {
    134     ASSERT_NOT_REACHED();
    135 }
    136 
    137 WorkerFileSystemClient::WorkerFileSystemClient()
    138 {
    139 }
    140 
    141 } // namespace WebKit
    142