1 /* 2 * Copyright (C) 2010 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 #ifndef DOMFileSystem_h 32 #define DOMFileSystem_h 33 34 #include "bindings/core/v8/ScriptWrappable.h" 35 #include "core/dom/ActiveDOMObject.h" 36 #include "core/dom/ExecutionContext.h" 37 #include "core/dom/ExecutionContextTask.h" 38 #include "modules/filesystem/DOMFileSystemBase.h" 39 #include "modules/filesystem/EntriesCallback.h" 40 #include "platform/heap/Handle.h" 41 42 namespace blink { 43 44 class DirectoryEntry; 45 class File; 46 class FileCallback; 47 class FileEntry; 48 class FileWriterCallback; 49 50 class DOMFileSystem FINAL : public DOMFileSystemBase, public ScriptWrappable, public ActiveDOMObject { 51 DEFINE_WRAPPERTYPEINFO(); 52 public: 53 static DOMFileSystem* create(ExecutionContext*, const String& name, FileSystemType, const KURL& rootURL); 54 55 // Creates a new isolated file system for the given filesystemId. 56 static DOMFileSystem* createIsolatedFileSystem(ExecutionContext*, const String& filesystemId); 57 58 DirectoryEntry* root(); 59 60 // DOMFileSystemBase overrides. 61 virtual void addPendingCallbacks() OVERRIDE; 62 virtual void removePendingCallbacks() OVERRIDE; 63 virtual void reportError(ErrorCallback*, PassRefPtrWillBeRawPtr<FileError>) OVERRIDE; 64 65 // ActiveDOMObject overrides. 66 virtual bool hasPendingActivity() const OVERRIDE; 67 68 void createWriter(const FileEntry*, FileWriterCallback*, ErrorCallback*); 69 void createFile(const FileEntry*, FileCallback*, ErrorCallback*); 70 71 // Schedule a callback. This should not cross threads (should be called on the same context thread). 72 // FIXME: move this to a more generic place. 73 template <typename CB, typename CBArg> 74 static void scheduleCallback(ExecutionContext*, CB*, PassRefPtrWillBeRawPtr<CBArg>); 75 76 template <typename CB, typename CBArg> 77 static void scheduleCallback(ExecutionContext*, CB*, CBArg*); 78 79 template <typename CB, typename CBArg> 80 static void scheduleCallback(ExecutionContext*, CB*, const HeapVector<CBArg>&); 81 82 template <typename CB, typename CBArg> 83 static void scheduleCallback(ExecutionContext*, CB*, const CBArg&); 84 85 template <typename CB> 86 static void scheduleCallback(ExecutionContext*, CB*); 87 88 template <typename CB, typename CBArg> scheduleCallback(CB * callback,PassRefPtrWillBeRawPtr<CBArg> callbackArg)89 void scheduleCallback(CB* callback, PassRefPtrWillBeRawPtr<CBArg> callbackArg) 90 { 91 scheduleCallback(executionContext(), callback, callbackArg); 92 } 93 94 template <typename CB, typename CBArg> scheduleCallback(CB * callback,CBArg * callbackArg)95 void scheduleCallback(CB* callback, CBArg* callbackArg) 96 { 97 scheduleCallback(executionContext(), callback, callbackArg); 98 } 99 100 template <typename CB, typename CBArg> scheduleCallback(CB * callback,const CBArg & callbackArg)101 void scheduleCallback(CB* callback, const CBArg& callbackArg) 102 { 103 scheduleCallback(executionContext(), callback, callbackArg); 104 } 105 106 private: 107 DOMFileSystem(ExecutionContext*, const String& name, FileSystemType, const KURL& rootURL); 108 109 class DispatchCallbackTaskBase : public ExecutionContextTask { 110 public: DispatchCallbackTaskBase()111 DispatchCallbackTaskBase() 112 : m_taskName("FileSystem") 113 { 114 } 115 taskNameForInstrumentation()116 virtual const String& taskNameForInstrumentation() const OVERRIDE 117 { 118 return m_taskName; 119 } 120 121 private: 122 const String m_taskName; 123 }; 124 125 // A helper template to schedule a callback task. 126 template <typename CB, typename CBArg> 127 class DispatchCallbackRefPtrArgTask FINAL : public DispatchCallbackTaskBase { 128 public: DispatchCallbackRefPtrArgTask(CB * callback,PassRefPtrWillBeRawPtr<CBArg> arg)129 DispatchCallbackRefPtrArgTask(CB* callback, PassRefPtrWillBeRawPtr<CBArg> arg) 130 : m_callback(callback) 131 , m_callbackArg(arg) 132 { 133 } 134 performTask(ExecutionContext *)135 virtual void performTask(ExecutionContext*) OVERRIDE 136 { 137 m_callback->handleEvent(m_callbackArg.get()); 138 } 139 140 private: 141 Persistent<CB> m_callback; 142 RefPtrWillBePersistent<CBArg> m_callbackArg; 143 }; 144 145 template <typename CB, typename CBArg> 146 class DispatchCallbackPtrArgTask FINAL : public DispatchCallbackTaskBase { 147 public: DispatchCallbackPtrArgTask(CB * callback,CBArg * arg)148 DispatchCallbackPtrArgTask(CB* callback, CBArg* arg) 149 : m_callback(callback) 150 , m_callbackArg(arg) 151 { 152 } 153 performTask(ExecutionContext *)154 virtual void performTask(ExecutionContext*) OVERRIDE 155 { 156 m_callback->handleEvent(m_callbackArg.get()); 157 } 158 159 private: 160 Persistent<CB> m_callback; 161 Persistent<CBArg> m_callbackArg; 162 }; 163 164 template <typename CB, typename CBArg> 165 class DispatchCallbackNonPtrArgTask FINAL : public DispatchCallbackTaskBase { 166 public: DispatchCallbackNonPtrArgTask(CB * callback,const CBArg & arg)167 DispatchCallbackNonPtrArgTask(CB* callback, const CBArg& arg) 168 : m_callback(callback) 169 , m_callbackArg(arg) 170 { 171 } 172 performTask(ExecutionContext *)173 virtual void performTask(ExecutionContext*) OVERRIDE 174 { 175 m_callback->handleEvent(m_callbackArg); 176 } 177 178 private: 179 Persistent<CB> m_callback; 180 CBArg m_callbackArg; 181 }; 182 183 template <typename CB> 184 class DispatchCallbackNoArgTask FINAL : public DispatchCallbackTaskBase { 185 public: DispatchCallbackNoArgTask(CB * callback)186 DispatchCallbackNoArgTask(CB* callback) 187 : m_callback(callback) 188 { 189 } 190 performTask(ExecutionContext *)191 virtual void performTask(ExecutionContext*) OVERRIDE 192 { 193 m_callback->handleEvent(); 194 } 195 196 private: 197 Persistent<CB> m_callback; 198 }; 199 200 int m_numberOfPendingCallbacks; 201 }; 202 203 template <typename CB, typename CBArg> scheduleCallback(ExecutionContext * executionContext,CB * callback,PassRefPtrWillBeRawPtr<CBArg> arg)204 void DOMFileSystem::scheduleCallback(ExecutionContext* executionContext, CB* callback, PassRefPtrWillBeRawPtr<CBArg> arg) 205 { 206 ASSERT(executionContext->isContextThread()); 207 if (callback) 208 executionContext->postTask(adoptPtr(new DispatchCallbackRefPtrArgTask<CB, CBArg>(callback, arg))); 209 } 210 211 template <typename CB, typename CBArg> scheduleCallback(ExecutionContext * executionContext,CB * callback,CBArg * arg)212 void DOMFileSystem::scheduleCallback(ExecutionContext* executionContext, CB* callback, CBArg* arg) 213 { 214 ASSERT(executionContext->isContextThread()); 215 if (callback) 216 executionContext->postTask(adoptPtr(new DispatchCallbackPtrArgTask<CB, CBArg>(callback, arg))); 217 } 218 219 template <typename CB, typename CBArg> scheduleCallback(ExecutionContext * executionContext,CB * callback,const HeapVector<CBArg> & arg)220 void DOMFileSystem::scheduleCallback(ExecutionContext* executionContext, CB* callback, const HeapVector<CBArg>& arg) 221 { 222 ASSERT(executionContext->isContextThread()); 223 if (callback) 224 executionContext->postTask(adoptPtr(new DispatchCallbackNonPtrArgTask<CB, PersistentHeapVector<CBArg> >(callback, arg))); 225 } 226 227 template <typename CB, typename CBArg> scheduleCallback(ExecutionContext * executionContext,CB * callback,const CBArg & arg)228 void DOMFileSystem::scheduleCallback(ExecutionContext* executionContext, CB* callback, const CBArg& arg) 229 { 230 ASSERT(executionContext->isContextThread()); 231 if (callback) 232 executionContext->postTask(adoptPtr(new DispatchCallbackNonPtrArgTask<CB, CBArg>(callback, arg))); 233 } 234 235 template <typename CB> scheduleCallback(ExecutionContext * executionContext,CB * callback)236 void DOMFileSystem::scheduleCallback(ExecutionContext* executionContext, CB* callback) 237 { 238 ASSERT(executionContext->isContextThread()); 239 if (callback) 240 executionContext->postTask(adoptPtr(new DispatchCallbackNoArgTask<CB>(callback))); 241 } 242 243 } // namespace blink 244 245 #endif // DOMFileSystem_h 246