Revision: 23445 http://trac.macosforge.org/projects/launchd/changeset/23445 Author: zarzycki@apple.com Date: 2007-10-23 08:47:01 -0700 (Tue, 23 Oct 2007) Log Message: ----------- <rdar://problem/5510464> ER: Provide a way for launchd to NULL out a tasks exception report when launched Modified Paths: -------------- trunk/launchd/src/Makefile.am trunk/launchd/src/Makefile.in trunk/launchd/src/launchd_core_logic.c trunk/launchd/src/launchd_runtime.c trunk/launchd/src/launchd_runtime.h trunk/launchd/src/liblaunch_private.h Modified: trunk/launchd/src/Makefile.am =================================================================== --- trunk/launchd/src/Makefile.am 2007-10-23 15:41:39 UTC (rev 23444) +++ trunk/launchd/src/Makefile.am 2007-10-23 15:47:01 UTC (rev 23445) @@ -2,7 +2,7 @@ CLEANFILES = protocol_vproc.h protocol_vprocServer.c protocol_vprocUser.c protocol_vprocServer.h \ launchd_internal.h launchd_internalServer.h launchd_internalServer.c launchd_internalUser.c \ - notifyServer.c notifyServer.h job_replyUser.c job_reply.h __version.c + notifyServer.c notifyServer.h job_replyUser.c job_reply.h __version.c mach_excServer.c mach_excServer.h protocol_vproc.h protocol_vprocServer.c protocol_vprocUser.c protocol_vprocServer.h: $(srcdir)/protocol_job.defs mig $(MIGFLAGS) -sheader protocol_vprocServer.h $(srcdir)/protocol_job.defs @@ -48,9 +48,9 @@ launchd_CFLAGS = -mdynamic-no-pic $(AM_CFLAGS) -Wno-unused-parameter launchd_LDFLAGS = -lbsm -launchd_SOURCES = launchd.c launchd_core_logic.c launchd_unix_ipc.c protocol_vprocServer.c notifyServer.c launchd_internalUser.c launchd_internalServer.c job_replyUser.c launchd_runtime.c launchd_runtime_kill.c job_forwardUser.c +launchd_SOURCES = launchd.c launchd_core_logic.c launchd_unix_ipc.c protocol_vprocServer.c notifyServer.c launchd_internalUser.c launchd_internalServer.c job_replyUser.c launchd_runtime.c launchd_runtime_kill.c job_forwardUser.c mach_excServer.c -launchd_runtime.c:: notifyServer.h launchd_internal.h +launchd_runtime.c:: notifyServer.h launchd_internal.h mach_excServer.h launchd_core_logic.c:: protocol_vproc.h job_reply.h protocol_vprocServer.h job_forward.h launchproxy_LDFLAGS = -weak_framework Security @@ -61,6 +61,9 @@ notifyServer.c notifyServer.h: /usr/include/mach/notify.defs mig $(MIGFLAGS) -header /dev/null -user /dev/null -sheader notifyServer.h /usr/include/mach/notify.defs +mach_excServer.c mach_excServer.h: /usr/include/mach/mach_exc.defs + mig $(MIGFLAGS) -header /dev/null -user /dev/null -sheader mach_excServer.h /usr/include/mach/mach_exc.defs + job_replyUser.c job_reply.h: $(srcdir)/protocol_job_reply.defs mig $(MIGFLAGS) -sheader /dev/null -server /dev/null $(srcdir)/protocol_job_reply.defs Modified: trunk/launchd/src/Makefile.in =================================================================== --- trunk/launchd/src/Makefile.in 2007-10-23 15:41:39 UTC (rev 23444) +++ trunk/launchd/src/Makefile.in 2007-10-23 15:47:01 UTC (rev 23445) @@ -97,7 +97,7 @@ launchd_unix_ipc.c protocol_vprocServer.c notifyServer.c \ launchd_internalUser.c launchd_internalServer.c \ job_replyUser.c launchd_runtime.c launchd_runtime_kill.c \ - job_forwardUser.c + job_forwardUser.c mach_excServer.c @LIBS_ONLY_FALSE@am_launchd_OBJECTS = launchd-launchd.$(OBJEXT) \ @LIBS_ONLY_FALSE@ launchd-launchd_core_logic.$(OBJEXT) \ @LIBS_ONLY_FALSE@ launchd-launchd_unix_ipc.$(OBJEXT) \ @@ -108,7 +108,8 @@ @LIBS_ONLY_FALSE@ launchd-job_replyUser.$(OBJEXT) \ @LIBS_ONLY_FALSE@ launchd-launchd_runtime.$(OBJEXT) \ @LIBS_ONLY_FALSE@ launchd-launchd_runtime_kill.$(OBJEXT) \ -@LIBS_ONLY_FALSE@ launchd-job_forwardUser.$(OBJEXT) +@LIBS_ONLY_FALSE@ launchd-job_forwardUser.$(OBJEXT) \ +@LIBS_ONLY_FALSE@ launchd-mach_excServer.$(OBJEXT) launchd_OBJECTS = $(am_launchd_OBJECTS) launchd_LDADD = $(LDADD) launchd_LINK = $(CCLD) $(launchd_CFLAGS) $(CFLAGS) $(launchd_LDFLAGS) \ @@ -240,7 +241,7 @@ AM_CFLAGS = -no-cpp-precomp -F/System/Library/PrivateFrameworks -Wall -Wextra -Waggregate-return -Wshadow -Wmissing-prototypes -Wmissing-declarations -Werror -D__MigTypeCheck=1 -fvisibility=hidden -Dmig_external=__private_extern__ CLEANFILES = protocol_vproc.h protocol_vprocServer.c protocol_vprocUser.c protocol_vprocServer.h \ launchd_internal.h launchd_internalServer.h launchd_internalServer.c launchd_internalUser.c \ - notifyServer.c notifyServer.h job_replyUser.c job_reply.h __version.c + notifyServer.c notifyServer.h job_replyUser.c job_reply.h __version.c mach_excServer.c mach_excServer.h @LIBS_ONLY_TRUE@noinst_LIBRARIES = liblaunch.a liblaunch_profile.a @LIBS_ONLY_TRUE@liblaunch_a_CFLAGS = -D__DARWIN_NON_CANCELABLE=1 $(AM_CFLAGS) @@ -255,7 +256,7 @@ @LIBS_ONLY_FALSE@SystemStarter_SOURCES = StartupItems.c IPC.c SystemStarter.c @LIBS_ONLY_FALSE@launchd_CFLAGS = -mdynamic-no-pic $(AM_CFLAGS) -Wno-unused-parameter @LIBS_ONLY_FALSE@launchd_LDFLAGS = -lbsm -@LIBS_ONLY_FALSE@launchd_SOURCES = launchd.c launchd_core_logic.c launchd_unix_ipc.c protocol_vprocServer.c notifyServer.c launchd_internalUser.c launchd_internalServer.c job_replyUser.c launchd_runtime.c launchd_runtime_kill.c job_forwardUser.c +@LIBS_ONLY_FALSE@launchd_SOURCES = launchd.c launchd_core_logic.c launchd_unix_ipc.c protocol_vprocServer.c notifyServer.c launchd_internalUser.c launchd_internalServer.c job_replyUser.c launchd_runtime.c launchd_runtime_kill.c job_forwardUser.c mach_excServer.c @LIBS_ONLY_FALSE@launchproxy_LDFLAGS = -weak_framework Security @LIBS_ONLY_FALSE@man1_MANS = wait4path.1 launchctl.1 @LIBS_ONLY_FALSE@man5_MANS = launchd.plist.5 launchd.conf.5 @@ -426,6 +427,7 @@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/launchd-launchd_runtime.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/launchd-launchd_runtime_kill.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/launchd-launchd_unix_ipc.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/launchd-mach_excServer.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/launchd-notifyServer.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/launchd-protocol_vprocServer.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/launchproxy.Po@am__quote@ @@ -804,6 +806,20 @@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ source='job_forwardUser.c' object='launchd-job_forwardUser.obj' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(launchd_CFLAGS) $(CFLAGS) -c -o launchd-job_forwardUser.obj `if test -f 'job_forwardUser.c'; then $(CYGPATH_W) 'job_forwardUser.c'; else $(CYGPATH_W) '$(srcdir)/job_forwardUser.c'; fi` + +launchd-mach_excServer.o: mach_excServer.c +@am__fastdepCC_TRUE@ $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(launchd_CFLAGS) $(CFLAGS) -MT launchd-mach_excServer.o -MD -MP -MF $(DEPDIR)/launchd-mach_excServer.Tpo -c -o launchd-mach_excServer.o `test -f 'mach_excServer.c' || echo '$(srcdir)/'`mach_excServer.c +@am__fastdepCC_TRUE@ mv -f $(DEPDIR)/launchd-mach_excServer.Tpo $(DEPDIR)/launchd-mach_excServer.Po +@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='mach_excServer.c' object='launchd-mach_excServer.o' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ +@am__fastdepCC_FALSE@ $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(launchd_CFLAGS) $(CFLAGS) -c -o launchd-mach_excServer.o `test -f 'mach_excServer.c' || echo '$(srcdir)/'`mach_excServer.c + +launchd-mach_excServer.obj: mach_excServer.c +@am__fastdepCC_TRUE@ $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(launchd_CFLAGS) $(CFLAGS) -MT launchd-mach_excServer.obj -MD -MP -MF $(DEPDIR)/launchd-mach_excServer.Tpo -c -o launchd-mach_excServer.obj `if test -f 'mach_excServer.c'; then $(CYGPATH_W) 'mach_excServer.c'; else $(CYGPATH_W) '$(srcdir)/mach_excServer.c'; fi` +@am__fastdepCC_TRUE@ mv -f $(DEPDIR)/launchd-mach_excServer.Tpo $(DEPDIR)/launchd-mach_excServer.Po +@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='mach_excServer.c' object='launchd-mach_excServer.obj' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ +@am__fastdepCC_FALSE@ $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(launchd_CFLAGS) $(CFLAGS) -c -o launchd-mach_excServer.obj `if test -f 'mach_excServer.c'; then $(CYGPATH_W) 'mach_excServer.c'; else $(CYGPATH_W) '$(srcdir)/mach_excServer.c'; fi` install-man1: $(man1_MANS) $(man_MANS) @$(NORMAL_INSTALL) test -z "$(man1dir)" || $(MKDIR_P) "$(DESTDIR)$(man1dir)" @@ -1165,7 +1181,7 @@ @LIBS_ONLY_TRUE@ cp liblaunch.a $(DESTDIR)/usr/local/lib/system/liblaunch_debug.a @LIBS_ONLY_TRUE@ cp liblaunch_profile.a $(DESTDIR)/usr/local/lib/system/liblaunch_profile.a -@LIBS_ONLY_FALSE@launchd_runtime.c:: notifyServer.h launchd_internal.h +@LIBS_ONLY_FALSE@launchd_runtime.c:: notifyServer.h launchd_internal.h mach_excServer.h @LIBS_ONLY_FALSE@launchd_core_logic.c:: protocol_vproc.h job_reply.h protocol_vprocServer.h job_forward.h @LIBS_ONLY_FALSE@job_forwardUser.c job_forward.h: $(srcdir)/protocol_job_forward.defs @@ -1174,6 +1190,9 @@ @LIBS_ONLY_FALSE@notifyServer.c notifyServer.h: /usr/include/mach/notify.defs @LIBS_ONLY_FALSE@ mig $(MIGFLAGS) -header /dev/null -user /dev/null -sheader notifyServer.h /usr/include/mach/notify.defs +@LIBS_ONLY_FALSE@mach_excServer.c mach_excServer.h: /usr/include/mach/mach_exc.defs +@LIBS_ONLY_FALSE@ mig $(MIGFLAGS) -header /dev/null -user /dev/null -sheader mach_excServer.h /usr/include/mach/mach_exc.defs + @LIBS_ONLY_FALSE@job_replyUser.c job_reply.h: $(srcdir)/protocol_job_reply.defs @LIBS_ONLY_FALSE@ mig $(MIGFLAGS) -sheader /dev/null -server /dev/null $(srcdir)/protocol_job_reply.defs Modified: trunk/launchd/src/launchd_core_logic.c =================================================================== --- trunk/launchd/src/launchd_core_logic.c 2007-10-23 15:41:39 UTC (rev 23444) +++ trunk/launchd/src/launchd_core_logic.c 2007-10-23 15:47:01 UTC (rev 23445) @@ -334,6 +334,7 @@ char *groupname; char *stdoutpath; char *stderrpath; + char *alt_exc_handler; struct machservice *lastlookup; unsigned int lastlookup_gennum; char *seatbelt_profile; @@ -361,7 +362,7 @@ currently_ignored:1, forced_peers_to_demand_mode:1, setnice:1, hopefully_exits_last:1, removal_pending:1, wait4pipe_eof:1, sent_sigkill:1, debug_before_kill:1, weird_bootstrap:1, start_on_mount:1, per_user:1, hopefully_exits_first:1, deny_unknown_mslookups:1, unload_at_mig_return:1, abandon_pg:1, - poll_for_vfs_changes:1; + poll_for_vfs_changes:1, internal_exc_handler:1; const char label[0]; }; @@ -862,6 +863,9 @@ if (j->stderrpath) { free(j->stderrpath); } + if (j->alt_exc_handler) { + free(j->alt_exc_handler); + } if (j->seatbelt_profile) { free(j->seatbelt_profile); } @@ -1324,6 +1328,13 @@ found_key = true; } break; + case 'm': + case 'M': + if (strcasecmp(key, LAUNCH_JOBKEY_MACHEXCEPTIONHANDLER) == 0) { + j->internal_exc_handler = value; + found_key = true; + } + break; case 'i': case 'I': if (strcasecmp(key, LAUNCH_JOBKEY_INITGROUPS) == 0) { @@ -1377,6 +1388,12 @@ char **where2put = NULL; switch (key[0]) { + case 'm': + case 'M': + if (strcasecmp(key, LAUNCH_JOBKEY_MACHEXCEPTIONHANDLER) == 0) { + where2put = &j->alt_exc_handler; + } + break; case 'p': case 'P': if (strcasecmp(key, LAUNCH_JOBKEY_PROGRAM) == 0) { @@ -4003,9 +4020,20 @@ void job_setup_exception_port(job_t j, task_t target_task) { + struct machservice *ms; thread_state_flavor_t f = 0; + mach_port_t exc_port = the_exception_server; - if (!the_exception_server) { + if (j->alt_exc_handler) { + ms = jobmgr_lookup_service(j->mgr, j->alt_exc_handler, true, 0); + if (ms) { + exc_port = machservice_port(ms); + } else { + job_log(j, LOG_WARNING, "Falling back to default Mach exception handler. Could not find: %s", j->alt_exc_handler); + } + } else if (j->internal_exc_handler) { + exc_port = runtime_get_kernel_port(); + } else if (!exc_port) { return; } @@ -4016,9 +4044,9 @@ #endif if (target_task) { - job_assumes(j, task_set_exception_ports(target_task, EXC_MASK_CRASH, the_exception_server, + job_assumes(j, task_set_exception_ports(target_task, EXC_MASK_CRASH, exc_port, EXCEPTION_STATE_IDENTITY | MACH_EXCEPTION_CODES, f) == KERN_SUCCESS); - } else if (getpid() == 1) { + } else if (getpid() == 1 && the_exception_server) { mach_port_t mhp = mach_host_self(); job_assumes(j, host_set_exception_ports(mhp, EXC_MASK_CRASH, the_exception_server, EXCEPTION_STATE_IDENTITY | MACH_EXCEPTION_CODES, f) == KERN_SUCCESS); Modified: trunk/launchd/src/launchd_runtime.c =================================================================== --- trunk/launchd/src/launchd_runtime.c 2007-10-23 15:41:39 UTC (rev 23444) +++ trunk/launchd/src/launchd_runtime.c 2007-10-23 15:47:01 UTC (rev 23445) @@ -61,6 +61,7 @@ #include "launchd_internalServer.h" #include "launchd_internal.h" #include "notifyServer.h" +#include "mach_excServer.h" /* We shouldn't be including these */ #include "launch.h" @@ -86,6 +87,7 @@ static void *kqueue_demand_loop(void *arg); static void log_kevent_struct(int level, struct kevent *kev, int indx); +static boolean_t launchd_internal_demux(mach_msg_header_t *Request, mach_msg_header_t *Reply); static void record_caller_creds(mach_msg_header_t *mh); static void launchd_runtime2(mach_msg_size_t msg_size, mig_reply_error_t *bufRequest, mig_reply_error_t *bufReply); static mach_msg_size_t max_msg_size; @@ -115,6 +117,12 @@ }; static sigset_t sigign_set; +mach_port_t +runtime_get_kernel_port(void) +{ + return launchd_internal_port; +} + static int internal_mask_pri = LOG_UPTO(LOG_NOTICE); //static int internal_mask_pri = LOG_UPTO(LOG_DEBUG); @@ -850,9 +858,11 @@ { if (launchd_internal_server_routine(Request)) { return launchd_internal_server(Request, Reply); + } else if (notify_server_routine(Request)) { + return notify_server(Request, Reply); + } else { + return mach_exc_server(Request, Reply); } - - return notify_server(Request, Reply); } kern_return_t @@ -1451,3 +1461,57 @@ { runtime_busy_cnt--; } + +kern_return_t +catch_mach_exception_raise(mach_port_t exception_port, mach_port_t thread, mach_port_t task, + exception_type_t exception, mach_exception_data_t code, mach_msg_type_number_t codeCnt) +{ + pid_t p4t = -1; + + launchd_assumes(pid_for_task(task, &p4t) == 0); + + runtime_syslog(LOG_NOTICE, "%s(): PID: %u thread: 0x%x type: 0x%x code: %p codeCnt: 0x%x", + __func__, p4t, thread, exception, code, codeCnt); + + launchd_assumes(launchd_mport_deallocate(thread) == KERN_SUCCESS); + launchd_assumes(launchd_mport_deallocate(task) == KERN_SUCCESS); + + return 0; +} + +kern_return_t +catch_mach_exception_raise_state(mach_port_t exception_port, + exception_type_t exception, const mach_exception_data_t code, mach_msg_type_number_t codeCnt, + int *flavor, const thread_state_t old_state, mach_msg_type_number_t old_stateCnt, + thread_state_t new_state, mach_msg_type_number_t *new_stateCnt) +{ + runtime_syslog(LOG_NOTICE, "%s(): type: 0x%x code: %p codeCnt: 0x%x flavor: %p old_state: %p old_stateCnt: 0x%x new_state: %p new_stateCnt: %p", + __func__, exception, code, codeCnt, flavor, old_state, old_stateCnt, new_state, new_stateCnt); + + memcpy(new_state, old_state, old_stateCnt * sizeof(old_state[0])); + *new_stateCnt = old_stateCnt; + + return 0; +} + +kern_return_t +catch_mach_exception_raise_state_identity(mach_port_t exception_port, mach_port_t thread, mach_port_t task, + exception_type_t exception, mach_exception_data_t code, mach_msg_type_number_t codeCnt, + int *flavor, thread_state_t old_state, mach_msg_type_number_t old_stateCnt, + thread_state_t new_state, mach_msg_type_number_t *new_stateCnt) +{ + pid_t p4t = -1; + + launchd_assumes(pid_for_task(task, &p4t) == 0); + + runtime_syslog(LOG_NOTICE, "%s(): PID: %u thread: 0x%x type: 0x%x code: %p codeCnt: 0x%x flavor: %p old_state: %p old_stateCnt: 0x%x new_state: %p new_stateCnt: %p", + __func__, p4t, thread, exception, code, codeCnt, flavor, old_state, old_stateCnt, new_state, new_stateCnt); + + memcpy(new_state, old_state, old_stateCnt * sizeof(old_state[0])); + *new_stateCnt = old_stateCnt; + + launchd_assumes(launchd_mport_deallocate(thread) == KERN_SUCCESS); + launchd_assumes(launchd_mport_deallocate(task) == KERN_SUCCESS); + + return 0; +} Modified: trunk/launchd/src/launchd_runtime.h =================================================================== --- trunk/launchd/src/launchd_runtime.h 2007-10-23 15:41:39 UTC (rev 23444) +++ trunk/launchd/src/launchd_runtime.h 2007-10-23 15:47:01 UTC (rev 23445) @@ -98,7 +98,7 @@ typedef boolean_t (*mig_callback)(mach_msg_header_t *, mach_msg_header_t *); typedef void (*timeout_callback)(void); -boolean_t launchd_internal_demux(mach_msg_header_t *Request, mach_msg_header_t *Reply); +mach_port_t runtime_get_kernel_port(void); void runtime_add_ref(void); void runtime_del_ref(void); Modified: trunk/launchd/src/liblaunch_private.h =================================================================== --- trunk/launchd/src/liblaunch_private.h 2007-10-23 15:41:39 UTC (rev 23444) +++ trunk/launchd/src/liblaunch_private.h 2007-10-23 15:47:01 UTC (rev 23445) @@ -55,6 +55,7 @@ #define LAUNCH_JOBKEY_PERJOBMACHSERVICES "PerJobMachServices" #define LAUNCH_JOBKEY_SERVICEIPC "ServiceIPC" #define LAUNCH_JOBKEY_BINARYORDERPREFERENCE "BinaryOrderPreference" +#define LAUNCH_JOBKEY_MACHEXCEPTIONHANDLER "MachExceptionHandler" #define LAUNCH_JOBKEY_MACH_KUNCSERVER "kUNCServer" #define LAUNCH_JOBKEY_MACH_EXCEPTIONSERVER "ExceptionServer"
participants (1)
-
source_changes@macosforge.org