Line data Source code
1 : /* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
2 : /* vim: set ts=8 sts=2 et sw=2 tw=80: */
3 : /* This Source Code Form is subject to the terms of the Mozilla Public
4 : * License, v. 2.0. If a copy of the MPL was not distributed with this file,
5 : * You can obtain one at http://mozilla.org/MPL/2.0/. */
6 :
7 : #ifndef mozilla_dom_GetFilesHelper_h
8 : #define mozilla_dom_GetFilesHelper_h
9 :
10 : #include "mozilla/Mutex.h"
11 : #include "mozilla/RefPtr.h"
12 : #include "nsCycleCollectionTraversalCallback.h"
13 : #include "nsTArray.h"
14 : #include "nsTHashtable.h"
15 :
16 : class nsIGlobalObject;
17 :
18 : namespace mozilla {
19 : namespace dom {
20 :
21 : class BlobImpl;
22 : class ContentParent;
23 : class File;
24 : class GetFilesHelperParent;
25 : class OwningFileOrDirectory;
26 : class Promise;
27 :
28 0 : class GetFilesCallback
29 : {
30 : public:
31 0 : NS_INLINE_DECL_REFCOUNTING(GetFilesCallback);
32 :
33 : virtual void
34 : Callback(nsresult aStatus, const Sequence<RefPtr<File>>& aFiles) = 0;
35 :
36 : protected:
37 0 : virtual ~GetFilesCallback() {}
38 : };
39 :
40 : class GetFilesHelperBase
41 : {
42 : protected:
43 0 : explicit GetFilesHelperBase(bool aRecursiveFlag)
44 0 : : mRecursiveFlag(aRecursiveFlag)
45 0 : {}
46 :
47 0 : virtual ~GetFilesHelperBase() {}
48 :
49 : virtual bool
50 0 : IsCanceled()
51 : {
52 0 : return false;
53 : }
54 :
55 : nsresult
56 : ExploreDirectory(const nsAString& aDOMPath, nsIFile* aFile);
57 :
58 : nsresult
59 : AddExploredDirectory(nsIFile* aDirectory);
60 :
61 : bool
62 : ShouldFollowSymLink(nsIFile* aDirectory);
63 :
64 : bool mRecursiveFlag;
65 :
66 : // We populate this array in the I/O thread with the BlobImpl.
67 : FallibleTArray<RefPtr<BlobImpl>> mTargetBlobImplArray;
68 : nsTHashtable<nsStringHashKey> mExploredDirectories;
69 : };
70 :
71 : // Retrieving the list of files can be very time/IO consuming. We use this
72 : // helper class to do it just once.
73 : class GetFilesHelper : public Runnable
74 : , public GetFilesHelperBase
75 : {
76 : friend class GetFilesHelperParent;
77 :
78 : public:
79 : static already_AddRefed<GetFilesHelper>
80 : Create(nsIGlobalObject* aGlobal,
81 : const nsTArray<OwningFileOrDirectory>& aFilesOrDirectory,
82 : bool aRecursiveFlag, ErrorResult& aRv);
83 :
84 : void
85 : AddPromise(Promise* aPromise);
86 :
87 : void
88 : AddCallback(GetFilesCallback* aCallback);
89 :
90 : // CC methods
91 : void Unlink();
92 : void Traverse(nsCycleCollectionTraversalCallback &cb);
93 :
94 : protected:
95 : GetFilesHelper(nsIGlobalObject* aGlobal, bool aRecursiveFlag);
96 :
97 : virtual ~GetFilesHelper();
98 :
99 : void
100 0 : SetDirectoryPath(const nsAString& aDirectoryPath)
101 : {
102 0 : mDirectoryPath = aDirectoryPath;
103 0 : }
104 :
105 : virtual bool
106 0 : IsCanceled() override
107 : {
108 0 : MutexAutoLock lock(mMutex);
109 0 : return mCanceled;
110 : }
111 :
112 : virtual void
113 : Work(ErrorResult& aRv);
114 :
115 : virtual void
116 0 : Cancel() {};
117 :
118 : NS_IMETHOD
119 : Run() override;
120 :
121 : void
122 : RunIO();
123 :
124 : void
125 : RunMainThread();
126 :
127 : void
128 : OperationCompleted();
129 :
130 : void
131 : ResolveOrRejectPromise(Promise* aPromise);
132 :
133 : void
134 : RunCallback(GetFilesCallback* aCallback);
135 :
136 : nsCOMPtr<nsIGlobalObject> mGlobal;
137 :
138 : bool mListingCompleted;
139 : nsString mDirectoryPath;
140 :
141 : // This is the real File sequence that we expose via Promises.
142 : Sequence<RefPtr<File>> mFiles;
143 :
144 : // Error code to propagate.
145 : nsresult mErrorResult;
146 :
147 : nsTArray<RefPtr<Promise>> mPromises;
148 : nsTArray<RefPtr<GetFilesCallback>> mCallbacks;
149 :
150 : Mutex mMutex;
151 :
152 : // This variable is protected by mutex.
153 : bool mCanceled;
154 : };
155 :
156 0 : class GetFilesHelperChild final : public GetFilesHelper
157 : {
158 : public:
159 0 : GetFilesHelperChild(nsIGlobalObject* aGlobal, bool aRecursiveFlag)
160 0 : : GetFilesHelper(aGlobal, aRecursiveFlag)
161 0 : , mPendingOperation(false)
162 0 : {}
163 :
164 : virtual void
165 : Work(ErrorResult& aRv) override;
166 :
167 : virtual void
168 : Cancel() override;
169 :
170 : bool
171 : AppendBlobImpl(BlobImpl* aBlobImpl);
172 :
173 : void
174 : Finished(nsresult aResult);
175 :
176 : private:
177 : nsID mUUID;
178 : bool mPendingOperation;
179 : };
180 :
181 : class GetFilesHelperParentCallback;
182 :
183 : class GetFilesHelperParent final : public GetFilesHelper
184 : {
185 : friend class GetFilesHelperParentCallback;
186 :
187 : public:
188 : static already_AddRefed<GetFilesHelperParent>
189 : Create(const nsID& aUUID, const nsAString& aDirectoryPath,
190 : bool aRecursiveFlag, ContentParent* aContentParent, ErrorResult& aRv);
191 :
192 : private:
193 : GetFilesHelperParent(const nsID& aUUID, ContentParent* aContentParent,
194 : bool aRecursiveFlag);
195 :
196 : ~GetFilesHelperParent();
197 :
198 : RefPtr<ContentParent> mContentParent;
199 : nsID mUUID;
200 : };
201 :
202 : } // dom namespace
203 : } // mozilla namespace
204 :
205 : #endif // mozilla_dom_GetFilesHelper_h
|