Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(168)

Side by Side Diff: Source/core/fileapi/FileReader.cpp

Issue 858743002: Make ThrottleController an ExecutionContext supplement. (Closed) Base URL: svn://svn.chromium.org/blink/trunk
Patch Set: check for document-detached state + rebase Created 5 years, 11 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
« no previous file with comments | « Source/core/fileapi/FileReader.h ('k') | no next file » | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 /* 1 /*
2 * Copyright (C) 2010 Google Inc. All rights reserved. 2 * Copyright (C) 2010 Google Inc. All rights reserved.
3 * 3 *
4 * Redistribution and use in source and binary forms, with or without 4 * Redistribution and use in source and binary forms, with or without
5 * modification, are permitted provided that the following conditions are 5 * modification, are permitted provided that the following conditions are
6 * met: 6 * met:
7 * 7 *
8 * * Redistributions of source code must retain the above copyright 8 * * Redistributions of source code must retain the above copyright
9 * notice, this list of conditions and the following disclaimer. 9 * notice, this list of conditions and the following disclaimer.
10 * * Redistributions in binary form must reproduce the above 10 * * Redistributions in binary form must reproduce the above
(...skipping 21 matching lines...) Expand all
32 #include "core/fileapi/FileReader.h" 32 #include "core/fileapi/FileReader.h"
33 33
34 #include "bindings/core/v8/ExceptionState.h" 34 #include "bindings/core/v8/ExceptionState.h"
35 #include "core/dom/CrossThreadTask.h" 35 #include "core/dom/CrossThreadTask.h"
36 #include "core/dom/DOMArrayBuffer.h" 36 #include "core/dom/DOMArrayBuffer.h"
37 #include "core/dom/Document.h" 37 #include "core/dom/Document.h"
38 #include "core/dom/ExceptionCode.h" 38 #include "core/dom/ExceptionCode.h"
39 #include "core/dom/ExecutionContext.h" 39 #include "core/dom/ExecutionContext.h"
40 #include "core/events/ProgressEvent.h" 40 #include "core/events/ProgressEvent.h"
41 #include "core/fileapi/File.h" 41 #include "core/fileapi/File.h"
42 #include "core/frame/LocalFrame.h"
43 #include "core/inspector/InspectorInstrumentation.h" 42 #include "core/inspector/InspectorInstrumentation.h"
44 #include "core/workers/WorkerClients.h"
45 #include "core/workers/WorkerGlobalScope.h"
46 #include "platform/Logging.h" 43 #include "platform/Logging.h"
47 #include "platform/Supplementable.h" 44 #include "platform/Supplementable.h"
48 #include "wtf/CurrentTime.h" 45 #include "wtf/CurrentTime.h"
49 #include "wtf/Deque.h" 46 #include "wtf/Deque.h"
50 #include "wtf/HashSet.h" 47 #include "wtf/HashSet.h"
51 #include "wtf/text/CString.h" 48 #include "wtf/text/CString.h"
52 49
53 namespace blink { 50 namespace blink {
54 51
55 namespace { 52 namespace {
(...skipping 11 matching lines...) Expand all
67 #endif 64 #endif
68 65
69 } // namespace 66 } // namespace
70 67
71 // Embedders like chromium limit the number of simultaneous requests to avoid 68 // Embedders like chromium limit the number of simultaneous requests to avoid
72 // excessive IPC congestion. We limit this to 100 per thread to throttle the 69 // excessive IPC congestion. We limit this to 100 per thread to throttle the
73 // requests (the value is arbitrarily chosen). 70 // requests (the value is arbitrarily chosen).
74 static const size_t kMaxOutstandingRequestsPerThread = 100; 71 static const size_t kMaxOutstandingRequestsPerThread = 100;
75 static const double progressNotificationIntervalMS = 50; 72 static const double progressNotificationIntervalMS = 50;
76 73
77 typedef PersistentHeapDequeWillBeHeapDeque<Member<FileReader> > FileReaderDeque; 74 class FileReader::ThrottlingController final : public NoBaseWillBeGarbageCollect edFinalized<FileReader::ThrottlingController>, public WillBeHeapSupplement<Execu tionContext> {
78 typedef PersistentHeapHashSetWillBeHeapHashSet<Member<FileReader> > FileReaderHa shSet;
79
80 // FIXME: Oilpan: if ExecutionContext is moved to the heap, consider
81 // making this object an ExecutionContext supplement (only.)
82 class FileReader::ThrottlingController final : public NoBaseWillBeGarbageCollect edFinalized<FileReader::ThrottlingController>, public WillBeHeapSupplement<Local Frame>, public WillBeHeapSupplement<WorkerClients> {
83 WILL_BE_USING_GARBAGE_COLLECTED_MIXIN(FileReader::ThrottlingController); 75 WILL_BE_USING_GARBAGE_COLLECTED_MIXIN(FileReader::ThrottlingController);
84 public: 76 public:
85 static ThrottlingController* from(ExecutionContext* context) 77 static ThrottlingController* from(ExecutionContext* context)
86 { 78 {
87 if (!context) 79 if (!context)
88 return 0; 80 return 0;
89 81
90 if (context->isDocument()) { 82 ThrottlingController* controller = static_cast<ThrottlingController*>(Wi llBeHeapSupplement<ExecutionContext>::from(*context, supplementName()));
91 Document* document = toDocument(context); 83 if (!controller) {
92 if (!document->frame())
93 return 0;
94
95 ThrottlingController* controller = static_cast<ThrottlingController* >(WillBeHeapSupplement<LocalFrame>::from(document->frame(), supplementName()));
96 if (controller)
97 return controller;
98
99 controller = new ThrottlingController(); 84 controller = new ThrottlingController();
100 WillBeHeapSupplement<LocalFrame>::provideTo(*document->frame(), supp lementName(), adoptPtrWillBeNoop(controller)); 85 WillBeHeapSupplement<ExecutionContext>::provideTo(*context, suppleme ntName(), adoptPtrWillBeNoop(controller));
101 return controller;
102 } 86 }
103 ASSERT(!isMainThread());
104 ASSERT(context->isWorkerGlobalScope());
105 WorkerGlobalScope* workerGlobalScope = toWorkerGlobalScope(context);
106 ThrottlingController* controller = static_cast<ThrottlingController*>(Wi llBeHeapSupplement<WorkerClients>::from(workerGlobalScope->clients(), supplement Name()));
107 if (controller)
108 return controller;
109
110 controller = new ThrottlingController();
111 WillBeHeapSupplement<WorkerClients>::provideTo(*workerGlobalScope->clien ts(), supplementName(), adoptPtrWillBeNoop(controller));
112 return controller; 87 return controller;
113 } 88 }
114 89
115 ~ThrottlingController() { } 90 ~ThrottlingController() { }
116 91
117 enum FinishReaderType { DoNotRunPendingReaders, RunPendingReaders }; 92 enum FinishReaderType { DoNotRunPendingReaders, RunPendingReaders };
118 93
119 static void pushReader(ExecutionContext* context, FileReader* reader) 94 static void pushReader(ExecutionContext* context, FileReader* reader)
120 { 95 {
121 ThrottlingController* controller = from(context); 96 ThrottlingController* controller = from(context);
(...skipping 23 matching lines...) Expand all
145 120
146 controller->finishReader(reader, nextStep); 121 controller->finishReader(reader, nextStep);
147 } 122 }
148 123
149 void trace(Visitor* visitor) 124 void trace(Visitor* visitor)
150 { 125 {
151 #if ENABLE(OILPAN) 126 #if ENABLE(OILPAN)
152 visitor->trace(m_pendingReaders); 127 visitor->trace(m_pendingReaders);
153 visitor->trace(m_runningReaders); 128 visitor->trace(m_runningReaders);
154 #endif 129 #endif
155 WillBeHeapSupplement<LocalFrame>::trace(visitor); 130 WillBeHeapSupplement<ExecutionContext>::trace(visitor);
156 WillBeHeapSupplement<WorkerClients>::trace(visitor);
157 } 131 }
158 132
159 private: 133 private:
160 ThrottlingController() 134 ThrottlingController()
161 : m_maxRunningReaders(kMaxOutstandingRequestsPerThread) 135 : m_maxRunningReaders(kMaxOutstandingRequestsPerThread)
162 { 136 {
163 } 137 }
164 138
165 void pushReader(FileReader* reader) 139 void pushReader(FileReader* reader)
166 { 140 {
(...skipping 38 matching lines...) Expand 10 before | Expand all | Expand 10 after
205 return; 179 return;
206 FileReader* reader = m_pendingReaders.takeFirst(); 180 FileReader* reader = m_pendingReaders.takeFirst();
207 reader->executePendingRead(); 181 reader->executePendingRead();
208 m_runningReaders.add(reader); 182 m_runningReaders.add(reader);
209 } 183 }
210 } 184 }
211 185
212 static const char* supplementName() { return "FileReaderThrottlingController "; } 186 static const char* supplementName() { return "FileReaderThrottlingController "; }
213 187
214 const size_t m_maxRunningReaders; 188 const size_t m_maxRunningReaders;
189
190 using FileReaderDeque = PersistentHeapDequeWillBeHeapDeque<Member<FileReader >>;
191 using FileReaderHashSet = PersistentHeapHashSetWillBeHeapHashSet<Member<File Reader>>;
192
215 FileReaderDeque m_pendingReaders; 193 FileReaderDeque m_pendingReaders;
216 FileReaderHashSet m_runningReaders; 194 FileReaderHashSet m_runningReaders;
217 }; 195 };
218 196
219 FileReader* FileReader::create(ExecutionContext* context) 197 FileReader* FileReader::create(ExecutionContext* context)
220 { 198 {
221 FileReader* fileReader = new FileReader(context); 199 FileReader* fileReader = new FileReader(context);
222 fileReader->suspendIfNeeded(); 200 fileReader->suspendIfNeeded();
223 return fileReader; 201 return fileReader;
224 } 202 }
(...skipping 78 matching lines...) Expand 10 before | Expand all | Expand 10 after
303 if (m_state == LOADING) { 281 if (m_state == LOADING) {
304 exceptionState.throwDOMException(InvalidStateError, "The object is alrea dy busy reading Blobs."); 282 exceptionState.throwDOMException(InvalidStateError, "The object is alrea dy busy reading Blobs.");
305 return; 283 return;
306 } 284 }
307 285
308 if (blob->hasBeenClosed()) { 286 if (blob->hasBeenClosed()) {
309 exceptionState.throwDOMException(InvalidStateError, String(blob->isFile( ) ? "File" : "Blob") + " has been closed."); 287 exceptionState.throwDOMException(InvalidStateError, String(blob->isFile( ) ? "File" : "Blob") + " has been closed.");
310 return; 288 return;
311 } 289 }
312 290
313 if (!ThrottlingController::from(executionContext())) { 291 ExecutionContext* context = executionContext();
292 if (!context) {
293 exceptionState.throwDOMException(AbortError, "Reading from a detached Fi leReader is not supported.");
294 return;
295 }
296
297 // A document loader will not load new resources once the Document has detac hed from its frame.
298 if (context->isDocument() && !toDocument(context)->frame()) {
314 exceptionState.throwDOMException(AbortError, "Reading from a Document-de tached FileReader is not supported."); 299 exceptionState.throwDOMException(AbortError, "Reading from a Document-de tached FileReader is not supported.");
315 return; 300 return;
316 } 301 }
317 302
318 // "Snapshot" the Blob data rather than the Blob itself as ongoing 303 // "Snapshot" the Blob data rather than the Blob itself as ongoing
319 // read operations should not be affected if close() is called on 304 // read operations should not be affected if close() is called on
320 // the Blob being read. 305 // the Blob being read.
321 m_blobDataHandle = blob->blobDataHandle(); 306 m_blobDataHandle = blob->blobDataHandle();
322 m_blobType = blob->type(); 307 m_blobType = blob->type();
323 m_readType = type; 308 m_readType = type;
324 m_state = LOADING; 309 m_state = LOADING;
325 m_loadingState = LoadingStatePending; 310 m_loadingState = LoadingStatePending;
326 m_error = nullptr; 311 m_error = nullptr;
327 ThrottlingController::pushReader(executionContext(), this); 312 ASSERT(ThrottlingController::from(context));
313 ThrottlingController::pushReader(context, this);
328 } 314 }
329 315
330 void FileReader::executePendingRead() 316 void FileReader::executePendingRead()
331 { 317 {
332 ASSERT(m_loadingState == LoadingStatePending); 318 ASSERT(m_loadingState == LoadingStatePending);
333 m_loadingState = LoadingStateLoading; 319 m_loadingState = LoadingStateLoading;
334 320
335 m_loader = adoptPtr(new FileReaderLoader(m_readType, this)); 321 m_loader = adoptPtr(new FileReaderLoader(m_readType, this));
336 m_loader->setEncoding(m_encoding); 322 m_loader->setEncoding(m_encoding);
337 m_loader->setDataType(m_blobType); 323 m_loader->setDataType(m_blobType);
(...skipping 147 matching lines...) Expand 10 before | Expand all | Expand 10 after
485 } 471 }
486 472
487 void FileReader::trace(Visitor* visitor) 473 void FileReader::trace(Visitor* visitor)
488 { 474 {
489 visitor->trace(m_error); 475 visitor->trace(m_error);
490 RefCountedGarbageCollectedEventTargetWithInlineData<FileReader>::trace(visit or); 476 RefCountedGarbageCollectedEventTargetWithInlineData<FileReader>::trace(visit or);
491 ActiveDOMObject::trace(visitor); 477 ActiveDOMObject::trace(visitor);
492 } 478 }
493 479
494 } // namespace blink 480 } // namespace blink
OLDNEW
« no previous file with comments | « Source/core/fileapi/FileReader.h ('k') | no next file » | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698