mirror of
https://gitlab.winehq.org/wine/wine-gecko.git
synced 2024-09-13 09:24:08 -07:00
Backed out changeset 1c6223f7c74f (bug 876029) for Android armv6 mochitest-1/3 crahes.
This commit is contained in:
parent
451cdd58c6
commit
3e3b5b26c1
@ -11,7 +11,6 @@
|
|||||||
#include "mozilla/Services.h"
|
#include "mozilla/Services.h"
|
||||||
#include "nsIObserver.h"
|
#include "nsIObserver.h"
|
||||||
#include "nsIObserverService.h"
|
#include "nsIObserverService.h"
|
||||||
#include "nsMemoryPressure.h"
|
|
||||||
#include "nsThreadUtils.h"
|
#include "nsThreadUtils.h"
|
||||||
#include <errno.h>
|
#include <errno.h>
|
||||||
#include <fcntl.h>
|
#include <fcntl.h>
|
||||||
@ -25,6 +24,37 @@ using namespace mozilla;
|
|||||||
|
|
||||||
namespace {
|
namespace {
|
||||||
|
|
||||||
|
class MemoryPressureRunnable : public nsRunnable
|
||||||
|
{
|
||||||
|
const char *mTopic;
|
||||||
|
const PRUnichar *mData;
|
||||||
|
public:
|
||||||
|
MemoryPressureRunnable(const char *aTopic, const PRUnichar *aData) :
|
||||||
|
mTopic(aTopic), mData(aData)
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
NS_IMETHOD Run()
|
||||||
|
{
|
||||||
|
MOZ_ASSERT(NS_IsMainThread());
|
||||||
|
LOG("Dispatching low-memory memory-pressure event");
|
||||||
|
|
||||||
|
nsCOMPtr<nsIObserverService> os = services::GetObserverService();
|
||||||
|
if (os) {
|
||||||
|
os->NotifyObservers(nullptr, mTopic, mData);
|
||||||
|
}
|
||||||
|
return NS_OK;
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
static void
|
||||||
|
Dispatch(const char *aTopic, const PRUnichar *aData)
|
||||||
|
{
|
||||||
|
nsRefPtr<MemoryPressureRunnable> memoryPressureRunnable =
|
||||||
|
new MemoryPressureRunnable(aTopic, aData);
|
||||||
|
NS_DispatchToMainThread(memoryPressureRunnable);
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* MemoryPressureWatcher watches sysfs from its own thread to notice when the
|
* MemoryPressureWatcher watches sysfs from its own thread to notice when the
|
||||||
* system is under memory pressure. When we observe memory pressure, we use
|
* system is under memory pressure. When we observe memory pressure, we use
|
||||||
@ -156,8 +186,8 @@ public:
|
|||||||
|
|
||||||
// We use low-memory-no-forward because each process has its own watcher
|
// We use low-memory-no-forward because each process has its own watcher
|
||||||
// and thus there is no need for the main process to forward this event.
|
// and thus there is no need for the main process to forward this event.
|
||||||
rv = NS_DispatchMemoryPressure(MemPressure_New);
|
Dispatch("memory-pressure",
|
||||||
NS_ENSURE_SUCCESS(rv, rv);
|
NS_LITERAL_STRING("low-memory-no-forward").get());
|
||||||
|
|
||||||
// Manually check lowMemFd until we observe that memory pressure is over.
|
// Manually check lowMemFd until we observe that memory pressure is over.
|
||||||
// We won't fire any more low-memory events until we observe that
|
// We won't fire any more low-memory events until we observe that
|
||||||
@ -189,8 +219,8 @@ public:
|
|||||||
NS_ENSURE_SUCCESS(rv, rv);
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
if (memoryPressure) {
|
if (memoryPressure) {
|
||||||
rv = NS_DispatchMemoryPressure(MemPressure_Ongoing);
|
Dispatch("memory-pressure",
|
||||||
NS_ENSURE_SUCCESS(rv, rv);
|
NS_LITERAL_STRING("low-memory-ongoing-no-forward").get());
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
} while (false);
|
} while (false);
|
||||||
|
@ -15,7 +15,6 @@
|
|||||||
#include "nsIObserverService.h"
|
#include "nsIObserverService.h"
|
||||||
#include "nsIRunnable.h"
|
#include "nsIRunnable.h"
|
||||||
#include "nsISupports.h"
|
#include "nsISupports.h"
|
||||||
#include "nsMemoryPressure.h"
|
|
||||||
#include "nsPrintfCString.h"
|
#include "nsPrintfCString.h"
|
||||||
#include "nsThread.h"
|
#include "nsThread.h"
|
||||||
|
|
||||||
@ -188,7 +187,7 @@ bool MaybeScheduleMemoryPressureEvent()
|
|||||||
sLastLowMemoryNotificationTime = PR_IntervalNow();
|
sLastLowMemoryNotificationTime = PR_IntervalNow();
|
||||||
|
|
||||||
LOG("Scheduling memory pressure notification.");
|
LOG("Scheduling memory pressure notification.");
|
||||||
NS_DispatchEventualMemoryPressure(MemPressure_New);
|
ScheduleMemoryPressureEvent();
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -213,7 +212,7 @@ void CheckMemAvailable()
|
|||||||
// so don't worry about firing this notification too often.
|
// so don't worry about firing this notification too often.
|
||||||
LOG("Detected low virtual memory.");
|
LOG("Detected low virtual memory.");
|
||||||
PR_ATOMIC_INCREMENT(&sNumLowVirtualMemEvents);
|
PR_ATOMIC_INCREMENT(&sNumLowVirtualMemEvents);
|
||||||
NS_DispatchEventualMemoryPressure(MemPressure_New);
|
ScheduleMemoryPressureEvent();
|
||||||
}
|
}
|
||||||
else if (stat.ullAvailPageFile < sLowCommitSpaceThreshold * 1024 * 1024) {
|
else if (stat.ullAvailPageFile < sLowCommitSpaceThreshold * 1024 * 1024) {
|
||||||
LOG("Detected low available page file space.");
|
LOG("Detected low available page file space.");
|
||||||
|
@ -24,7 +24,6 @@ MODULE = 'xpcom'
|
|||||||
|
|
||||||
EXPORTS += [
|
EXPORTS += [
|
||||||
'nsEventQueue.h',
|
'nsEventQueue.h',
|
||||||
'nsMemoryPressure.h',
|
|
||||||
'nsProcess.h',
|
'nsProcess.h',
|
||||||
'nsThread.h',
|
'nsThread.h',
|
||||||
]
|
]
|
||||||
@ -41,7 +40,6 @@ CPP_SOURCES += [
|
|||||||
'TimerThread.cpp',
|
'TimerThread.cpp',
|
||||||
'nsEnvironment.cpp',
|
'nsEnvironment.cpp',
|
||||||
'nsEventQueue.cpp',
|
'nsEventQueue.cpp',
|
||||||
'nsMemoryPressure.cpp',
|
|
||||||
'nsProcessCommon.cpp',
|
'nsProcessCommon.cpp',
|
||||||
'nsThread.cpp',
|
'nsThread.cpp',
|
||||||
'nsThreadManager.cpp',
|
'nsThreadManager.cpp',
|
||||||
|
@ -1,48 +0,0 @@
|
|||||||
#include "nsMemoryPressure.h"
|
|
||||||
#include "mozilla/Assertions.h"
|
|
||||||
#include "mozilla/Atomics.h"
|
|
||||||
|
|
||||||
#include "nsThreadUtils.h"
|
|
||||||
|
|
||||||
using namespace mozilla;
|
|
||||||
|
|
||||||
static Atomic<int32_t, Relaxed> sMemoryPressurePending;
|
|
||||||
MOZ_STATIC_ASSERT(MemPressure_None == 0,
|
|
||||||
"Bad static initialization with the default constructor.");
|
|
||||||
|
|
||||||
MemoryPressureState
|
|
||||||
NS_GetPendingMemoryPressure()
|
|
||||||
{
|
|
||||||
int32_t value = sMemoryPressurePending.exchange(MemPressure_None);
|
|
||||||
return MemoryPressureState(value);
|
|
||||||
}
|
|
||||||
|
|
||||||
void
|
|
||||||
NS_DispatchEventualMemoryPressure(MemoryPressureState state)
|
|
||||||
{
|
|
||||||
/*
|
|
||||||
* A new memory pressure event erases an ongoing memory pressure, but an
|
|
||||||
* existing "new" memory pressure event takes precedence over a new "ongoing"
|
|
||||||
* memory pressure event.
|
|
||||||
*/
|
|
||||||
switch (state) {
|
|
||||||
case MemPressure_None:
|
|
||||||
sMemoryPressurePending = MemPressure_None;
|
|
||||||
break;
|
|
||||||
case MemPressure_New:
|
|
||||||
sMemoryPressurePending = MemPressure_New;
|
|
||||||
break;
|
|
||||||
case MemPressure_Ongoing:
|
|
||||||
sMemoryPressurePending.compareExchange(MemPressure_None, MemPressure_Ongoing);
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
nsresult
|
|
||||||
NS_DispatchMemoryPressure(MemoryPressureState state)
|
|
||||||
{
|
|
||||||
NS_DispatchEventualMemoryPressure(state);
|
|
||||||
nsCOMPtr<nsIRunnable> event = new nsRunnable;
|
|
||||||
NS_ENSURE_TRUE(event, NS_ERROR_OUT_OF_MEMORY);
|
|
||||||
return NS_DispatchToMainThread(event);
|
|
||||||
}
|
|
@ -1,76 +0,0 @@
|
|||||||
/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
|
|
||||||
/* vim:set ts=2 sw=2 sts=2 et cindent: */
|
|
||||||
/* 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/. */
|
|
||||||
|
|
||||||
#ifndef nsMemoryPressure_h__
|
|
||||||
#define nsMemoryPressure_h__
|
|
||||||
|
|
||||||
#include "nscore.h"
|
|
||||||
|
|
||||||
enum MemoryPressureState {
|
|
||||||
/*
|
|
||||||
* No memory pressure.
|
|
||||||
*/
|
|
||||||
MemPressure_None = 0,
|
|
||||||
|
|
||||||
/*
|
|
||||||
* New memory pressure deteced.
|
|
||||||
*
|
|
||||||
* On a new memory pressure, we stop everything to start cleaning
|
|
||||||
* aggresively the memory used, in order to free as much memory as
|
|
||||||
* possible.
|
|
||||||
*/
|
|
||||||
MemPressure_New,
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Repeated memory pressure.
|
|
||||||
*
|
|
||||||
* A repeated memory pressure implies to clean softly recent allocations.
|
|
||||||
* It is supposed to happen after a new memory pressure which already
|
|
||||||
* cleaned aggressivley. So there is no need to damage the reactivity of
|
|
||||||
* Gecko by stopping the world again.
|
|
||||||
*
|
|
||||||
* In case of conflict with an new memory pressue, the new memory pressure
|
|
||||||
* takes precedence over an ongoing memory pressure. The reason being
|
|
||||||
* that if no events are processed between 2 notifications (new followed
|
|
||||||
* by ongoing, or ongoing followed by a new) we want to be as aggresive as
|
|
||||||
* possible on the clean-up of the memory. After all, we are trying to
|
|
||||||
* keep Gecko alive as long as possible.
|
|
||||||
*/
|
|
||||||
MemPressure_Ongoing
|
|
||||||
};
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Return and erase the latest state of the memory pressure event set by any of
|
|
||||||
* the corresponding dispatch function.
|
|
||||||
*/
|
|
||||||
MemoryPressureState
|
|
||||||
NS_GetPendingMemoryPressure();
|
|
||||||
|
|
||||||
/**
|
|
||||||
* This function causes the main thread to fire a memory pressure event
|
|
||||||
* before processing the next event, but if there are no events pending in
|
|
||||||
* the main thread's event queue, the memory pressure event would not be
|
|
||||||
* dispatched until one is enqueued. It is infallible and does not allocate
|
|
||||||
* any memory.
|
|
||||||
*
|
|
||||||
* You may call this function from any thread.
|
|
||||||
*/
|
|
||||||
void
|
|
||||||
NS_DispatchEventualMemoryPressure(MemoryPressureState state);
|
|
||||||
|
|
||||||
/**
|
|
||||||
* This function causes the main thread to fire a memory pressure event
|
|
||||||
* before processing the next event. We wake up the main thread by adding a
|
|
||||||
* dummy event to its event loop, so, unlike with
|
|
||||||
* NS_DispatchEventualMemoryPressure, this memory-pressure event is always
|
|
||||||
* fired relatively quickly, even if the event loop is otherwise empty.
|
|
||||||
*
|
|
||||||
* You may call this function from any thread.
|
|
||||||
*/
|
|
||||||
nsresult
|
|
||||||
NS_DispatchMemoryPressure(MemoryPressureState state);
|
|
||||||
|
|
||||||
#endif // nsMemoryPressure_h__
|
|
@ -5,7 +5,6 @@
|
|||||||
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
|
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
|
||||||
|
|
||||||
#include "mozilla/ReentrantMonitor.h"
|
#include "mozilla/ReentrantMonitor.h"
|
||||||
#include "nsMemoryPressure.h"
|
|
||||||
#include "nsThread.h"
|
#include "nsThread.h"
|
||||||
#include "nsThreadManager.h"
|
#include "nsThreadManager.h"
|
||||||
#include "nsIClassInfoImpl.h"
|
#include "nsIClassInfoImpl.h"
|
||||||
@ -58,6 +57,23 @@ NS_DECL_CI_INTERFACE_GETTER(nsThread)
|
|||||||
|
|
||||||
nsIThreadObserver* nsThread::sMainThreadObserver = nullptr;
|
nsIThreadObserver* nsThread::sMainThreadObserver = nullptr;
|
||||||
|
|
||||||
|
namespace mozilla {
|
||||||
|
|
||||||
|
// Fun fact: Android's GCC won't convert bool* to int32_t*, so we can't
|
||||||
|
// PR_ATOMIC_SET a bool.
|
||||||
|
static int32_t sMemoryPressurePending = 0;
|
||||||
|
|
||||||
|
/*
|
||||||
|
* It's important that this function not acquire any locks, nor do anything
|
||||||
|
* which might cause malloc to run.
|
||||||
|
*/
|
||||||
|
void ScheduleMemoryPressureEvent()
|
||||||
|
{
|
||||||
|
PR_ATOMIC_SET(&sMemoryPressurePending, 1);
|
||||||
|
}
|
||||||
|
|
||||||
|
} // namespace mozilla
|
||||||
|
|
||||||
//-----------------------------------------------------------------------------
|
//-----------------------------------------------------------------------------
|
||||||
// Because we do not have our own nsIFactory, we have to implement nsIClassInfo
|
// Because we do not have our own nsIFactory, we have to implement nsIClassInfo
|
||||||
// somewhat manually.
|
// somewhat manually.
|
||||||
@ -564,20 +580,14 @@ nsThread::ProcessNextEvent(bool mayWait, bool *result)
|
|||||||
// Fire a memory pressure notification, if we're the main thread and one is
|
// Fire a memory pressure notification, if we're the main thread and one is
|
||||||
// pending.
|
// pending.
|
||||||
if (MAIN_THREAD == mIsMainThread && !ShuttingDown()) {
|
if (MAIN_THREAD == mIsMainThread && !ShuttingDown()) {
|
||||||
MemoryPressureState mpPending = NS_GetPendingMemoryPressure();
|
bool mpPending = PR_ATOMIC_SET(&sMemoryPressurePending, 0);
|
||||||
if (mpPending != MemPressure_None) {
|
if (mpPending) {
|
||||||
nsCOMPtr<nsIObserverService> os = services::GetObserverService();
|
nsCOMPtr<nsIObserverService> os = services::GetObserverService();
|
||||||
|
|
||||||
// Use no-forward to prevent the notifications from being transferred to
|
|
||||||
// the children of this process.
|
|
||||||
NS_NAMED_LITERAL_STRING(lowMem, "low-memory-no-forward");
|
|
||||||
NS_NAMED_LITERAL_STRING(lowMemOngoing, "low-memory-ongoing-no-forward");
|
|
||||||
|
|
||||||
if (os) {
|
if (os) {
|
||||||
os->NotifyObservers(nullptr, "memory-pressure",
|
os->NotifyObservers(nullptr, "memory-pressure",
|
||||||
mpPending == MemPressure_New ? lowMem.get() :
|
NS_LITERAL_STRING("low-memory").get());
|
||||||
lowMemOngoing.get());
|
}
|
||||||
} else {
|
else {
|
||||||
NS_WARNING("Can't get observer service!");
|
NS_WARNING("Can't get observer service!");
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -128,4 +128,16 @@ private:
|
|||||||
nsresult mResult;
|
nsresult mResult;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
namespace mozilla {
|
||||||
|
|
||||||
|
/**
|
||||||
|
* This function causes the main thread to fire a memory pressure event at its
|
||||||
|
* next available opportunity.
|
||||||
|
*
|
||||||
|
* You may call this function from any thread.
|
||||||
|
*/
|
||||||
|
void ScheduleMemoryPressureEvent();
|
||||||
|
|
||||||
|
} // namespace mozilla
|
||||||
|
|
||||||
#endif // nsThread_h__
|
#endif // nsThread_h__
|
||||||
|
Loading…
Reference in New Issue
Block a user