Revision: 23097 http://trac.macosforge.org/projects/launchd/changeset/23097 Author: zarzycki@apple.com Date: 2007-02-22 10:22:46 -0800 (Thu, 22 Feb 2007) Log Message: ----------- <rdar://problem/5016362> Step one of 4746572 (seatbelt stuff) Modified Paths: -------------- trunk/launchd/src/Makefile.am trunk/launchd/src/Makefile.in trunk/launchd/src/launchd_core_logic.c trunk/launchd/src/libbootstrap.c trunk/launchd/src/protocol_job.defs Added Paths: ----------- trunk/launchd/src/libbootstrap_private.h Modified: trunk/launchd/src/Makefile.am =================================================================== --- trunk/launchd/src/Makefile.am 2007-02-22 01:34:11 UTC (rev 23096) +++ trunk/launchd/src/Makefile.am 2007-02-22 18:22:46 UTC (rev 23097) @@ -70,22 +70,23 @@ install-data-hook: mkdir -p $(DESTDIR)/usr/libexec + mkdir -p $(DESTDIR)/usr/include/servers + mkdir -p $(DESTDIR)/usr/local/include + mkdir -p $(DESTDIR)/$(sysconfdir)/mach_init.d + mkdir -p $(DESTDIR)/$(sysconfdir)/mach_init_per_user.d + mkdir -p $(DESTDIR)/Library/LaunchDaemons + mkdir -p $(DESTDIR)/Library/LaunchAgents + mkdir -p $(DESTDIR)/System/Library/LaunchAgents + mkdir -p $(DESTDIR)/System/Library/LaunchDaemons cp $(srcdir)/StartupItemContext $(DESTDIR)/usr/libexec - mkdir -p $(DESTDIR)/usr/include/servers cp $(srcdir)/liblaunch_public.h $(DESTDIR)/usr/include/launch.h cp $(srcdir)/libvproc_public.h $(DESTDIR)/usr/include/vproc.h cp $(srcdir)/libbootstrap_public.h $(DESTDIR)/usr/include/servers/bootstrap.h cp $(srcdir)/libbootstrap_public.h $(DESTDIR)/usr/include/servers/bootstrap_defs.h - mkdir -p $(DESTDIR)/usr/local/include + cp $(srcdir)/libbootstrap_private.h $(DESTDIR)/usr/local/include/bootstrap_priv.h cp $(srcdir)/liblaunch_private.h $(DESTDIR)/usr/local/include/launch_priv.h cp $(srcdir)/libvproc_private.h $(DESTDIR)/usr/local/include/vproc_priv.h cp $(srcdir)/reboot2.h $(DESTDIR)/usr/local/include/reboot2.h - mkdir -p $(DESTDIR)/$(sysconfdir)/mach_init.d - mkdir -p $(DESTDIR)/$(sysconfdir)/mach_init_per_user.d - mkdir -p $(DESTDIR)/Library/LaunchDaemons - mkdir -p $(DESTDIR)/Library/LaunchAgents - mkdir -p $(DESTDIR)/System/Library/LaunchAgents - mkdir -p $(DESTDIR)/System/Library/LaunchDaemons cp $(srcdir)/com.apple.SystemStarter.plist $(DESTDIR)/System/Library/LaunchDaemons endif Modified: trunk/launchd/src/Makefile.in =================================================================== --- trunk/launchd/src/Makefile.in 2007-02-22 01:34:11 UTC (rev 23096) +++ trunk/launchd/src/Makefile.in 2007-02-22 18:22:46 UTC (rev 23097) @@ -1060,22 +1060,23 @@ @LIBS_ONLY_FALSE@install-data-hook: @LIBS_ONLY_FALSE@ mkdir -p $(DESTDIR)/usr/libexec +@LIBS_ONLY_FALSE@ mkdir -p $(DESTDIR)/usr/include/servers +@LIBS_ONLY_FALSE@ mkdir -p $(DESTDIR)/usr/local/include +@LIBS_ONLY_FALSE@ mkdir -p $(DESTDIR)/$(sysconfdir)/mach_init.d +@LIBS_ONLY_FALSE@ mkdir -p $(DESTDIR)/$(sysconfdir)/mach_init_per_user.d +@LIBS_ONLY_FALSE@ mkdir -p $(DESTDIR)/Library/LaunchDaemons +@LIBS_ONLY_FALSE@ mkdir -p $(DESTDIR)/Library/LaunchAgents +@LIBS_ONLY_FALSE@ mkdir -p $(DESTDIR)/System/Library/LaunchAgents +@LIBS_ONLY_FALSE@ mkdir -p $(DESTDIR)/System/Library/LaunchDaemons @LIBS_ONLY_FALSE@ cp $(srcdir)/StartupItemContext $(DESTDIR)/usr/libexec -@LIBS_ONLY_FALSE@ mkdir -p $(DESTDIR)/usr/include/servers @LIBS_ONLY_FALSE@ cp $(srcdir)/liblaunch_public.h $(DESTDIR)/usr/include/launch.h @LIBS_ONLY_FALSE@ cp $(srcdir)/libvproc_public.h $(DESTDIR)/usr/include/vproc.h @LIBS_ONLY_FALSE@ cp $(srcdir)/libbootstrap_public.h $(DESTDIR)/usr/include/servers/bootstrap.h @LIBS_ONLY_FALSE@ cp $(srcdir)/libbootstrap_public.h $(DESTDIR)/usr/include/servers/bootstrap_defs.h -@LIBS_ONLY_FALSE@ mkdir -p $(DESTDIR)/usr/local/include +@LIBS_ONLY_FALSE@ cp $(srcdir)/libbootstrap_private.h $(DESTDIR)/usr/local/include/bootstrap_priv.h @LIBS_ONLY_FALSE@ cp $(srcdir)/liblaunch_private.h $(DESTDIR)/usr/local/include/launch_priv.h @LIBS_ONLY_FALSE@ cp $(srcdir)/libvproc_private.h $(DESTDIR)/usr/local/include/vproc_priv.h @LIBS_ONLY_FALSE@ cp $(srcdir)/reboot2.h $(DESTDIR)/usr/local/include/reboot2.h -@LIBS_ONLY_FALSE@ mkdir -p $(DESTDIR)/$(sysconfdir)/mach_init.d -@LIBS_ONLY_FALSE@ mkdir -p $(DESTDIR)/$(sysconfdir)/mach_init_per_user.d -@LIBS_ONLY_FALSE@ mkdir -p $(DESTDIR)/Library/LaunchDaemons -@LIBS_ONLY_FALSE@ mkdir -p $(DESTDIR)/Library/LaunchAgents -@LIBS_ONLY_FALSE@ mkdir -p $(DESTDIR)/System/Library/LaunchAgents -@LIBS_ONLY_FALSE@ mkdir -p $(DESTDIR)/System/Library/LaunchDaemons @LIBS_ONLY_FALSE@ cp $(srcdir)/com.apple.SystemStarter.plist $(DESTDIR)/System/Library/LaunchDaemons # Tell versions [3.59,3.63) of GNU make to not export all variables. # Otherwise a system limit (for SysV at least) may be exceeded. Modified: trunk/launchd/src/launchd_core_logic.c =================================================================== --- trunk/launchd/src/launchd_core_logic.c 2007-02-22 01:34:11 UTC (rev 23096) +++ trunk/launchd/src/launchd_core_logic.c 2007-02-22 18:22:46 UTC (rev 23097) @@ -76,6 +76,7 @@ #include "liblaunch_public.h" #include "liblaunch_private.h" #include "libbootstrap_public.h" +#include "libbootstrap_private.h" #include "libvproc_public.h" #include "libvproc_internal.h" @@ -101,14 +102,14 @@ SLIST_ENTRY(machservice) sle; job_t job; mach_port_name_t port; - unsigned int isActive:1, reset:1, recv:1, hide:1, kUNCServer:1, must_match_uid:1, debug_on_close:1; + unsigned int isActive:1, reset:1, recv:1, hide:1, kUNCServer:1, must_match_uid:1, debug_on_close:1, per_pid:1; char name[0]; }; static void machservice_setup(launch_data_t obj, const char *key, void *context); static void machservice_setup_options(launch_data_t obj, const char *key, void *context); static void machservice_resetport(job_t j, struct machservice *ms); -static struct machservice *machservice_new(job_t j, const char *name, mach_port_t *serviceport); +static struct machservice *machservice_new(job_t j, const char *name, mach_port_t *serviceport, bool pid_local); static void machservice_ignore(job_t j, struct machservice *ms); static void machservice_watch(job_t j, struct machservice *ms); static void machservice_delete(struct machservice *); @@ -223,7 +224,7 @@ static void jobmgr_callback(void *obj, struct kevent *kev); static pid_t jobmgr_fork(jobmgr_t jm); static void jobmgr_setup_env_from_other_jobs(jobmgr_t jm); -static struct machservice *jobmgr_lookup_service(jobmgr_t jm, const char *name, bool check_parent); +static struct machservice *jobmgr_lookup_service(jobmgr_t jm, const char *name, bool check_parent, pid_t target_pid); static void jobmgr_logv(jobmgr_t jm, int pri, int err, const char *msg, va_list ap) __attribute__((format(printf, 4, 0))); static void jobmgr_log(jobmgr_t jm, int pri, const char *msg, ...) __attribute__((format(printf, 3, 4))); /* static void jobmgr_log_error(jobmgr_t jm, int pri, const char *msg, ...) __attribute__((format(printf, 3, 4))); */ @@ -3097,7 +3098,7 @@ } struct machservice * -machservice_new(job_t j, const char *name, mach_port_t *serviceport) +machservice_new(job_t j, const char *name, mach_port_t *serviceport, bool pid_local) { struct machservice *ms; @@ -3107,6 +3108,7 @@ strcpy(ms->name, name); ms->job = j; + ms->per_pid = pid_local; if (*serviceport == MACH_PORT_NULL) { if (!job_assumes(j, launchd_mport_create_recv(&ms->port) == KERN_SUCCESS)) { @@ -3236,12 +3238,12 @@ struct machservice *ms; mach_port_t p = MACH_PORT_NULL; - if ((ms = jobmgr_lookup_service(j->mgr, key, false))) { + if ((ms = jobmgr_lookup_service(j->mgr, key, false, 0))) { job_log(j, LOG_WARNING, "Conflict with job: %s over Mach service: %s", ms->job->label, key); return; } - if ((ms = machservice_new(j, key, &p)) == NULL) { + if ((ms = machservice_new(j, key, &p, false)) == NULL) { job_log_error(j, LOG_WARNING, "Cannot add service: %s", key); return; } @@ -3516,13 +3518,23 @@ } struct machservice * -jobmgr_lookup_service(jobmgr_t jm, const char *name, bool check_parent) +jobmgr_lookup_service(jobmgr_t jm, const char *name, bool check_parent, pid_t target_pid) { struct machservice *ms; job_t ji; + if (target_pid) { + jobmgr_assumes(jm, !check_parent); + } + TAILQ_FOREACH(ji, &jm->jobs, sle) { + if (target_pid && (ji->p != target_pid)) { + continue; + } SLIST_FOREACH(ms, &ji->machservices, sle) { + if (target_pid && !ms->per_pid) { + continue; + } if (strcmp(name, ms->name) == 0) { return ms; } @@ -3537,7 +3549,7 @@ return NULL; } - return jobmgr_lookup_service(jm->parentmgr, name, true); + return jobmgr_lookup_service(jm->parentmgr, name, true, 0); } mach_port_t @@ -4270,7 +4282,7 @@ ji->mach_uid = which_user; - if ((ms = machservice_new(ji, lbuf, up_cont)) == NULL) { + if ((ms = machservice_new(ji, lbuf, up_cont, false)) == NULL) { job_remove(ji); return BOOTSTRAP_NO_MEMORY; } @@ -4301,7 +4313,7 @@ runtime_get_caller_creds(&ldc); - ms = jobmgr_lookup_service(j->mgr, servicename, true); + ms = jobmgr_lookup_service(j->mgr, servicename, true, 0); if (ms == NULL) { job_log(j, LOG_DEBUG, "Check-in of Mach service failed. Unknown: %s", servicename); @@ -4329,7 +4341,7 @@ } kern_return_t -job_mig_register(job_t j, name_t servicename, mach_port_t serviceport) +job_mig_register2(job_t j, name_t servicename, mach_port_t serviceport, uint64_t flags) { struct machservice *ms; struct ldcred ldc; @@ -4344,7 +4356,7 @@ job_log(j, LOG_NOTICE, "bootstrap_register() is deprecated. PID: %u Service: %s", ldc.pid, servicename); #endif - job_log(j, LOG_DEBUG, "Mach service registration attempt: %s", servicename); + job_log(j, LOG_DEBUG, "%sMach service registration attempt: %s", flags & BOOTSTRAP_PER_PID_SERVICE ? "Per PID " : "", servicename); /* * From a per-user/session launchd's perspective, SecurityAgent (UID @@ -4359,7 +4371,7 @@ } } - ms = jobmgr_lookup_service(j->mgr, servicename, false); + ms = jobmgr_lookup_service(j->mgr, servicename, false, flags & BOOTSTRAP_PER_PID_SERVICE ? ldc.pid : 0); if (ms) { if (machservice_job(ms) != j) { @@ -4374,7 +4386,7 @@ } if (serviceport != MACH_PORT_NULL) { - if ((ms = machservice_new(j, servicename, &serviceport))) { + if ((ms = machservice_new(j, servicename, &serviceport, flags & BOOTSTRAP_PER_PID_SERVICE ? true : false))) { machservice_request_notifications(ms); } else { return BOOTSTRAP_NO_MEMORY; @@ -4385,7 +4397,7 @@ } kern_return_t -job_mig_look_up(job_t j, name_t servicename, mach_port_t *serviceportp, mach_msg_type_name_t *ptype) +job_mig_look_up2(job_t j, name_t servicename, mach_port_t *serviceportp, mach_msg_type_name_t *ptype, pid_t target_pid, uint64_t flags) { struct machservice *ms; struct ldcred ldc; @@ -4400,7 +4412,11 @@ return VPROC_ERR_TRY_PER_USER; } - ms = jobmgr_lookup_service(j->mgr, servicename, true); + if (flags & BOOTSTRAP_PER_PID_SERVICE) { + ms = jobmgr_lookup_service(j->mgr, servicename, false, target_pid); + } else { + ms = jobmgr_lookup_service(j->mgr, servicename, true, 0); + } if (ms && machservice_hidden(ms) && !job_active(machservice_job(ms))) { ms = NULL; @@ -4410,16 +4426,16 @@ if (ms) { launchd_assumes(machservice_port(ms) != MACH_PORT_NULL); - job_log(j, LOG_DEBUG, "Mach service lookup (by PID %d): %s", ldc.pid, servicename); + job_log(j, LOG_DEBUG, "%sMach service lookup (by PID %d): %s", flags & BOOTSTRAP_PER_PID_SERVICE ? "Per PID " : "", ldc.pid, servicename); *serviceportp = machservice_port(ms); *ptype = MACH_MSG_TYPE_COPY_SEND; return BOOTSTRAP_SUCCESS; - } else if (inherited_bootstrap_port != MACH_PORT_NULL) { + } else if (!(flags & BOOTSTRAP_PER_PID_SERVICE) && (inherited_bootstrap_port != MACH_PORT_NULL)) { job_log(j, LOG_DEBUG, "Mach service lookup (by PID %d) forwarded: %s", ldc.pid, servicename); *ptype = MACH_MSG_TYPE_MOVE_SEND; return bootstrap_look_up(inherited_bootstrap_port, servicename, serviceportp); } else { - job_log(j, LOG_DEBUG, "Mach service lookup (by PID %d) failed: %s", ldc.pid, servicename); + job_log(j, LOG_DEBUG, "%sMach service lookup (by PID %d) failed: %s", flags & BOOTSTRAP_PER_PID_SERVICE ? "Per PID " : "", ldc.pid, servicename); return BOOTSTRAP_UNKNOWN_SERVICE; } } @@ -4572,7 +4588,7 @@ for (l2l_i = 0; l2l_i < l2l_name_cnt; l2l_i++) { struct machservice *ms; - if ((ms = machservice_new(jmr->anonj, l2l_names[l2l_i], &l2l_ports[l2l_i]))) { + if ((ms = machservice_new(jmr->anonj, l2l_names[l2l_i], &l2l_ports[l2l_i], false))) { machservice_request_notifications(ms); } } @@ -4721,7 +4737,7 @@ return BOOTSTRAP_NOT_PRIVILEGED; } - ms = jobmgr_lookup_service(j->mgr, servicename, false); + ms = jobmgr_lookup_service(j->mgr, servicename, false, 0); if (ms) { job_log(j, LOG_DEBUG, "Mach service creation attempt for failed. Already exists: %s", servicename); return BOOTSTRAP_NAME_IN_USE; @@ -4730,7 +4746,7 @@ job_checkin(j); *serviceportp = MACH_PORT_NULL; - ms = machservice_new(j, servicename, serviceportp); + ms = machservice_new(j, servicename, serviceportp, false); if (!launchd_assumes(ms != NULL)) { goto out_bad; Modified: trunk/launchd/src/libbootstrap.c =================================================================== --- trunk/launchd/src/libbootstrap.c 2007-02-22 01:34:11 UTC (rev 23096) +++ trunk/launchd/src/libbootstrap.c 2007-02-22 18:22:46 UTC (rev 23097) @@ -20,6 +20,7 @@ #include "config.h" #include "libbootstrap_public.h" +#include "libbootstrap_private.h" #include "libvproc_public.h" #include "libvproc_private.h" @@ -66,13 +67,19 @@ kern_return_t bootstrap_register(mach_port_t bp, name_t service_name, mach_port_t sp) { - kern_return_t kr = vproc_mig_register(bp, service_name, sp); + return bootstrap_register2(bp, service_name, sp, 0); +} +kern_return_t +bootstrap_register2(mach_port_t bp, name_t service_name, mach_port_t sp, uint64_t flags) +{ + kern_return_t kr = vproc_mig_register2(bp, service_name, sp, flags); + if (kr == VPROC_ERR_TRY_PER_USER) { mach_port_t puc; if (vproc_mig_lookup_per_user_context(bp, 0, &puc) == 0) { - kr = vproc_mig_register(puc, service_name, sp); + kr = vproc_mig_register2(puc, service_name, sp, flags); mach_port_deallocate(mach_task_self(), puc); } } @@ -95,10 +102,16 @@ kern_return_t bootstrap_look_up(mach_port_t bp, name_t service_name, mach_port_t *sp) { + return bootstrap_look_up2(bp, service_name, sp, 0, 0); +} + +kern_return_t +bootstrap_look_up2(mach_port_t bp, name_t service_name, mach_port_t *sp, pid_t target_pid, uint64_t flags) +{ kern_return_t kr; mach_port_t puc; - if ((kr = vproc_mig_look_up(bp, service_name, sp)) != VPROC_ERR_TRY_PER_USER) { + if ((kr = vproc_mig_look_up2(bp, service_name, sp, target_pid, flags)) != VPROC_ERR_TRY_PER_USER) { return kr; } @@ -106,7 +119,7 @@ return kr; } - kr = vproc_mig_look_up(puc, service_name, sp); + kr = vproc_mig_look_up2(puc, service_name, sp, target_pid, flags); mach_port_deallocate(mach_task_self(), puc); return kr; Added: trunk/launchd/src/libbootstrap_private.h =================================================================== --- trunk/launchd/src/libbootstrap_private.h (rev 0) +++ trunk/launchd/src/libbootstrap_private.h 2007-02-22 18:22:46 UTC (rev 23097) @@ -0,0 +1,40 @@ +#ifndef _BOOTSTRAP_PRIVATE_H_ +#define _BOOTSTRAP_PRIVATE_H_ +/* + * Copyright (c) 2007 Apple Inc. All rights reserved. + * + * @APPLE_APACHE_LICENSE_HEADER_START@ + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + * @APPLE_APACHE_LICENSE_HEADER_END@ + */ + +#include <servers/bootstrap.h> +#include <sys/types.h> + +__BEGIN_DECLS + +#pragma GCC visibility push(default) + +#define BOOTSTRAP_PER_PID_SERVICE 1 + +kern_return_t bootstrap_register2(mach_port_t bp, name_t service_name, mach_port_t sp, uint64_t flags); + +kern_return_t bootstrap_look_up2(mach_port_t bp, name_t service_name, mach_port_t *sp, pid_t target_pid, uint64_t flags); + +#pragma GCC visibility pop + +__END_DECLS + +#endif Modified: trunk/launchd/src/protocol_job.defs =================================================================== --- trunk/launchd/src/protocol_job.defs 2007-02-22 01:34:11 UTC (rev 23096) +++ trunk/launchd/src/protocol_job.defs 2007-02-22 18:22:46 UTC (rev 23097) @@ -54,15 +54,18 @@ __service_name : name_t; out __service_port : mach_port_move_receive_t); -routine register( +routine register2( __bs_port : job_t; __service_name : name_t; - __service_port : mach_port_t); + __service_port : mach_port_t; + __flags : uint64_t); -routine look_up( +routine look_up2( __bs_port : job_t; __service_name : name_t; - out __service_port : mach_port_send_t); + out __service_port : mach_port_send_t; + __target_pid : pid_t; + __flags : uint64_t); skip; /* last used in 10.4 */