Bug 1382955 (part 2) - Remove nsIPowerManagerService::{powerOff,reboot,restart} and related things. r=gsvelto.

This commit is contained in:
Nicholas Nethercote 2017-08-02 10:09:26 +10:00
Родитель f5c5231809
Коммит a6f655a6c9
13 изменённых файлов: 2 добавлений и 421 удалений

Просмотреть файл

@ -559,7 +559,7 @@ uint64_t ContentParent::sNextTabParentId = 0;
nsDataHashtable<nsUint64HashKey, TabParent*> ContentParent::sNextTabParents;
// This is true when subprocess launching is enabled. This is the
// case between StartUp() and ShutDown() or JoinAllSubprocesses().
// case between StartUp() and ShutDown().
static bool sCanLaunchSubprocesses;
// Set to true if the DISABLE_UNSAFE_CPOW_WARNINGS environment variable is
@ -646,53 +646,6 @@ ContentParent::ShutDown()
#endif
}
/*static*/ void
ContentParent::JoinProcessesIOThread(const nsTArray<ContentParent*>* aProcesses,
Monitor* aMonitor, bool* aDone)
{
const nsTArray<ContentParent*>& processes = *aProcesses;
for (uint32_t i = 0; i < processes.Length(); ++i) {
if (GeckoChildProcessHost* process = processes[i]->mSubprocess) {
process->Join();
}
}
{
MonitorAutoLock lock(*aMonitor);
*aDone = true;
lock.Notify();
}
// Don't touch any arguments to this function from now on.
}
/*static*/ void
ContentParent::JoinAllSubprocesses()
{
MOZ_ASSERT(NS_IsMainThread());
AutoTArray<ContentParent*, 8> processes;
GetAll(processes);
if (processes.IsEmpty()) {
printf_stderr("There are no live subprocesses.");
return;
}
printf_stderr("Subprocesses are still alive. Doing emergency join.\n");
bool done = false;
Monitor monitor("mozilla.dom.ContentParent.JoinAllSubprocesses");
XRE_GetIOMessageLoop()->PostTask(NewRunnableFunction(
&ContentParent::JoinProcessesIOThread,
&processes, &monitor, &done));
{
MonitorAutoLock lock(monitor);
while (!done) {
lock.Wait();
}
}
sCanLaunchSubprocesses = false;
}
/*static*/ uint32_t
ContentParent::GetPoolSize(const nsAString& aContentProcessType)
{

Просмотреть файл

@ -140,14 +140,6 @@ public:
/** Shut down the content-process machinery. */
static void ShutDown();
/**
* Ensure that all subprocesses are terminated and their OS
* resources have been reaped. This is synchronous and can be
* very expensive in general. It also bypasses the normal
* shutdown process.
*/
static void JoinAllSubprocesses();
static uint32_t GetPoolSize(const nsAString& aContentProcessType);
static uint32_t GetMaxProcessCount(const nsAString& aContentProcessType);
@ -671,9 +663,6 @@ private:
static nsDataHashtable<nsUint32HashKey, ContentParent*> *sJSPluginContentParents;
static StaticAutoPtr<LinkedList<ContentParent> > sContentParents;
static void JoinProcessesIOThread(const nsTArray<ContentParent*>* aProcesses,
Monitor* aMonitor, bool* aDone);
static hal::ProcessPriority GetInitialProcessPriority(Element* aFrameElement);
static ContentBridgeParent* CreateContentBridgeParent(const TabContext& aContext,

Просмотреть файл

@ -214,7 +214,6 @@ const char* mozilla::dom::ContentPrefs::gInitPrefs[] = {
"security.sandbox.logging.enabled",
"security.sandbox.mac.track.violations",
"security.sandbox.windows.log.stackTraceDepth",
"shutdown.watchdog.timeoutSecs",
"signed.applets.codebase_principal_support",
"svg.disabled",
"svg.display-lists.hit-testing.enabled",

Просмотреть файл

@ -24,24 +24,6 @@
#include <unistd.h>
#endif
#ifdef ANDROID
#include <android/log.h>
extern "C" char* PrintJSStack();
static void LogFunctionAndJSStack(const char* funcname) {
char *jsstack = PrintJSStack();
__android_log_print(ANDROID_LOG_INFO, "PowerManagerService", \
"Call to %s. The JS stack is:\n%s\n",
funcname,
jsstack ? jsstack : "<no JS stack>");
js_free(jsstack);
}
// bug 839452
#define LOG_FUNCTION_AND_JS_STACK() \
LogFunctionAndJSStack(__PRETTY_FUNCTION__);
#else
#define LOG_FUNCTION_AND_JS_STACK()
#endif
namespace mozilla {
namespace dom {
namespace power {
@ -69,12 +51,6 @@ void
PowerManagerService::Init()
{
RegisterWakeLockObserver(this);
// NB: default to *enabling* the watchdog even when the pref is
// absent, in case the profile might be damaged and we need to
// restart to repair it.
mWatchdogTimeoutSecs =
Preferences::GetInt("shutdown.watchdog.timeoutSecs", 10);
}
PowerManagerService::~PowerManagerService()
@ -119,68 +95,6 @@ PowerManagerService::Notify(const WakeLockInformation& aWakeLockInfo)
}
}
void
PowerManagerService::SyncProfile()
{
nsCOMPtr<nsIObserverService> obsServ = services::GetObserverService();
if (obsServ) {
const char16_t* context = u"shutdown-persist";
obsServ->NotifyObservers(nullptr, "profile-change-net-teardown", context);
obsServ->NotifyObservers(nullptr, "profile-change-teardown", context);
obsServ->NotifyObservers(nullptr, "profile-before-change", context);
obsServ->NotifyObservers(nullptr, "profile-before-change-qm", context);
obsServ->NotifyObservers(nullptr, "profile-before-change-telemetry", context);
}
}
NS_IMETHODIMP
PowerManagerService::Reboot()
{
LOG_FUNCTION_AND_JS_STACK() // bug 839452
StartForceQuitWatchdog(eHalShutdownMode_Reboot, mWatchdogTimeoutSecs);
// To synchronize any unsaved user data before rebooting.
SyncProfile();
hal::Reboot();
MOZ_CRASH("hal::Reboot() shouldn't return");
}
NS_IMETHODIMP
PowerManagerService::PowerOff()
{
LOG_FUNCTION_AND_JS_STACK() // bug 839452
StartForceQuitWatchdog(eHalShutdownMode_PowerOff, mWatchdogTimeoutSecs);
// To synchronize any unsaved user data before powering off.
SyncProfile();
hal::PowerOff();
MOZ_CRASH("hal::PowerOff() shouldn't return");
}
NS_IMETHODIMP
PowerManagerService::Restart()
{
LOG_FUNCTION_AND_JS_STACK() // bug 839452
// FIXME/bug 796826 this implementation is currently gonk-specific,
// because it relies on the Gonk to initialize the Gecko processes to
// restart B2G. It's better to do it here to have a real "restart".
StartForceQuitWatchdog(eHalShutdownMode_Restart, mWatchdogTimeoutSecs);
// Ensure all content processes are dead before we continue
// restarting. This code is used to restart to apply updates, and
// if we don't join all the subprocesses, race conditions can cause
// them to see an inconsistent view of the application directory.
ContentParent::JoinAllSubprocesses();
// To synchronize any unsaved user data before restarting.
SyncProfile();
#ifdef XP_UNIX
sync();
#endif
_exit(0);
MOZ_CRASH("_exit() shouldn't return");
}
NS_IMETHODIMP
PowerManagerService::AddWakeLockListener(nsIDOMMozWakeLockListener *aListener)
{

Просмотреть файл

@ -32,9 +32,7 @@ public:
NS_DECL_ISUPPORTS
NS_DECL_NSIPOWERMANAGERSERVICE
PowerManagerService()
: mWatchdogTimeoutSecs(0)
{}
PowerManagerService() {}
static already_AddRefed<PowerManagerService> GetInstance();
@ -70,13 +68,9 @@ private:
void ComputeWakeLockState(const hal::WakeLockInformation& aWakeLockInfo,
nsAString &aState);
void SyncProfile();
static StaticRefPtr<PowerManagerService> sSingleton;
nsTArray<nsCOMPtr<nsIDOMMozWakeLockListener>> mWakeLockListeners;
int32_t mWatchdogTimeoutSecs;
};
} // namespace power

Просмотреть файл

@ -19,21 +19,6 @@ interface mozIDOMWindow;
[scriptable, builtinclass, uuid(ba7ca4c1-9d92-4425-a83b-85dd7fa953f7)]
interface nsIPowerManagerService : nsISupports
{
/**
* This API will power off the machine.
*/
void powerOff();
/**
* This API will completely shut down and boot the machine.
*/
void reboot();
/**
* This API will restart the Gecko processes without powering off the machine.
*/
void restart();
void addWakeLockListener(in nsIDOMMozWakeLockListener aListener);
void removeWakeLockListener(in nsIDOMMozWakeLockListener aListener);
DOMString getWakeLockState(in DOMString aTopic);

Просмотреть файл

@ -646,27 +646,6 @@ NotifyNetworkChange(const NetworkInformation& aInfo)
NetworkObservers().BroadcastCachedInformation();
}
void Reboot()
{
AssertMainProcess();
AssertMainThread();
PROXY_IF_SANDBOXED(Reboot());
}
void PowerOff()
{
AssertMainProcess();
AssertMainThread();
PROXY_IF_SANDBOXED(PowerOff());
}
void StartForceQuitWatchdog(ShutdownMode aMode, int32_t aTimeoutSecs)
{
AssertMainProcess();
AssertMainThread();
PROXY_IF_SANDBOXED(StartForceQuitWatchdog(aMode, aTimeoutSecs));
}
void
RegisterWakeLockObserver(WakeLockObserver* aObserver)
{

Просмотреть файл

@ -290,20 +290,6 @@ void UnregisterSystemTimezoneChangeObserver(
void NotifySystemTimezoneChange(
const hal::SystemTimezoneChangeInformation& aSystemTimezoneChangeInfo);
/**
* Reboot the device.
*
* This API is currently only allowed to be used from the main process.
*/
void Reboot();
/**
* Power off the device.
*
* This API is currently only allowed to be used from the main process.
*/
void PowerOff();
/**
* Enable wake lock notifications from the backend.
*
@ -460,15 +446,6 @@ void SetCurrentThreadPriority(hal::ThreadPriority aThreadPriority);
void SetThreadPriority(PlatformThreadId aThreadId,
hal::ThreadPriority aThreadPriority);
/**
* Start a watchdog to compulsively shutdown the system if it hangs.
* @param aMode Specify how to shutdown the system.
* @param aTimeoutSecs Specify the delayed seconds to shutdown the system.
*
* This API is currently only allowed to be used from the main process.
*/
void StartForceQuitWatchdog(hal::ShutdownMode aMode, int32_t aTimeoutSecs);
/**
* Start monitoring disk space for low space situations.
*

Просмотреть файл

@ -20,19 +20,6 @@ namespace hal {
const uint64_t CONTENT_PROCESS_ID_UNKNOWN = uint64_t(-1);
const uint64_t CONTENT_PROCESS_ID_MAIN = 0;
/**
* These are defined by libhardware, specifically, hardware/libhardware/include/hardware/lights.h
* in the gonk subsystem.
* If these change and are exposed to JS, make sure nsIHal.idl is updated as well.
*/
enum ShutdownMode {
eHalShutdownMode_Unknown = -1,
eHalShutdownMode_PowerOff = 0,
eHalShutdownMode_Reboot = 1,
eHalShutdownMode_Restart = 2,
eHalShutdownMode_Count = 3
};
class SwitchEvent;
enum SwitchDevice {
@ -119,17 +106,6 @@ enum WakeLockControl {
namespace IPC {
/**
* Serializer for ShutdownMode.
*/
template <>
struct ParamTraits<mozilla::hal::ShutdownMode>
: public ContiguousEnumSerializer<
mozilla::hal::ShutdownMode,
mozilla::hal::eHalShutdownMode_Unknown,
mozilla::hal::eHalShutdownMode_Count>
{};
/**
* WakeLockControl serializer.
*/

Просмотреть файл

@ -1,25 +0,0 @@
/* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
/* vim: set sw=2 ts=8 et ft=cpp : */
/* 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 "Hal.h"
namespace mozilla {
namespace hal_impl {
void
Reboot()
{}
void
PowerOff()
{}
void
StartForceQuitWatchdog(hal::ShutdownMode aMode, int32_t aTimeoutSecs)
{}
} // namespace hal_impl
} // namespace mozilla

Просмотреть файл

@ -1,136 +0,0 @@
/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
/* 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 "Hal.h"
#include "HalLog.h"
#include <unistd.h>
#include <sys/reboot.h>
#include "nsIObserverService.h"
#include "mozilla/Services.h"
#include "MainThreadUtils.h"
namespace mozilla {
namespace hal_impl {
void
Reboot()
{
if (NS_IsMainThread()) {
nsCOMPtr<nsIObserverService> obsServ = services::GetObserverService();
if (obsServ) {
obsServ->NotifyObservers(nullptr, "system-reboot", nullptr);
}
}
sync();
reboot(RB_AUTOBOOT);
}
void
PowerOff()
{
if (NS_IsMainThread()) {
nsCOMPtr<nsIObserverService> obsServ = services::GetObserverService();
if (obsServ) {
obsServ->NotifyObservers(nullptr, "system-power-off", nullptr);
}
}
sync();
reboot(RB_POWER_OFF);
}
// Structure to specify how watchdog pthread is going to work.
typedef struct watchdogParam
{
hal::ShutdownMode mode; // Specify how to shutdown the system.
int32_t timeoutSecs; // Specify the delayed seconds to shutdown the system.
watchdogParam(hal::ShutdownMode aMode, int32_t aTimeoutSecs)
: mode(aMode), timeoutSecs(aTimeoutSecs) {}
} watchdogParam_t;
// Function to complusively shut down the system with a given mode.
static void
QuitHard(hal::ShutdownMode aMode)
{
switch (aMode)
{
case hal::eHalShutdownMode_PowerOff:
PowerOff();
break;
case hal::eHalShutdownMode_Reboot:
Reboot();
break;
case hal::eHalShutdownMode_Restart:
// Don't let signal handlers affect forced shutdown.
kill(0, SIGKILL);
// If we can't SIGKILL our process group, something is badly
// wrong. Trying to deliver a catch-able signal to ourselves can
// invoke signal handlers and might cause problems. So try
// _exit() and hope we go away.
_exit(1);
break;
default:
MOZ_CRASH();
}
}
// Function to complusively shut down the system with a given mode when timeout.
static void*
ForceQuitWatchdog(void* aParamPtr)
{
watchdogParam_t* paramPtr = reinterpret_cast<watchdogParam_t*>(aParamPtr);
if (paramPtr->timeoutSecs > 0 && paramPtr->timeoutSecs <= 30) {
// If we shut down normally before the timeout, this thread will
// be harmlessly reaped by the OS.
TimeStamp deadline =
(TimeStamp::Now() + TimeDuration::FromSeconds(paramPtr->timeoutSecs));
while (true) {
TimeDuration remaining = (deadline - TimeStamp::Now());
int sleepSeconds = int(remaining.ToSeconds());
if (sleepSeconds <= 0) {
break;
}
sleep(sleepSeconds);
}
}
hal::ShutdownMode mode = paramPtr->mode;
delete paramPtr;
QuitHard(mode);
return nullptr;
}
void
StartForceQuitWatchdog(hal::ShutdownMode aMode, int32_t aTimeoutSecs)
{
// Force-quits are intepreted a little more ferociously on Gonk,
// because while Gecko is in the process of shutting down, the user
// can't call 911, for example. And if we hang on shutdown, bad
// things happen. So, make sure that doesn't happen.
if (aTimeoutSecs <= 0) {
return;
}
// Use a raw pthread here to insulate ourselves from bugs in other
// Gecko code that we're trying to protect!
//
// Note that we let the watchdog in charge of releasing |paramPtr|
// if the pthread is successfully created.
watchdogParam_t* paramPtr = new watchdogParam_t(aMode, aTimeoutSecs);
pthread_t watchdog;
if (pthread_create(&watchdog, nullptr,
ForceQuitWatchdog,
reinterpret_cast<void*>(paramPtr))) {
// Better safe than sorry.
delete paramPtr;
QuitHard(aMode);
}
// The watchdog thread is off and running now.
}
} // hal_impl
} // mozilla

Просмотреть файл

@ -38,7 +38,6 @@ if CONFIG['MOZ_WIDGET_TOOLKIT'] == 'android':
]
UNIFIED_SOURCES += [
'android/AndroidSensor.cpp',
'fallback/FallbackPower.cpp',
'linux/LinuxMemory.cpp',
]
# AndroidHal.cpp cannot be built in unified mode because it relies on HalImpl.h.
@ -51,7 +50,6 @@ elif CONFIG['OS_TARGET'] == 'Linux':
'fallback/FallbackSensor.cpp',
'fallback/FallbackVibration.cpp',
'linux/LinuxMemory.cpp',
'linux/LinuxPower.cpp',
]
if CONFIG['MOZ_ENABLE_DBUS']:
UNIFIED_SOURCES += [
@ -64,7 +62,6 @@ elif CONFIG['OS_TARGET'] == 'Linux':
elif CONFIG['OS_TARGET'] == 'WINNT':
UNIFIED_SOURCES += [
'fallback/FallbackMemory.cpp',
'fallback/FallbackPower.cpp',
'fallback/FallbackScreenConfiguration.cpp',
'fallback/FallbackVibration.cpp',
'windows/WindowsSensor.cpp',
@ -77,14 +74,12 @@ elif CONFIG['MOZ_WIDGET_TOOLKIT'] == 'cocoa':
UNIFIED_SOURCES += [
'cocoa/CocoaBattery.cpp',
'fallback/FallbackMemory.cpp',
'fallback/FallbackPower.cpp',
'fallback/FallbackScreenConfiguration.cpp',
'fallback/FallbackVibration.cpp',
]
elif CONFIG['OS_TARGET'] in ('OpenBSD', 'NetBSD', 'FreeBSD', 'DragonFly'):
UNIFIED_SOURCES += [
'fallback/FallbackMemory.cpp',
'fallback/FallbackPower.cpp',
'fallback/FallbackScreenConfiguration.cpp',
'fallback/FallbackSensor.cpp',
'fallback/FallbackVibration.cpp',
@ -101,7 +96,6 @@ else:
UNIFIED_SOURCES += [
'fallback/FallbackBattery.cpp',
'fallback/FallbackMemory.cpp',
'fallback/FallbackPower.cpp',
'fallback/FallbackScreenConfiguration.cpp',
'fallback/FallbackSensor.cpp',
'fallback/FallbackVibration.cpp',

Просмотреть файл

@ -244,24 +244,6 @@ DisableSystemTimezoneChangeNotifications()
Hal()->SendDisableSystemTimezoneChangeNotifications();
}
void
Reboot()
{
MOZ_CRASH("Reboot() can't be called from sandboxed contexts.");
}
void
PowerOff()
{
MOZ_CRASH("PowerOff() can't be called from sandboxed contexts.");
}
void
StartForceQuitWatchdog(ShutdownMode aMode, int32_t aTimeoutSecs)
{
MOZ_CRASH("StartForceQuitWatchdog() can't be called from sandboxed contexts.");
}
void
EnableSensorNotifications(SensorType aSensor) {
Hal()->SendEnableSensorNotifications(aSensor);