mac: Revise incorrect comments about EXC_RESOURCE and EXC_GUARD

launchd actually does set the EXC_RESOURCE and EXC_GUARD handlers
exactly the same way that it sets the EXC_CRASH handler. See 10.9.5
launchd-842.92.1/src/core.c job_setup_exception_port().

Cases where an EXC_CRASH handler is set but EXC_RESOURCE and EXC_GUARD
handlers are not set occur when the exception ports are set by
/usr/bin/login instead of launchd. login looks up the
exception-reporting service by name and sets the exception port without
including EXC_MASK_RESOURCE or EXC_MASK_GUARD in the mask. See 10.10.5
system_cmds-643.30.1/login.tproj/login.c main().

login is a setuid executable, so it does not inherit its parent process’
exception handlers. See 10.10.5 xnu-2782.40.9/osfmk/kern/ipc_tt.c
ipc_task_reset().

Terminal.app executes login when establishing its command-line
environment, so the exception handlers set for Terminal.app itself
(including EXC_MASK_CRASH, EXC_MASK_RESOURCE, and EXC_MASK_GUARD) are
discarded, and then login sets an exception handler only for
EXC_MASK_CRASH. The same thing occurs for any other process descended
from login, including SSH sessions, because sshd executes login.

This is a bug in login filed as Apple radar 22978644. This bug led to a
misunderstanding about the use of EXC_RESOURCE and EXC_GUARD. Comments
that discuss this behavior are now reworded to be accurate, and
non-fatal EXC_RESOURCE exceptions are made eligible for forwarding to
the user ReportCrash (because it would normally handle them in the
absence of Crashpad) while Crashpad itself will still skip processing
them.

R=rsesek@chromium.org

Review URL: https://codereview.chromium.org/1391453002 .
This commit is contained in:
Mark Mentovai 2015-10-05 17:09:45 -04:00
parent bb13efbda7
commit ca2925e2a0

View File

@ -110,27 +110,14 @@ kern_return_t CrashReportExceptionHandler::CatchMachException(
}
}
if (IsExceptionNonfatalResource(exception, code[0], pid)) {
// Swallow non-fatal resource exceptions.
//
// Normally, all EXC_RESOURCE exceptions go to the host-level EXC_RESOURCE
// handler, com.apple.ReportCrash.root, which invokes spindump to handle
// them. These non-fatal exceptions are never user-visible and are not
// currently of interest to Crashpad. Returning success here gets the
// process going again quickly, without generating a crash report.
//
// Alternatively, this could return KERN_FAILURE to let the exception go to
// the host-level handler, but there doesnt seem to be much value in doing
// so.
ExcServerCopyState(
behavior, old_state, old_state_count, new_state, new_state_count);
return ExcServerSuccessfulReturnValue(exception, behavior, false);
}
CrashpadInfoClientOptions client_options;
process_snapshot.GetCrashpadOptions(&client_options);
if (client_options.crashpad_handler_behavior != TriState::kDisabled) {
if (client_options.crashpad_handler_behavior != TriState::kDisabled &&
!IsExceptionNonfatalResource(exception, code[0], pid)) {
// Non-fatal resource exceptions are never user-visible and are not
// currently of interest to Crashpad.
if (!process_snapshot.InitializeException(behavior,
thread,
exception,
@ -197,10 +184,6 @@ kern_return_t CrashReportExceptionHandler::CatchMachException(
// processes that havent actually crashed, and could result in reports not
// actually associated with crashes being sent to the operating system
// vendor.
//
// Note that normally, EXC_RESOURCE and EXC_GUARD exceptions are sent to the
// system-level com.apple.ReportCrash.Root job, and not to the user-level
// job that they are forwarded to here.
base::mac::ScopedMachSendRight
system_crash_reporter_handler(SystemCrashReporterHandler());
if (system_crash_reporter_handler) {