Files
palemoon27/xpcom/threads/nsEventQueue.cpp
T
roytam1 e1c4d9e76f import changes from `dev' branch of rmottola/Arctic-Fox:
- Bug 1077318 - call out to C++ for ARMv6 sub-word atomics. r=luke (2810c3f93)
- Bug 1142593 - factor atomics into the platform layer. r=waldo (f5088b2af)
- Bug 1173642 - Import unimplemented ARM64 Ion components. r=efaust (2567975a1)
- Bug 1170107 part 1 - Call GetProperty/CallProperty from the interpreter and Baseline. r=bhackett (fe45a446a)
- Bug 1170107 part 2 - Don't allocate a wrapper object for (pure) primitive.foo operations. r=bhackett (8793d7d2d)
- Bug 1152079 - Remove Purify support files. r=froydnj (69836c373)
- Bug 1152079 - Remove references to deleted Purify files from moz.build. r=bustage (ebd68a5fa)
- Bug 1126089 - Assert we don't Destroy nsFrameLoader in destructor (r=smaug) (c0894ed2b)
- Bug 1250871 - only send messages to child scripts when the docShell is still around. r=smaug (ac2562f55)
- Bug 1168750 - SharedStubs: (part3) Make split between baseline only and shared stubs, r=jandem (21c89cffe)
- Bug 1168750 - SharedStubs: (part4) Track for which engine a stub needs to get compiled, r=jandem (a36eb943b)
- Bug 1168753 - SharedStubs: Simplification to push BaselineFrame* in stubs, r=jandem (4a26b318d)
- pointer style (e20a50c7e)
- Bug 1169391 - Use a ReservedRooted class for optimized Rooted use in vm/Interpreter.cpp, r=terrence (1b80a857d)
- Bug 1182865 - Relax assertion on the allowed class for home objects, r=efaust (33009a9fe)
- Bug 1154391 - Update import declarations to current ES6 spec r=shu (ad7042d54)
- Bug 1154391 - Update parsing of export declarations to match current ES6 spec r=shu (4b509d9ec)
- Bug 1169171 - Split PNK_DELETE into several different kinds for each of the syntactically distinct modes of |delete| operation, depending upon the syntax of the operand. r=efaust (5667265fc)
- Bug 1169511 - Split PNK_TYPEOF into one kind for application to names one kind for application to other expressions. r=efaust (91a1086d8)
- pointer style (0546201d8)
- Bug 1163851 - Remove the remaining two tests of |pc->parsingForInit|, replacing them with yet another argument provided by the caller. r=efaust (919903e1e)
- Bug 1163851 - |pc->parsingForInit| is dead. Long live |InHandling|! r=efaust (bf35fb405)
- Bug 1167030 - Suppress MSVC warning C4661 in js/src. r=luke (1d28ed1d2)
- Bug 1167845 - Rejigger {in,de}crement/assignment parsing to vet targets primarily through a single Parser::isValidSimpleAssignmentTarget method, so that this method can also be called outside the parser. r=efaust (87484d3fc)
- Bug 1166950 - Introduce a new FunctionKind for class-constructors. r=efaust (e9dd197e1)
- Bug 1166950 - Make generator methods constructors. r=efaust (e076cacd6)
- Bug 1167845 - Rename ParseHandler::isName to ParseHandler::maybeName. r=efaust (1e090741b)
- Bug 1141865 - Part 3: Parse new.target, add Reflect support, and tests. (r=jorendorff, r=shu) (9e0282870)
- Bug 1139759 - Self-host %TypedArray%.prototype.copyWithin. r=till (8beea5f7c)
- pointer style (0da72f30a)
- Bug 1139769 - Add TypedArrayBuffer, TypedArrayByteOffset, and TypedArrayElementShift intrinsics to safely get the relevant information for a typed array. r=till (b5847a441)
- pointer style (5486dd33d)
- Bug 1139769 - Self-host %TypedArray%.prototype.subarray. r=t (b10c55e93)
- pointer style (335ab6c87)
- Bug 1140752 - Land code to self-host %TypedArray%.prototype.set, but don't enable it yet, pending perf-testing. This shouldn't make any changes to the build, except in terms of adding more code to it and affecting binary layout. r=jandem, also much feedback from till that effectively amounts to a review as well (98050308d)
- Bug 1144692: Fix --disable-ion builds; r=h4writer (3be32046c)
- Bug 1148970 - Check for possibly incomplete type sets when double checking the correctness of argument type set information, r=jandem. (934130c2e)
- bug 1171125 - Fix nsStackWalk to build for iOS. r=froydnj (c076c4d22)
- Bug 1119980 - Use 'snprintf' instead of 'sprintf' to avoid a warning on Lollipop-based builds. r=froydnj (a000af66c)
- Bug 1146597 - Avoid unnecessary calls to maybeSweep under hasUnanalyzedPreliminaryObjects, r=jandem. (335ba3fc3)
- Bug 1162134 - IonMonkey MIPS: Fix build failure on MIPS (js/src/jit/CodeGenerator.cpp:6740:28: error: `obj' was not declared in this scope). r=bhackett (56824379b)
- Bug 1160884 followup - Add testcase. r=me (5495ad016)
- Bug 1141865 - Part 4: Remove LCallDirectEvalV in anticipation of register pressure with new.target in eval frames. (r=jandem) (cbb706356)
- Bug 1162242 - Part 1: Remove instances of #ifdef PR_LOGGING. r=froydnj PR_LOGGING is now always defined, we can remove #ifdefs checking for it. (878131a4a)
- revert pointer style for patch (a263375f1)
- Bug 1144097. Fix yet another is<ScopeObject>() assert. r=shu (96d516117)
- Bug 1145282. Reverse the sense of IsValidTerminatingScope and rename it to IsSyntacticScope. r=luke (3681fc831)
- Bug 1149897 - PerformanceStatsService data is not monotonic. r=jandem (927639ac6)
- Bug 1142457 - Compute stopwatch durations per thread on MacOS X. r=jandem, r=areinald (a52c388be)
2020-10-02 18:15:14 +08:00

158 lines
3.8 KiB
C++

/* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
/* vim: set ts=8 sts=2 et sw=2 tw=80: */
/* This Source Code Form is subject to the terms of the Mozilla Public
* License, v. 2.0. If a copy of the MPL was not distributed with this
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
#include "nsEventQueue.h"
#include "nsAutoPtr.h"
#include "mozilla/Logging.h"
#include "nsThreadUtils.h"
#include "prthread.h"
#include "mozilla/ChaosMode.h"
using namespace mozilla;
static PRLogModuleInfo*
GetLog()
{
static PRLogModuleInfo* sLog;
if (!sLog) {
sLog = PR_NewLogModule("nsEventQueue");
}
return sLog;
}
#ifdef LOG
#undef LOG
#endif
#define LOG(args) PR_LOG(GetLog(), PR_LOG_DEBUG, args)
nsEventQueue::nsEventQueue()
: mReentrantMonitor("nsEventQueue.mReentrantMonitor")
, mHead(nullptr)
, mTail(nullptr)
, mOffsetHead(0)
, mOffsetTail(0)
{
}
nsEventQueue::~nsEventQueue()
{
// It'd be nice to be able to assert that no one else is holding the monitor,
// but NSPR doesn't really expose APIs for it.
NS_ASSERTION(IsEmpty(),
"Non-empty event queue being destroyed; events being leaked.");
if (mHead) {
FreePage(mHead);
}
}
bool
nsEventQueue::GetEvent(bool aMayWait, nsIRunnable** aResult)
{
{
ReentrantMonitorAutoEnter mon(mReentrantMonitor);
while (IsEmpty()) {
if (!aMayWait) {
if (aResult) {
*aResult = nullptr;
}
return false;
}
LOG(("EVENTQ(%p): wait begin\n", this));
mon.Wait();
LOG(("EVENTQ(%p): wait end\n", this));
}
if (aResult) {
*aResult = mHead->mEvents[mOffsetHead++];
// Check if mHead points to empty Page
if (mOffsetHead == EVENTS_PER_PAGE) {
Page* dead = mHead;
mHead = mHead->mNext;
FreePage(dead);
mOffsetHead = 0;
}
}
}
return true;
}
void
nsEventQueue::PutEvent(nsIRunnable* aRunnable)
{
// Avoid calling AddRef+Release while holding our monitor.
nsCOMPtr<nsIRunnable> event(aRunnable);
if (ChaosMode::isActive(ChaosMode::ThreadScheduling)) {
// With probability 0.5, yield so other threads have a chance to
// dispatch events to this queue first.
if (ChaosMode::randomUint32LessThan(2)) {
PR_Sleep(PR_INTERVAL_NO_WAIT);
}
}
ReentrantMonitorAutoEnter mon(mReentrantMonitor);
if (!mHead) {
mHead = NewPage();
MOZ_ASSERT(mHead);
mTail = mHead;
mOffsetHead = 0;
mOffsetTail = 0;
} else if (mOffsetTail == EVENTS_PER_PAGE) {
Page* page = NewPage();
MOZ_ASSERT(page);
mTail->mNext = page;
mTail = page;
mOffsetTail = 0;
}
event.swap(mTail->mEvents[mOffsetTail]);
++mOffsetTail;
LOG(("EVENTQ(%p): notify\n", this));
mon.NotifyAll();
}
size_t
nsEventQueue::Count()
{
ReentrantMonitorAutoEnter mon(mReentrantMonitor);
// It is obvious count is 0 when the queue is empty.
if (!mHead) {
return 0;
}
/* How we count the number of events in the queue:
* 1. Let pageCount(x, y) denote the number of pages excluding the tail page
* where x is the index of head page and y is the index of the tail page.
* 2. Then we have pageCount(x, y) = y - x.
*
* Ex: pageCount(0, 0) = 0 where both head and tail pages point to page 0.
* pageCount(0, 1) = 1 where head points to page 0 and tail points page 1.
*
* 3. number of events = (EVENTS_PER_PAGE * pageCount(x, y))
* - (empty slots in head page) + (non-empty slots in tail page)
* = (EVENTS_PER_PAGE * pageCount(x, y)) - mOffsetHead + mOffsetTail
*/
int count = -mOffsetHead;
// Compute (EVENTS_PER_PAGE * pageCount(x, y))
for (Page* page = mHead; page != mTail; page = page->mNext) {
count += EVENTS_PER_PAGE;
}
count += mOffsetTail;
MOZ_ASSERT(count >= 0);
return count;
}