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

Side by Side Diff: Source/core/timing/PerformanceBase.cpp

Issue 1198863006: First version of PerformanceObserver (Closed) Base URL: https://chromium.googlesource.com/chromium/blink.git@master
Patch Set: Switch from microtask to timer for firing events. Created 5 years, 5 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
OLDNEW
1 /* 1 /*
2 * Copyright (C) 2010 Google Inc. All rights reserved. 2 * Copyright (C) 2010 Google Inc. All rights reserved.
3 * Copyright (C) 2012 Intel Inc. All rights reserved. 3 * Copyright (C) 2012 Intel Inc. All rights reserved.
4 * 4 *
5 * Redistribution and use in source and binary forms, with or without 5 * Redistribution and use in source and binary forms, with or without
6 * modification, are permitted provided that the following conditions are 6 * modification, are permitted provided that the following conditions are
7 * met: 7 * met:
8 * 8 *
9 * * Redistributions of source code must retain the above copyright 9 * * Redistributions of source code must retain the above copyright
10 * notice, this list of conditions and the following disclaimer. 10 * notice, this list of conditions and the following disclaimer.
(...skipping 17 matching lines...) Expand all
28 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 28 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
29 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 29 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
30 */ 30 */
31 31
32 #include "config.h" 32 #include "config.h"
33 #include "core/timing/PerformanceBase.h" 33 #include "core/timing/PerformanceBase.h"
34 34
35 #include "core/dom/Document.h" 35 #include "core/dom/Document.h"
36 #include "core/events/Event.h" 36 #include "core/events/Event.h"
37 #include "core/timing/PerformanceCompositeTiming.h" 37 #include "core/timing/PerformanceCompositeTiming.h"
38 #include "core/timing/PerformanceObserver.h"
38 #include "core/timing/PerformanceRenderTiming.h" 39 #include "core/timing/PerformanceRenderTiming.h"
39 #include "core/timing/PerformanceResourceTiming.h" 40 #include "core/timing/PerformanceResourceTiming.h"
40 #include "core/timing/PerformanceUserTiming.h" 41 #include "core/timing/PerformanceUserTiming.h"
41 #include "platform/network/ResourceTimingInfo.h" 42 #include "platform/network/ResourceTimingInfo.h"
42 #include "platform/weborigin/SecurityOrigin.h" 43 #include "platform/weborigin/SecurityOrigin.h"
43 #include "wtf/CurrentTime.h" 44 #include "wtf/CurrentTime.h"
44 45
45 namespace blink { 46 namespace blink {
46 47
47 static const size_t defaultResourceTimingBufferSize = 150; 48 static const size_t defaultResourceTimingBufferSize = 150;
48 static const size_t defaultFrameTimingBufferSize = 150; 49 static const size_t defaultFrameTimingBufferSize = 150;
49 50
50 PerformanceBase::PerformanceBase(double timeOrigin) 51 PerformanceBase::PerformanceBase(double timeOrigin)
51 : m_frameTimingBufferSize(defaultFrameTimingBufferSize) 52 : m_frameTimingBufferSize(defaultFrameTimingBufferSize)
52 , m_resourceTimingBufferSize(defaultResourceTimingBufferSize) 53 , m_resourceTimingBufferSize(defaultResourceTimingBufferSize)
53 , m_timeOrigin(timeOrigin) 54 , m_timeOrigin(timeOrigin)
54 , m_userTiming(nullptr) 55 , m_userTiming(nullptr)
56 , m_observerFilterOptions(PerformanceEntry::Invalid)
55 { 57 {
56 } 58 }
57 59
58 PerformanceBase::~PerformanceBase() 60 PerformanceBase::~PerformanceBase()
59 { 61 {
60 } 62 }
61 63
62 const AtomicString& PerformanceBase::interfaceName() const 64 const AtomicString& PerformanceBase::interfaceName() const
63 { 65 {
64 return EventTargetNames::Performance; 66 return EventTargetNames::Performance;
(...skipping 16 matching lines...) Expand all
81 entries.appendVector(m_userTiming->getMeasures()); 83 entries.appendVector(m_userTiming->getMeasures());
82 } 84 }
83 85
84 std::sort(entries.begin(), entries.end(), PerformanceEntry::startTimeCompare LessThan); 86 std::sort(entries.begin(), entries.end(), PerformanceEntry::startTimeCompare LessThan);
85 return entries; 87 return entries;
86 } 88 }
87 89
88 PerformanceEntryVector PerformanceBase::getEntriesByType(const String& entryType ) 90 PerformanceEntryVector PerformanceBase::getEntriesByType(const String& entryType )
89 { 91 {
90 PerformanceEntryVector entries; 92 PerformanceEntryVector entries;
93 PerformanceEntry::EntryType entryTypeEnum = PerformanceEntry::toEntryTypeEnu m(entryType);
esprehn 2015/07/24 08:23:12 Maybe just |type| ?
MikeB 2015/07/24 19:30:38 Done.
91 94
92 if (equalIgnoringCase(entryType, "resource")) { 95 if (entryTypeEnum == PerformanceEntry::Invalid)
96 return entries;
97
98 if (entryTypeEnum == PerformanceEntry::Resource) {
93 for (const auto& resource : m_resourceTimingBuffer) 99 for (const auto& resource : m_resourceTimingBuffer)
94 entries.append(resource); 100 entries.append(resource);
95 } 101 }
96 102
97 if (equalIgnoringCase(entryType, "composite") 103 if (entryTypeEnum == PerformanceEntry::Composite || entryTypeEnum == Performance Entry::Render) {
98 || equalIgnoringCase(entryType, "render")) {
99 for (const auto& frame : m_frameTimingBuffer) { 104 for (const auto& frame : m_frameTimingBuffer) {
100 if (equalIgnoringCase(entryType, frame->entryType())) { 105 if (entryTypeEnum == frame->entryTypeEnum()) {
101 entries.append(frame); 106 entries.append(frame);
102 } 107 }
103 } 108 }
104 } 109 }
105 110
106 if (m_userTiming) { 111 if (m_userTiming) {
107 if (equalIgnoringCase(entryType, "mark")) 112 if (entryTypeEnum == PerformanceEntry::Mark)
108 entries.appendVector(m_userTiming->getMarks()); 113 entries.appendVector(m_userTiming->getMarks());
109 else if (equalIgnoringCase(entryType, "measure")) 114 else if (entryTypeEnum == PerformanceEntry::Measure)
110 entries.appendVector(m_userTiming->getMeasures()); 115 entries.appendVector(m_userTiming->getMeasures());
111 } 116 }
112 117
113 std::sort(entries.begin(), entries.end(), PerformanceEntry::startTimeCompare LessThan); 118 std::sort(entries.begin(), entries.end(), PerformanceEntry::startTimeCompare LessThan);
114 return entries; 119 return entries;
115 } 120 }
116 121
117 PerformanceEntryVector PerformanceBase::getEntriesByName(const String& name, con st String& entryType) 122 PerformanceEntryVector PerformanceBase::getEntriesByName(const String& name, con st String& entryType)
118 { 123 {
119 PerformanceEntryVector entries; 124 PerformanceEntryVector entries;
125 PerformanceEntry::EntryType entryTypeEnum = PerformanceEntry::toEntryTypeEnu m(entryType);
120 126
121 if (entryType.isNull() || equalIgnoringCase(entryType, "resource")) { 127 if (!entryType.isNull() && entryTypeEnum == PerformanceEntry::Invalid)
128 return entries;
129
130 if (entryType.isNull() || entryTypeEnum == PerformanceEntry::Resource) {
122 for (const auto& resource : m_resourceTimingBuffer) { 131 for (const auto& resource : m_resourceTimingBuffer) {
123 if (resource->name() == name) 132 if (resource->name() == name)
124 entries.append(resource); 133 entries.append(resource);
125 } 134 }
126 } 135 }
127 136
128 if (entryType.isNull() || equalIgnoringCase(entryType, "composite") 137 if (entryType.isNull() || entryTypeEnum == PerformanceEntry::Composite || en tryTypeEnum == PerformanceEntry::Render) {
129 || equalIgnoringCase(entryType, "render")) {
130 for (const auto& frame : m_frameTimingBuffer) { 138 for (const auto& frame : m_frameTimingBuffer) {
131 if (frame->name() == name && (entryType.isNull() 139 if (frame->name() == name && (entryType.isNull()
132 || equalIgnoringCase(entryType, frame->entryType()))) { 140 || equalIgnoringCase(entryType, frame->entryType()))) {
133 entries.append(frame); 141 entries.append(frame);
134 } 142 }
135 } 143 }
136 } 144 }
137 145
138 if (m_userTiming) { 146 if (m_userTiming) {
139 if (entryType.isNull() || equalIgnoringCase(entryType, "mark")) 147 if (entryType.isNull() || entryTypeEnum == PerformanceEntry::Mark)
140 entries.appendVector(m_userTiming->getMarks(name)); 148 entries.appendVector(m_userTiming->getMarks(name));
141 if (entryType.isNull() || equalIgnoringCase(entryType, "measure")) 149 if (entryType.isNull() || entryTypeEnum == PerformanceEntry::Measure)
142 entries.appendVector(m_userTiming->getMeasures(name)); 150 entries.appendVector(m_userTiming->getMeasures(name));
143 } 151 }
144 152
145 std::sort(entries.begin(), entries.end(), PerformanceEntry::startTimeCompare LessThan); 153 std::sort(entries.begin(), entries.end(), PerformanceEntry::startTimeCompare LessThan);
146 return entries; 154 return entries;
147 } 155 }
148 156
149 void PerformanceBase::webkitClearResourceTimings() 157 void PerformanceBase::webkitClearResourceTimings()
150 { 158 {
151 m_resourceTimingBuffer.clear(); 159 m_resourceTimingBuffer.clear();
(...skipping 52 matching lines...) Expand 10 before | Expand all | Expand 10 after
204 for (const ResourceResponse& response : redirectChain) { 212 for (const ResourceResponse& response : redirectChain) {
205 if (!passesTimingAllowCheck(response, initiatorSecurityOrigin, emptyAtom )) 213 if (!passesTimingAllowCheck(response, initiatorSecurityOrigin, emptyAtom ))
206 return false; 214 return false;
207 } 215 }
208 216
209 return true; 217 return true;
210 } 218 }
211 219
212 void PerformanceBase::addResourceTiming(const ResourceTimingInfo& info) 220 void PerformanceBase::addResourceTiming(const ResourceTimingInfo& info)
213 { 221 {
214 if (isResourceTimingBufferFull()) 222 if (isResourceTimingBufferFull() && !hasObserverFor(PerformanceEntry::Resour ce))
215 return; 223 return;
216 SecurityOrigin* securityOrigin = nullptr; 224 SecurityOrigin* securityOrigin = nullptr;
217 if (ExecutionContext* context = executionContext()) 225 if (ExecutionContext* context = executionContext())
218 securityOrigin = context->securityOrigin(); 226 securityOrigin = context->securityOrigin();
219 if (!securityOrigin) 227 if (!securityOrigin)
220 return; 228 return;
221 229
222 const ResourceResponse& finalResponse = info.finalResponse(); 230 const ResourceResponse& finalResponse = info.finalResponse();
223 bool allowTimingDetails = passesTimingAllowCheck(finalResponse, *securityOri gin, info.originalTimingAllowOrigin()); 231 bool allowTimingDetails = passesTimingAllowCheck(finalResponse, *securityOri gin, info.originalTimingAllowOrigin());
224 double startTime = info.initialTime(); 232 double startTime = info.initialTime();
(...skipping 12 matching lines...) Expand all
237 ASSERT(finalTiming); 245 ASSERT(finalTiming);
238 if (finalTiming) 246 if (finalTiming)
239 startTime = finalTiming->requestTime(); 247 startTime = finalTiming->requestTime();
240 } 248 }
241 249
242 ResourceLoadTiming* lastRedirectTiming = redirectChain.last().resourceLoadTi ming(); 250 ResourceLoadTiming* lastRedirectTiming = redirectChain.last().resourceLoadTi ming();
243 ASSERT(lastRedirectTiming); 251 ASSERT(lastRedirectTiming);
244 double lastRedirectEndTime = lastRedirectTiming->receiveHeadersEnd(); 252 double lastRedirectEndTime = lastRedirectTiming->receiveHeadersEnd();
245 253
246 PerformanceEntry* entry = PerformanceResourceTiming::create(info, timeOrigin (), startTime, lastRedirectEndTime, allowTimingDetails, allowRedirectDetails); 254 PerformanceEntry* entry = PerformanceResourceTiming::create(info, timeOrigin (), startTime, lastRedirectEndTime, allowTimingDetails, allowRedirectDetails);
247 addResourceTimingBuffer(entry); 255 notifyObserversOfEntry(entry);
256 if (!isResourceTimingBufferFull())
257 addResourceTimingBuffer(entry);
248 } 258 }
249 259
250 void PerformanceBase::addResourceTimingBuffer(PerformanceEntry* entry) 260 void PerformanceBase::addResourceTimingBuffer(PerformanceEntry* entry)
251 { 261 {
252 m_resourceTimingBuffer.append(entry); 262 m_resourceTimingBuffer.append(entry);
253 263
254 if (isResourceTimingBufferFull()) 264 if (isResourceTimingBufferFull())
255 dispatchEvent(Event::create(EventTypeNames::webkitresourcetimingbufferfu ll)); 265 dispatchEvent(Event::create(EventTypeNames::webkitresourcetimingbufferfu ll));
256 } 266 }
257 267
258 bool PerformanceBase::isResourceTimingBufferFull() 268 bool PerformanceBase::isResourceTimingBufferFull()
259 { 269 {
260 return m_resourceTimingBuffer.size() >= m_resourceTimingBufferSize; 270 return m_resourceTimingBuffer.size() >= m_resourceTimingBufferSize;
261 } 271 }
262 272
263 void PerformanceBase::addRenderTiming(Document* initiatorDocument, unsigned sour ceFrame, double startTime, double finishTime) 273 void PerformanceBase::addRenderTiming(Document* initiatorDocument, unsigned sour ceFrame, double startTime, double finishTime)
264 { 274 {
265 if (isFrameTimingBufferFull()) 275 if (isFrameTimingBufferFull() && !hasObserverFor(PerformanceEntry::Render))
266 return; 276 return;
267 277
268 PerformanceEntry* entry = PerformanceRenderTiming::create(initiatorDocument, sourceFrame, startTime, finishTime); 278 PerformanceEntry* entry = PerformanceRenderTiming::create(initiatorDocument, sourceFrame, startTime, finishTime);
269 addFrameTimingBuffer(entry); 279 notifyObserversOfEntry(entry);
280 if (!isFrameTimingBufferFull())
281 addFrameTimingBuffer(entry);
270 } 282 }
271 283
272 void PerformanceBase::addCompositeTiming(Document* initiatorDocument, unsigned s ourceFrame, double startTime) 284 void PerformanceBase::addCompositeTiming(Document* initiatorDocument, unsigned s ourceFrame, double startTime)
273 { 285 {
274 if (isFrameTimingBufferFull()) 286 if (isFrameTimingBufferFull() && !hasObserverFor(PerformanceEntry::Composite ))
275 return; 287 return;
276 288
277 PerformanceEntry* entry = PerformanceCompositeTiming::create(initiatorDocume nt, sourceFrame, startTime); 289 PerformanceEntry* entry = PerformanceCompositeTiming::create(initiatorDocume nt, sourceFrame, startTime);
278 addFrameTimingBuffer(entry); 290 notifyObserversOfEntry(entry);
291 if (!isFrameTimingBufferFull())
292 addFrameTimingBuffer(entry);
279 } 293 }
280 294
281 void PerformanceBase::addFrameTimingBuffer(PerformanceEntry* entry) 295 void PerformanceBase::addFrameTimingBuffer(PerformanceEntry* entry)
282 { 296 {
283 m_frameTimingBuffer.append(entry); 297 m_frameTimingBuffer.append(entry);
284 298
285 if (isFrameTimingBufferFull()) 299 if (isFrameTimingBufferFull())
286 dispatchEvent(Event::create(EventTypeNames::frametimingbufferfull)); 300 dispatchEvent(Event::create(EventTypeNames::frametimingbufferfull));
287 } 301 }
288 302
289 bool PerformanceBase::isFrameTimingBufferFull() 303 bool PerformanceBase::isFrameTimingBufferFull()
290 { 304 {
291 return m_frameTimingBuffer.size() >= m_frameTimingBufferSize; 305 return m_frameTimingBuffer.size() >= m_frameTimingBufferSize;
292 } 306 }
293 307
294 void PerformanceBase::mark(const String& markName, ExceptionState& exceptionStat e) 308 void PerformanceBase::mark(const String& markName, ExceptionState& exceptionStat e)
295 { 309 {
296 if (!m_userTiming) 310 if (!m_userTiming)
297 m_userTiming = UserTiming::create(this); 311 m_userTiming = UserTiming::create(this);
298 m_userTiming->mark(markName, exceptionState); 312 NewPerformanceEntryCallback callback = WTF::bind<PerformanceEntry*>(&Perform anceBase::notifyObserversOfEntry, this);
313 m_userTiming->mark(markName, callback, exceptionState);
299 } 314 }
300 315
301 void PerformanceBase::clearMarks(const String& markName) 316 void PerformanceBase::clearMarks(const String& markName)
302 { 317 {
303 if (!m_userTiming) 318 if (!m_userTiming)
304 m_userTiming = UserTiming::create(this); 319 m_userTiming = UserTiming::create(this);
305 m_userTiming->clearMarks(markName); 320 m_userTiming->clearMarks(markName);
306 } 321 }
307 322
308 void PerformanceBase::measure(const String& measureName, const String& startMark , const String& endMark, ExceptionState& exceptionState) 323 void PerformanceBase::measure(const String& measureName, const String& startMark , const String& endMark, ExceptionState& exceptionState)
309 { 324 {
310 if (!m_userTiming) 325 if (!m_userTiming)
311 m_userTiming = UserTiming::create(this); 326 m_userTiming = UserTiming::create(this);
312 m_userTiming->measure(measureName, startMark, endMark, exceptionState); 327 NewPerformanceEntryCallback callback = WTF::bind<PerformanceEntry*>(&Perform anceBase::notifyObserversOfEntry, this);
328 m_userTiming->measure(measureName, startMark, endMark, callback, exceptionSt ate);
313 } 329 }
314 330
315 void PerformanceBase::clearMeasures(const String& measureName) 331 void PerformanceBase::clearMeasures(const String& measureName)
316 { 332 {
317 if (!m_userTiming) 333 if (!m_userTiming)
318 m_userTiming = UserTiming::create(this); 334 m_userTiming = UserTiming::create(this);
319 m_userTiming->clearMeasures(measureName); 335 m_userTiming->clearMeasures(measureName);
320 } 336 }
321 337
338 void PerformanceBase::registerPerformanceObserver(PerformanceObserver* observer)
339 {
340 m_observerFilterOptions |= observer->filterOptions();
341 m_observers.add(observer);
342 }
343
344 void PerformanceBase::unregisterPerformanceObserver(PerformanceObserver* oldObse rver)
345 {
346 m_observers.remove(oldObserver);
347 m_observerFilterOptions = PerformanceEntry::Invalid;
348 for (auto& observer : m_observers) {
esprehn 2015/07/24 08:23:12 const auto&
MikeB 2015/07/24 19:30:38 Done.
349 m_observerFilterOptions |= observer->filterOptions();
350 }
351 }
352
353 void PerformanceBase::notifyObserversOfEntry(PerformanceEntry* entry)
354 {
355 for (auto& observer : m_observers) {
356 if (observer->filterOptions() & entry->entryTypeEnum())
357 observer->enqueuePerformanceEntry(entry);
358 }
359 }
360
361 bool PerformanceBase::hasObserverFor(PerformanceEntry::EntryType filterType)
362 {
363 return m_observerFilterOptions & filterType;
364 }
365
322 double PerformanceBase::now() const 366 double PerformanceBase::now() const
323 { 367 {
324 double nowSeconds = monotonicallyIncreasingTime() - m_timeOrigin; 368 double nowSeconds = monotonicallyIncreasingTime() - m_timeOrigin;
325 const double resolutionSeconds = 0.000005; 369 const double resolutionSeconds = 0.000005;
326 return 1000.0 * floor(nowSeconds / resolutionSeconds) * resolutionSeconds; 370 return 1000.0 * floor(nowSeconds / resolutionSeconds) * resolutionSeconds;
327 } 371 }
328 372
329 DEFINE_TRACE(PerformanceBase) 373 DEFINE_TRACE(PerformanceBase)
330 { 374 {
331 visitor->trace(m_frameTimingBuffer); 375 visitor->trace(m_frameTimingBuffer);
332 visitor->trace(m_resourceTimingBuffer); 376 visitor->trace(m_resourceTimingBuffer);
333 visitor->trace(m_userTiming); 377 visitor->trace(m_userTiming);
378 visitor->trace(m_observers);
334 EventTargetWithInlineData::trace(visitor); 379 EventTargetWithInlineData::trace(visitor);
335 } 380 }
336 381
337 } // namespace blink 382 } // namespace blink
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698