Switch PPluginModule from PCrashReporter to shmem-based CrashReportHost/Client. (bug 1338281 part 5, r=billm)
This commit is contained in:
@@ -10,7 +10,6 @@
|
||||
#include "mozilla/Attributes.h"
|
||||
#include "mozilla/dom/ContentParent.h"
|
||||
#include "mozilla/dom/ContentChild.h"
|
||||
#include "mozilla/dom/PCrashReporterParent.h"
|
||||
#include "mozilla/ipc/GeckoChildProcessHost.h"
|
||||
#include "mozilla/ipc/MessageChannel.h"
|
||||
#include "mozilla/ipc/ProtocolUtils.h"
|
||||
@@ -67,15 +66,14 @@ using mozilla::ProfileGatherer;
|
||||
#endif
|
||||
using mozilla::ipc::MessageChannel;
|
||||
using mozilla::ipc::GeckoChildProcessHost;
|
||||
using mozilla::dom::PCrashReporterParent;
|
||||
using mozilla::dom::CrashReporterParent;
|
||||
|
||||
using namespace mozilla;
|
||||
using namespace mozilla::plugins;
|
||||
using namespace mozilla::plugins::parent;
|
||||
|
||||
#ifdef MOZ_CRASHREPORTER
|
||||
#include "mozilla/dom/CrashReporterParent.h"
|
||||
#include "mozilla/ipc/CrashReporterClient.h"
|
||||
#include "mozilla/ipc/CrashReporterHost.h"
|
||||
|
||||
using namespace CrashReporter;
|
||||
#endif
|
||||
@@ -598,25 +596,12 @@ PluginModuleChromeParent::OnProcessLaunched(const bool aSucceeded)
|
||||
|
||||
#ifdef MOZ_CRASHREPORTER
|
||||
// If this fails, we're having IPC troubles, and we're doomed anyways.
|
||||
if (!CrashReporterParent::CreateCrashReporter(this)) {
|
||||
if (!InitCrashReporter()) {
|
||||
mShutdown = true;
|
||||
Close();
|
||||
OnInitFailure();
|
||||
return;
|
||||
}
|
||||
CrashReporterParent* crashReporter = CrashReporter();
|
||||
if (crashReporter) {
|
||||
crashReporter->AnnotateCrashReport(NS_LITERAL_CSTRING("AsyncPluginInit"),
|
||||
mIsStartingAsync ?
|
||||
NS_LITERAL_CSTRING("1") :
|
||||
NS_LITERAL_CSTRING("0"));
|
||||
}
|
||||
#ifdef XP_WIN
|
||||
{ // Scope for lock
|
||||
mozilla::MutexAutoLock lock(mCrashReporterMutex);
|
||||
mCrashReporter = CrashReporter();
|
||||
}
|
||||
#endif
|
||||
#endif
|
||||
|
||||
#if defined(XP_WIN) && defined(_X86_)
|
||||
@@ -686,6 +671,37 @@ PluginModuleChromeParent::WaitForIPCConnection()
|
||||
return true;
|
||||
}
|
||||
|
||||
bool
|
||||
PluginModuleChromeParent::InitCrashReporter()
|
||||
{
|
||||
#ifdef MOZ_CRASHREPORTER
|
||||
ipc::Shmem shmem;
|
||||
if (!ipc::CrashReporterClient::AllocShmem(this, &shmem)) {
|
||||
return false;
|
||||
}
|
||||
|
||||
NativeThreadId threadId;
|
||||
if (!CallInitCrashReporter(shmem, &threadId)) {
|
||||
return false;
|
||||
}
|
||||
|
||||
{
|
||||
mozilla::MutexAutoLock lock(mCrashReporterMutex);
|
||||
mCrashReporter = MakeUnique<ipc::CrashReporterHost>(
|
||||
GeckoProcessType_Plugin,
|
||||
shmem,
|
||||
threadId);
|
||||
|
||||
mCrashReporter->AddNote(NS_LITERAL_CSTRING("AsyncPluginInit"),
|
||||
mIsStartingAsync ?
|
||||
NS_LITERAL_CSTRING("1") :
|
||||
NS_LITERAL_CSTRING("0"));
|
||||
}
|
||||
#endif
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
PluginModuleParent::PluginModuleParent(bool aIsChrome, bool aAllowAsyncInit)
|
||||
: mQuirks(QUIRKS_NOT_INITIALIZED)
|
||||
, mIsChrome(aIsChrome)
|
||||
@@ -703,6 +719,9 @@ PluginModuleParent::PluginModuleParent(bool aIsChrome, bool aAllowAsyncInit)
|
||||
, mNPInitialized(false)
|
||||
, mIsNPShutdownPending(false)
|
||||
, mAsyncNewRv(NS_ERROR_NOT_INITIALIZED)
|
||||
#ifdef MOZ_CRASHREPORTER
|
||||
, mCrashReporterMutex("PluginModuleChromeParent::mCrashReporterMutex")
|
||||
#endif
|
||||
{
|
||||
#if defined(MOZ_CRASHREPORTER)
|
||||
CrashReporter::AnnotateCrashReport(NS_LITERAL_CSTRING("AsyncPluginInit"),
|
||||
@@ -752,10 +771,6 @@ PluginModuleChromeParent::PluginModuleChromeParent(const char* aFilePath,
|
||||
, mHangUIParent(nullptr)
|
||||
, mHangUIEnabled(true)
|
||||
, mIsTimerReset(true)
|
||||
#ifdef MOZ_CRASHREPORTER
|
||||
, mCrashReporterMutex("PluginModuleChromeParent::mCrashReporterMutex")
|
||||
, mCrashReporter(nullptr)
|
||||
#endif
|
||||
#endif
|
||||
#ifdef MOZ_CRASHREPORTER_INJECTOR
|
||||
, mFlashProcess1(0)
|
||||
@@ -838,12 +853,11 @@ PluginModuleChromeParent::~PluginModuleChromeParent()
|
||||
|
||||
#ifdef MOZ_CRASHREPORTER
|
||||
void
|
||||
PluginModuleChromeParent::WriteExtraDataForMinidump(AnnotationTable& notes)
|
||||
PluginModuleChromeParent::WriteExtraDataForMinidump()
|
||||
{
|
||||
#ifdef XP_WIN
|
||||
// mCrashReporterMutex is already held by the caller
|
||||
mCrashReporterMutex.AssertCurrentThreadOwns();
|
||||
#endif
|
||||
|
||||
typedef nsDependentCString CS;
|
||||
|
||||
// Get the plugin filename, try to get just the file leafname
|
||||
@@ -853,27 +867,26 @@ PluginModuleChromeParent::WriteExtraDataForMinidump(AnnotationTable& notes)
|
||||
filePos = 0;
|
||||
else
|
||||
filePos++;
|
||||
notes.Put(NS_LITERAL_CSTRING("PluginFilename"), CS(pluginFile.substr(filePos).c_str()));
|
||||
mCrashReporter->AddNote(NS_LITERAL_CSTRING("PluginFilename"), CS(pluginFile.substr(filePos).c_str()));
|
||||
|
||||
notes.Put(NS_LITERAL_CSTRING("PluginName"), mPluginName);
|
||||
notes.Put(NS_LITERAL_CSTRING("PluginVersion"), mPluginVersion);
|
||||
mCrashReporter->AddNote(NS_LITERAL_CSTRING("PluginName"), mPluginName);
|
||||
mCrashReporter->AddNote(NS_LITERAL_CSTRING("PluginVersion"), mPluginVersion);
|
||||
|
||||
CrashReporterParent* crashReporter = CrashReporter();
|
||||
if (crashReporter) {
|
||||
if (mCrashReporter) {
|
||||
#ifdef XP_WIN
|
||||
if (mPluginCpuUsageOnHang.Length() > 0) {
|
||||
notes.Put(NS_LITERAL_CSTRING("NumberOfProcessors"),
|
||||
nsPrintfCString("%d", PR_GetNumberOfProcessors()));
|
||||
mCrashReporter->AddNote(NS_LITERAL_CSTRING("NumberOfProcessors"),
|
||||
nsPrintfCString("%d", PR_GetNumberOfProcessors()));
|
||||
|
||||
nsCString cpuUsageStr;
|
||||
cpuUsageStr.AppendFloat(std::ceil(mPluginCpuUsageOnHang[0] * 100) / 100);
|
||||
notes.Put(NS_LITERAL_CSTRING("PluginCpuUsage"), cpuUsageStr);
|
||||
mCrashReporter->AddNote(NS_LITERAL_CSTRING("PluginCpuUsage"), cpuUsageStr);
|
||||
|
||||
#ifdef MOZ_CRASHREPORTER_INJECTOR
|
||||
for (uint32_t i=1; i<mPluginCpuUsageOnHang.Length(); ++i) {
|
||||
nsCString tempStr;
|
||||
tempStr.AppendFloat(std::ceil(mPluginCpuUsageOnHang[i] * 100) / 100);
|
||||
notes.Put(nsPrintfCString("CpuUsageFlashProcess%d", i), tempStr);
|
||||
mCrashReporter->AddNote(nsPrintfCString("CpuUsageFlashProcess%d", i), tempStr);
|
||||
}
|
||||
#endif
|
||||
}
|
||||
@@ -1203,12 +1216,9 @@ PluginModuleChromeParent::TakeFullMinidump(base::ProcessId aContentPid,
|
||||
nsString& aDumpId)
|
||||
{
|
||||
#ifdef MOZ_CRASHREPORTER
|
||||
#ifdef XP_WIN
|
||||
mozilla::MutexAutoLock lock(mCrashReporterMutex);
|
||||
#endif // XP_WIN
|
||||
|
||||
CrashReporterParent* crashReporter = CrashReporter();
|
||||
if (!crashReporter) {
|
||||
if (!mCrashReporter) {
|
||||
return;
|
||||
}
|
||||
|
||||
@@ -1227,8 +1237,11 @@ PluginModuleChromeParent::TakeFullMinidump(base::ProcessId aContentPid,
|
||||
{
|
||||
// We have a single browser report, generate a new plugin process parent
|
||||
// report and pair it up with the browser report handed in.
|
||||
reportsReady = crashReporter->GenerateMinidumpAndPair(this, browserDumpFile,
|
||||
NS_LITERAL_CSTRING("browser"));
|
||||
reportsReady = mCrashReporter->GenerateMinidumpAndPair(
|
||||
this,
|
||||
browserDumpFile,
|
||||
NS_LITERAL_CSTRING("browser"));
|
||||
|
||||
if (!reportsReady) {
|
||||
browserDumpFile = nullptr;
|
||||
CrashReporter::DeleteMinidumpFilesForID(aBrowserDumpId);
|
||||
@@ -1240,20 +1253,20 @@ PluginModuleChromeParent::TakeFullMinidump(base::ProcessId aContentPid,
|
||||
// the browser process, content process when running under e10s, and
|
||||
// various flash subprocesses if we're the flash module.
|
||||
if (!reportsReady) {
|
||||
reportsReady = crashReporter->GeneratePairedMinidump(this);
|
||||
reportsReady = mCrashReporter->GenerateMinidumpAndPair(
|
||||
this,
|
||||
nullptr, // Pair with a dump of this process and thread.
|
||||
NS_LITERAL_CSTRING("browser"));
|
||||
}
|
||||
|
||||
if (reportsReady) {
|
||||
// Important to set this here, it tells the ActorDestroy handler
|
||||
// that we have an existing crash report that needs to be finalized.
|
||||
mPluginDumpID = crashReporter->ChildDumpID();
|
||||
aDumpId = mPluginDumpID;
|
||||
aDumpId = mCrashReporter->MinidumpID();
|
||||
PLUGIN_LOG_DEBUG(
|
||||
("generated paired browser/plugin minidumps: %s)",
|
||||
NS_ConvertUTF16toUTF8(mPluginDumpID).get()));
|
||||
NS_ConvertUTF16toUTF8(aDumpId).get()));
|
||||
nsAutoCString additionalDumps("browser");
|
||||
nsCOMPtr<nsIFile> pluginDumpFile;
|
||||
if (GetMinidumpForID(mPluginDumpID, getter_AddRefs(pluginDumpFile)) &&
|
||||
if (GetMinidumpForID(aDumpId, getter_AddRefs(pluginDumpFile)) &&
|
||||
pluginDumpFile) {
|
||||
#ifdef MOZ_CRASHREPORTER_INJECTOR
|
||||
// If we have handles to the flash sandbox processes on Windows,
|
||||
@@ -1276,7 +1289,7 @@ PluginModuleChromeParent::TakeFullMinidump(base::ProcessId aContentPid,
|
||||
}
|
||||
}
|
||||
}
|
||||
crashReporter->AnnotateCrashReport(
|
||||
mCrashReporter->AddNote(
|
||||
NS_LITERAL_CSTRING("additional_minidumps"),
|
||||
additionalDumps);
|
||||
} else {
|
||||
@@ -1294,33 +1307,28 @@ PluginModuleChromeParent::TerminateChildProcess(MessageLoop* aMsgLoop,
|
||||
#ifdef MOZ_CRASHREPORTER
|
||||
// Start by taking a full minidump if necessary, this is done early
|
||||
// because it also needs to lock the mCrashReporterMutex and Mutex doesn't
|
||||
// support recrusive locking.
|
||||
// support recursive locking.
|
||||
nsAutoString dumpId;
|
||||
if (aDumpId.IsEmpty()) {
|
||||
TakeFullMinidump(aContentPid, EmptyString(), dumpId);
|
||||
}
|
||||
|
||||
#ifdef XP_WIN
|
||||
mozilla::MutexAutoLock lock(mCrashReporterMutex);
|
||||
CrashReporterParent* crashReporter = mCrashReporter;
|
||||
if (!crashReporter) {
|
||||
if (!mCrashReporter) {
|
||||
// If mCrashReporter is null then the hang has ended, the plugin module
|
||||
// is shutting down. There's nothing to do here.
|
||||
return;
|
||||
}
|
||||
#else
|
||||
CrashReporterParent* crashReporter = CrashReporter();
|
||||
#endif // XP_WIN
|
||||
crashReporter->AnnotateCrashReport(NS_LITERAL_CSTRING("PluginHang"),
|
||||
NS_LITERAL_CSTRING("1"));
|
||||
crashReporter->AnnotateCrashReport(NS_LITERAL_CSTRING("HangMonitorDescription"),
|
||||
aMonitorDescription);
|
||||
mCrashReporter->AddNote(NS_LITERAL_CSTRING("PluginHang"),
|
||||
NS_LITERAL_CSTRING("1"));
|
||||
mCrashReporter->AddNote(NS_LITERAL_CSTRING("HangMonitorDescription"),
|
||||
aMonitorDescription);
|
||||
#ifdef XP_WIN
|
||||
if (mHangUIParent) {
|
||||
unsigned int hangUIDuration = mHangUIParent->LastShowDurationMs();
|
||||
if (hangUIDuration) {
|
||||
nsPrintfCString strHangUIDuration("%u", hangUIDuration);
|
||||
crashReporter->AnnotateCrashReport(
|
||||
mCrashReporter->AddNote(
|
||||
NS_LITERAL_CSTRING("PluginHangUIDuration"),
|
||||
strHangUIDuration);
|
||||
}
|
||||
@@ -1501,12 +1509,6 @@ PluginModuleChromeParent::OnHangUIContinue()
|
||||
#endif // XP_WIN
|
||||
|
||||
#ifdef MOZ_CRASHREPORTER
|
||||
CrashReporterParent*
|
||||
PluginModuleChromeParent::CrashReporter()
|
||||
{
|
||||
return static_cast<CrashReporterParent*>(LoneManagedOrNullAsserts(ManagedPCrashReporterParent()));
|
||||
}
|
||||
|
||||
#ifdef MOZ_CRASHREPORTER_INJECTOR
|
||||
static void
|
||||
RemoveMinidump(nsIFile* minidump)
|
||||
@@ -1526,31 +1528,26 @@ RemoveMinidump(nsIFile* minidump)
|
||||
void
|
||||
PluginModuleChromeParent::ProcessFirstMinidump()
|
||||
{
|
||||
#ifdef XP_WIN
|
||||
mozilla::MutexAutoLock lock(mCrashReporterMutex);
|
||||
#endif
|
||||
CrashReporterParent* crashReporter = CrashReporter();
|
||||
if (!crashReporter)
|
||||
|
||||
if (!mCrashReporter)
|
||||
return;
|
||||
|
||||
AnnotationTable notes(4);
|
||||
WriteExtraDataForMinidump(notes);
|
||||
WriteExtraDataForMinidump();
|
||||
|
||||
if (!mPluginDumpID.IsEmpty()) {
|
||||
// mPluginDumpID may be set in TerminateChildProcess, which means the
|
||||
if (mCrashReporter->HasMinidump()) {
|
||||
// A minidump may be set in TerminateChildProcess, which means the
|
||||
// process hang monitor has already collected a 3-way browser, plugin,
|
||||
// content crash report. If so, update the existing report with our
|
||||
// annotations and finalize it. If not, fall through for standard
|
||||
// plugin crash report handling.
|
||||
crashReporter->GenerateChildData(¬es);
|
||||
crashReporter->FinalizeChildData();
|
||||
mCrashReporter->FinalizeCrashReport();
|
||||
return;
|
||||
}
|
||||
|
||||
uint32_t sequence = UINT32_MAX;
|
||||
nsCOMPtr<nsIFile> dumpFile;
|
||||
nsAutoCString flashProcessType;
|
||||
TakeMinidump(getter_AddRefs(dumpFile), &sequence);
|
||||
RefPtr<nsIFile> dumpFile = mCrashReporter->TakeCrashedChildMinidump(OtherPid(), &sequence);
|
||||
|
||||
#ifdef MOZ_CRASHREPORTER_INJECTOR
|
||||
nsCOMPtr<nsIFile> childDumpFile;
|
||||
@@ -1560,7 +1557,9 @@ PluginModuleChromeParent::ProcessFirstMinidump()
|
||||
TakeMinidumpForChild(mFlashProcess1,
|
||||
getter_AddRefs(childDumpFile),
|
||||
&childSequence)) {
|
||||
if (childSequence < sequence) {
|
||||
if (childSequence < sequence &&
|
||||
mCrashReporter->AdoptMinidump(childDumpFile))
|
||||
{
|
||||
RemoveMinidump(dumpFile);
|
||||
dumpFile = childDumpFile;
|
||||
sequence = childSequence;
|
||||
@@ -1574,7 +1573,9 @@ PluginModuleChromeParent::ProcessFirstMinidump()
|
||||
TakeMinidumpForChild(mFlashProcess2,
|
||||
getter_AddRefs(childDumpFile),
|
||||
&childSequence)) {
|
||||
if (childSequence < sequence) {
|
||||
if (childSequence < sequence &&
|
||||
mCrashReporter->AdoptMinidump(childDumpFile))
|
||||
{
|
||||
RemoveMinidump(dumpFile);
|
||||
dumpFile = childDumpFile;
|
||||
sequence = childSequence;
|
||||
@@ -1592,13 +1593,12 @@ PluginModuleChromeParent::ProcessFirstMinidump()
|
||||
}
|
||||
|
||||
PLUGIN_LOG_DEBUG(("got child minidump: %s",
|
||||
NS_ConvertUTF16toUTF8(mPluginDumpID).get()));
|
||||
NS_ConvertUTF16toUTF8(mCrashReporter->MinidumpID()).get()));
|
||||
|
||||
GetIDFromMinidump(dumpFile, mPluginDumpID);
|
||||
if (!flashProcessType.IsEmpty()) {
|
||||
notes.Put(NS_LITERAL_CSTRING("FlashProcessDump"), flashProcessType);
|
||||
mCrashReporter->AddNote(NS_LITERAL_CSTRING("FlashProcessDump"), flashProcessType);
|
||||
}
|
||||
crashReporter->GenerateCrashReportForMinidump(dumpFile, ¬es);
|
||||
mCrashReporter->FinalizeCrashReport();
|
||||
}
|
||||
#endif
|
||||
|
||||
@@ -1672,8 +1672,18 @@ PluginModuleParent::NotifyPluginCrashed()
|
||||
return;
|
||||
}
|
||||
|
||||
if (mPlugin)
|
||||
mPlugin->PluginCrashed(mPluginDumpID, mBrowserDumpID);
|
||||
if (!mPlugin) {
|
||||
return;
|
||||
}
|
||||
|
||||
nsString dumpID;
|
||||
nsString browserDumpID;
|
||||
#ifdef MOZ_CRASHREPORTER
|
||||
if (mCrashReporter && mCrashReporter->HasMinidump()) {
|
||||
dumpID = mCrashReporter->MinidumpID();
|
||||
}
|
||||
#endif
|
||||
mPlugin->PluginCrashed(dumpID, browserDumpID);
|
||||
}
|
||||
|
||||
PPluginInstanceParent*
|
||||
@@ -2988,45 +2998,6 @@ PluginModuleParent::RecvPluginHideWindow(const uint32_t& aWindowId)
|
||||
#endif
|
||||
}
|
||||
|
||||
PCrashReporterParent*
|
||||
PluginModuleParent::AllocPCrashReporterParent(mozilla::dom::NativeThreadId* id,
|
||||
uint32_t* processType)
|
||||
{
|
||||
MOZ_CRASH("unreachable");
|
||||
}
|
||||
|
||||
bool
|
||||
PluginModuleParent::DeallocPCrashReporterParent(PCrashReporterParent* actor)
|
||||
{
|
||||
MOZ_CRASH("unreachable");
|
||||
}
|
||||
|
||||
PCrashReporterParent*
|
||||
PluginModuleChromeParent::AllocPCrashReporterParent(mozilla::dom::NativeThreadId* id,
|
||||
uint32_t* processType)
|
||||
{
|
||||
#ifdef MOZ_CRASHREPORTER
|
||||
return new CrashReporterParent();
|
||||
#else
|
||||
return nullptr;
|
||||
#endif
|
||||
}
|
||||
|
||||
bool
|
||||
PluginModuleChromeParent::DeallocPCrashReporterParent(PCrashReporterParent* actor)
|
||||
{
|
||||
#ifdef MOZ_CRASHREPORTER
|
||||
#ifdef XP_WIN
|
||||
mozilla::MutexAutoLock lock(mCrashReporterMutex);
|
||||
if (actor == static_cast<PCrashReporterParent*>(mCrashReporter)) {
|
||||
mCrashReporter = nullptr;
|
||||
}
|
||||
#endif
|
||||
#endif
|
||||
delete actor;
|
||||
return true;
|
||||
}
|
||||
|
||||
mozilla::ipc::IPCResult
|
||||
PluginModuleParent::RecvSetCursor(const NSCursorInfo& aCursorInfo)
|
||||
{
|
||||
|
||||
Reference in New Issue
Block a user