1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
|
From f6d39ec03896eaf5d30d79d8165263c98e957749 Mon Sep 17 00:00:00 2001
From: Nathan Froyd <froydnj@mozilla.com>
Date: Fri, 6 Feb 2015 16:19:36 -0500
Subject: [PATCH] Bug 1036515 - Narrow the scope of unlocking mMonitor in
nsTimerImpl::PostTimerEvents. r=bsmedberg, a=abillings
---
xpcom/threads/TimerThread.cpp | 55 ++++++++++++++++++++++---------------------
1 file changed, 28 insertions(+), 27 deletions(-)
diff --git a/xpcom/threads/TimerThread.cpp b/xpcom/threads/TimerThread.cpp
index bd586c9..b95846f 100644
--- a/xpcom/threads/TimerThread.cpp
+++ b/xpcom/threads/TimerThread.cpp
@@ -239,43 +239,44 @@ NS_IMETHODIMP TimerThread::Run()
RemoveTimerInternal(timer);
timer = nullptr;
+#ifdef DEBUG_TIMERS
+ if (PR_LOG_TEST(GetTimerLog(), PR_LOG_DEBUG)) {
+ PR_LOG(GetTimerLog(), PR_LOG_DEBUG,
+ ("Timer thread woke up %fms from when it was supposed to\n",
+ fabs((now - timerRef->mTimeout).ToMilliseconds())));
+ }
+#endif
+
{
// We release mMonitor around the Fire call to avoid deadlock.
MonitorAutoUnlock unlock(mMonitor);
-#ifdef DEBUG_TIMERS
- if (PR_LOG_TEST(GetTimerLog(), PR_LOG_DEBUG)) {
- PR_LOG(GetTimerLog(), PR_LOG_DEBUG,
- ("Timer thread woke up %fms from when it was supposed to\n",
- fabs((now - timerRef->mTimeout).ToMilliseconds())));
- }
-#endif
// We are going to let the call to PostTimerEvent here handle the
// release of the timer so that we don't end up releasing the timer
// on the TimerThread instead of on the thread it targets.
timerRef = nsTimerImpl::PostTimerEvent(timerRef.forget());
+ }
- if (timerRef) {
- // We got our reference back due to an error.
- // Unhook the nsRefPtr, and release manually so we can get the
- // refcount.
- nsrefcnt rc = timerRef.forget().take()->Release();
- (void)rc;
-
- // The nsITimer interface requires that its users keep a reference
- // to the timers they use while those timers are initialized but
- // have not yet fired. If this ever happens, it is a bug in the
- // code that created and used the timer.
- //
- // Further, note that this should never happen even with a
- // misbehaving user, because nsTimerImpl::Release checks for a
- // refcount of 1 with an armed timer (a timer whose only reference
- // is from the timer thread) and when it hits this will remove the
- // timer from the timer thread and thus destroy the last reference,
- // preventing this situation from occurring.
- MOZ_ASSERT(rc != 0, "destroyed timer off its target thread!");
- }
+ if (timerRef) {
+ // We got our reference back due to an error.
+ // Unhook the nsRefPtr, and release manually so we can get the
+ // refcount.
+ nsrefcnt rc = timerRef.forget().take()->Release();
+ (void)rc;
+
+ // The nsITimer interface requires that its users keep a reference
+ // to the timers they use while those timers are initialized but
+ // have not yet fired. If this ever happens, it is a bug in the
+ // code that created and used the timer.
+ //
+ // Further, note that this should never happen even with a
+ // misbehaving user, because nsTimerImpl::Release checks for a
+ // refcount of 1 with an armed timer (a timer whose only reference
+ // is from the timer thread) and when it hits this will remove the
+ // timer from the timer thread and thus destroy the last reference,
+ // preventing this situation from occurring.
+ MOZ_ASSERT(rc != 0, "destroyed timer off its target thread!");
}
if (mShutdown)
--
2.2.1
|