Title: [175109] branches/safari-600.3-branch/Source/WebCore
Revision
175109
Author
[email protected]
Date
2014-10-23 02:26:59 -0700 (Thu, 23 Oct 2014)

Log Message

Merged r173132.  rdar://problem/18428706

Modified Paths

Diff

Modified: branches/safari-600.3-branch/Source/WebCore/ChangeLog (175108 => 175109)


--- branches/safari-600.3-branch/Source/WebCore/ChangeLog	2014-10-23 09:25:54 UTC (rev 175108)
+++ branches/safari-600.3-branch/Source/WebCore/ChangeLog	2014-10-23 09:26:59 UTC (rev 175109)
@@ -1,5 +1,44 @@
 2014-10-23  Babak Shafiei  <[email protected]>
 
+        Merge r173132.
+
+    2014-08-29  Gavin Barraclough  <[email protected]>
+
+            DOMTimer::m_nestingLevel is prone to overflow
+            https://bugs.webkit.org/show_bug.cgi?id=136399
+
+            Reviewed by Alexey Proskuryakov.
+
+            Since this would happen after the 2 billionth timer fire this is unlikely,
+            and consequences aren't severe (breaks throttling).
+
+            This change has the following consequences.
+
+                - m_nestingLevel saturates to its max value.
+                - unnested timers are indicated by a nesting level of 0.
+                - repeat timers update m_nestingLevel on every fire,
+                  not just those that should have been throttled.
+
+            The last point is subtle, but ultimately should be inconsequential. Timers
+            whose requested timeout is less that the minimum interval will saturate quickly
+            anyway; timers with an original interval greater than the minimum previously
+            wouldn't have incremented m_nestingLevel, but doing so now doesn't hurt since
+            they won't be throttled when they hit the threshold. This simplifies things
+            conceptually a little & reduces the test performed on each timer fire.
+
+            * page/DOMTimer.cpp:
+            (WebCore::shouldForwardUserGesture):
+                - unnested timers are indicated by a nesting level of 0
+            (WebCore::DOMTimer::DOMTimer):
+                - don't increment nesting level on construction
+            (WebCore::DOMTimer::fired):
+                - saturating increments
+            (WebCore::DOMTimer::adjustMinimumTimerInterval):
+            (WebCore::DOMTimer::intervalClampedToMinimum):
+                - added ASSERTs
+
+2014-10-23  Babak Shafiei  <[email protected]>
+
         Merge r172964.
 
     2014-08-26  Tim Horton  <[email protected]>

Modified: branches/safari-600.3-branch/Source/WebCore/page/DOMTimer.cpp (175108 => 175109)


--- branches/safari-600.3-branch/Source/WebCore/page/DOMTimer.cpp	2014-10-23 09:25:54 UTC (rev 175108)
+++ branches/safari-600.3-branch/Source/WebCore/page/DOMTimer.cpp	2014-10-23 09:26:59 UTC (rev 175109)
@@ -55,12 +55,12 @@
 {
     return UserGestureIndicator::processingUserGesture()
         && interval <= maxIntervalForUserGestureForwarding
-        && nestingLevel == 1; // Gestures should not be forwarded to nested timers.
+        && !nestingLevel; // Gestures should not be forwarded to nested timers.
 }
 
 DOMTimer::DOMTimer(ScriptExecutionContext* context, std::unique_ptr<ScheduledAction> action, int interval, bool singleShot)
     : SuspendableTimer(context)
-    , m_nestingLevel(timerNestingLevel + 1)
+    , m_nestingLevel(timerNestingLevel)
     , m_action(WTF::move(action))
     , m_originalInterval(interval)
     , m_shouldForwardUserGesture(shouldForwardUserGesture(interval, m_nestingLevel))
@@ -130,7 +130,8 @@
         ASSERT(!document->frame()->timersPaused());
     }
 #endif
-    timerNestingLevel = m_nestingLevel;
+    timerNestingLevel = std::min(m_nestingLevel + 1, maxTimerNestingLevel);
+
     ASSERT(!isSuspended());
     ASSERT(!context->activeDOMObjectsAreSuspended());
     UserGestureIndicator gestureIndicator(m_shouldForwardUserGesture ? DefinitelyProcessingUserGesture : PossiblyProcessingUserGesture);
@@ -141,11 +142,14 @@
 
     // Simple case for non-one-shot timers.
     if (isActive()) {
-        double minimumInterval = context->minimumTimerInterval();
-        if (repeatInterval() && repeatInterval() < minimumInterval) {
+        if (m_nestingLevel < maxTimerNestingLevel) {
             m_nestingLevel++;
-            if (m_nestingLevel >= maxTimerNestingLevel)
-                augmentRepeatInterval(minimumInterval - repeatInterval());
+
+            double minimumInterval = context->minimumTimerInterval();
+            if (repeatInterval() && repeatInterval() < minimumInterval) {
+                if (m_nestingLevel == maxTimerNestingLevel)
+                    augmentRepeatInterval(minimumInterval - repeatInterval());
+            }
         }
 
         m_action->execute(context);
@@ -201,6 +205,7 @@
 
 void DOMTimer::adjustMinimumTimerInterval(double oldMinimumTimerInterval)
 {
+    ASSERT(m_nestingLevel <= maxTimerNestingLevel);
     if (m_nestingLevel < maxTimerNestingLevel)
         return;
 
@@ -218,6 +223,8 @@
 
 double DOMTimer::intervalClampedToMinimum(int timeout, double minimumTimerInterval) const
 {
+    ASSERT(m_nestingLevel <= maxTimerNestingLevel);
+
     double intervalMilliseconds = std::max(oneMillisecond, timeout * oneMillisecond);
 
     if (intervalMilliseconds < minimumTimerInterval && m_nestingLevel >= maxTimerNestingLevel)
_______________________________________________
webkit-changes mailing list
[email protected]
https://lists.webkit.org/mailman/listinfo/webkit-changes

Reply via email to