[launchd-changes] [23025] trunk/launchd/src

source_changes at macosforge.org source_changes at macosforge.org
Sun Jan 28 13:15:54 PST 2007


Revision: 23025
          http://trac.macosforge.org/projects/launchd/changeset/23025
Author:   zarzycki at apple.com
Date:     2007-01-28 13:15:53 -0800 (Sun, 28 Jan 2007)

Log Message:
-----------
The last remaining customer (loginwindow) of /etc/ttys has switched to launchd.

This is the easy part or removing init.c. The next stage will be to deal with
single-user-mode in launchd proper and clean up launchd's self-bootstrap logic.
Then we can finally delete init.c.

Modified Paths:
--------------
    trunk/launchd/src/init.c
    trunk/launchd/src/launchctl.1
    trunk/launchd/src/launchctl.c
    trunk/launchd/src/launchd.c
    trunk/launchd/src/launchd.h
    trunk/launchd/src/launchd_unix_ipc.c
    trunk/launchd/src/liblaunch_private.h

Modified: trunk/launchd/src/init.c
===================================================================
--- trunk/launchd/src/init.c	2007-01-26 23:45:13 UTC (rev 23024)
+++ trunk/launchd/src/init.c	2007-01-28 21:15:53 UTC (rev 23025)
@@ -55,10 +55,6 @@
 
 static const char *const __rcs_file_version__ = "$Revision$";
 
-#include <Security/Authorization.h>
-#include <Security/AuthorizationTags.h>
-#include <Security/AuthSession.h>
-
 #include <sys/types.h>
 #include <sys/queue.h>
 #include <sys/param.h>
@@ -91,14 +87,7 @@
 
 #define _PATH_RUNCOM            "/etc/rc"
 
-/*
- * Sleep times; used to prevent thrashing.
- */
-#define	GETTY_SPACING		 5	/* N secs minimum getty spacing */
-#define	GETTY_SLEEP		30	/* sleep N secs after spacing problem */
 #define	STALL_TIMEOUT		30	/* wait N secs after warning */
-#define	DEATH_WATCH		10	/* wait N secs for procs to die */
-#define FAILED_HW_PASS		 5	/* wait N secs before croaking user */
 
 static void stall(char *, ...);
 
@@ -117,58 +106,8 @@
 
 static void setctty(const char *, int);
 
-// gvdl at next.com 14 Aug 1995
-//   - from ~apps/loginwindow_proj/loginwindow/common.h
-#define REALLY_EXIT_TO_CONSOLE                  229
-
-// From old init.c
-// These flags are used in the se_flags field of the init_session structure
-#define	SE_SHUTDOWN	0x1		/* session won't be restarted */
-
-// The flags below control what sort of getty is launched.
-#define SE_GETTY_LAUNCH	0x30	/* What type of getty to launch */ 
-#define SE_COMMON	0x00	/* Usual command that is run - getty */
-#define SE_ONERROR	0x10	/* Command to run if error condition occurs.
-				 * This will almost always be the windowserver
-				 * and loginwindow.  This is so if the w.s.
-				 * ever dies, that the naive user (stan)
-				 * doesn't ever see the console window. */
-#define SE_ONOPTION 	0x20	/* Command to run when loginwindow exits with
-				 * special error code (229).  This signifies
-				 * that the user typed "console" at l.w. and
-				 * l.w. wants to exit and have init run getty
-				 * which will then put up a console window. */
-
-typedef struct _se_command {
-	char	*path;		/* what to run on that port */
-	char	**argv;		/* pre-parsed argument array */
-} se_cmd_t;
-
-typedef struct init_session {
-	kq_callback se_callback;	/* run loop callback */
-	int	se_index;		/* index of entry in ttys file */
-	pid_t	se_process;		/* controlling process */
-	time_t	se_started;		/* used to avoid thrashing */
-	int	se_flags;		/* status of session */
-	char	*se_device;		/* filename of port */
-	se_cmd_t se_getty;		/* what to run on that port */
-	se_cmd_t se_onerror;		/* See SE_ONERROR above */
-	se_cmd_t se_onoption;		/* See SE_ONOPTION above */
-	TAILQ_ENTRY(init_session) tqe;
-} *session_t;
-
-static TAILQ_HEAD(sessionshead, init_session) sessions = TAILQ_HEAD_INITIALIZER(sessions);
-
-static void session_new(int, struct ttyent *);
-static void session_free(session_t);
-static void session_launch(session_t);
-static void session_reap(session_t);
-static void session_callback(void *, struct kevent *);
-
-static char **construct_argv(char *);
 static void setsecuritylevel(int);
 static int getsecuritylevel(void);
-static int setupargv(session_t, struct ttyent *);
 static bool should_fsck(void);
 
 void
@@ -183,8 +122,6 @@
 void
 init_pre_kevent(void)
 {
-	session_t s;
-
 	if (single_user_pid || runcom_pid)
 		return;
 
@@ -200,16 +137,12 @@
 	 * mode, and the run script has not set a higher level of security 
 	 * than level 1, then put the kernel into secure mode.
 	 */
-	if (getsecuritylevel() == 0)
+	if (getsecuritylevel() == 0) {
 		setsecuritylevel(1);
-
-	TAILQ_FOREACH(s, &sessions, tqe) {
-		if (s->se_process == 0)
-			session_launch(s);
 	}
 }
 
-static void
+void
 stall(char *message, ...)
 {
 	va_list ap;
@@ -220,7 +153,7 @@
 	sleep(STALL_TIMEOUT);
 }
 
-static int
+int
 getsecuritylevel(void)
 {
 	int name[2], curlevel;
@@ -236,7 +169,7 @@
 	return curlevel;
 }
 
-static void
+void
 setsecuritylevel(int newlevel)
 {
 	int name[2], curlevel;
@@ -259,7 +192,7 @@
  * Start a session and allocate a controlling terminal.
  * Only called by children of init after forking.
  */
-static void
+void
 setctty(const char *name, int flags)
 {
 	int fd;
@@ -275,7 +208,7 @@
 	}
 }
 
-static void
+void
 single_user(void)
 {
 	bool runcom_fsck = should_fsck();
@@ -315,7 +248,7 @@
 	}
 }
 
-static void
+void
 single_user_callback(void *obj __attribute__((unused)), struct kevent *kev __attribute__((unused)))
 {
 	int status;
@@ -338,10 +271,11 @@
 }
 
 static struct timeval runcom_start_tv = { 0, 0 };
+
 /*
  * Run the system startup script.
  */
-static void
+void
 runcom(void)
 {
 	char *argv[] = { "/bin/launchctl", "bootstrap", NULL };
@@ -389,7 +323,7 @@
 	exit(EXIT_FAILURE);
 }
 
-static void
+void
 runcom_callback(void *obj __attribute__((unused)), struct kevent *kev __attribute__((unused)))
 {
 	int status;
@@ -421,323 +355,9 @@
 	single_user_mode = true;
 }
 
-/*
- * Construct an argument vector from a command line.
- */
-char **
-construct_argv(command)
-	char *command;
+bool
+init_check_pid(pid_t p)
 {
-	int argc = 0;
-	char **argv = (char **) malloc(((strlen(command) + 1) / 2 + 1)
-						* sizeof (char *));
-	static const char separators[] = " \t";
-
-	if ((argv[argc++] = strtok(command, separators)) == 0)
-		return 0;
-	while ((argv[argc++] = strtok(NULL, separators)))
-		continue;
-	return argv;
-}
-
-/*
- * Deallocate a session descriptor.
- */
-
-static void free_command(se_cmd_t *se_cmd)
-{
-    if (se_cmd->path) {
-	free(se_cmd->path);
-	free(se_cmd->argv);
-    }
-}
-
-void
-session_free(session_t s)
-{
-	TAILQ_REMOVE(&sessions, s, tqe);
-	if (s->se_process) {
-		if (kevent_mod(s->se_process, EVFILT_PROC, EV_ADD, 
-					NOTE_EXIT, 0, &kqsimple_zombie_reaper) == -1)
-			session_reap(s);
-		else
-			kill(s->se_process, SIGHUP);
-	}
-	free(s->se_device);
-	free_command(&s->se_getty);
-	free_command(&s->se_onerror);
-	free_command(&s->se_onoption);
-	free(s);
-}
-
-static int setup_command(se_cmd_t *se_cmd, char *command, char *arg )
-{
-	char *commandWithArg;
-
-	asprintf(&commandWithArg, "%s %s", command, arg);
-
-	free_command(se_cmd);
-
-	se_cmd->path = commandWithArg;
-	se_cmd->argv = construct_argv(commandWithArg);
-	if (se_cmd->argv == NULL) {
-		free(se_cmd->path);
-		se_cmd->path = NULL;
-		return 0;
-	}
-	return 1;
-}
-
-/*
- * Calculate getty and if useful window argv vectors.
- */
-static int
-setupargv(sp, typ)
-	session_t sp;
-	struct ttyent *typ;
-{
-    char *type;
-
-    if ( !setup_command(&sp->se_getty, typ->ty_getty, typ->ty_name) )
-    {
-	type = "getty";
-	goto bad_args;
-    }
-
-    if (typ->ty_onerror
-    && !setup_command(&sp->se_onerror, typ->ty_onerror, typ->ty_name) )
-    {
-	type = "onerror";
-	goto bad_args;
-    }
-
-    if (typ->ty_onoption
-    && !setup_command(&sp->se_onoption, typ->ty_onoption, typ->ty_name) )
-    {
-	type = "onoption";
-	goto bad_args;
-    }
-
-    return 1;
-
-bad_args:
-    syslog(LOG_WARNING, "can't parse %s for port %s", type, sp->se_device);
-    return 0;
-}
-
-
-/*
- * Allocate a new session descriptor.
- */
-void
-session_new(session_index, typ)
-	int session_index;
-	struct ttyent *typ;
-{
-	session_t s;
-
-	if ((typ->ty_status & TTY_ON) == 0 ||
-	    typ->ty_name == 0 ||
-	    typ->ty_getty == 0)
-		return;
-
-	s = calloc(1, sizeof(struct init_session));
-
-	s->se_callback = session_callback;
-	s->se_index = session_index;
-
-	TAILQ_INSERT_TAIL(&sessions, s, tqe);
-
-	asprintf(&s->se_device, "%s%s", _PATH_DEV, typ->ty_name);
-
-	if (setupargv(s, typ) == 0)
-		session_free(s);
-}
-
-static void
-session_launch(session_t s)
-{
-	pid_t pid;
-	sigset_t mask;
-	se_cmd_t *se_cmd;
-	const char *session_type = NULL;
-	time_t current_time      = time(NULL);
-	bool is_loginwindow = false;
-
-	// Setup the default values;
-	switch (s->se_flags & SE_GETTY_LAUNCH) {
-	case SE_ONOPTION:
-		if (s->se_onoption.path) {
-			se_cmd       = &s->se_onoption;
-			session_type = "onoption";
-			break;
-		}
-		/* No break */
-	case SE_ONERROR:
-		if (s->se_onerror.path) {
-			se_cmd       = &s->se_onerror;
-			session_type = "onerror";
-			break;
-		}
-		/* No break */
-	case SE_COMMON:
-	default:
-		se_cmd       = &s->se_getty;
-		session_type = "getty";
-		break;
-	}
-
-	if (strcmp(se_cmd->argv[0], "/System/Library/CoreServices/loginwindow.app/Contents/MacOS/loginwindow") == 0)
-		is_loginwindow = true;
-
-	pid = launchd_fork();
-
-	if (pid == -1) {
-		syslog(LOG_ERR, "can't fork for %s on port %s: %m",
-				session_type, s->se_device);
-		return;
-	}
-
-	if (pid) {
-		s->se_process = pid;
-		s->se_started = time(NULL);
-		s->se_flags  &= ~SE_GETTY_LAUNCH; // clear down getty launch type
-		if (kevent_mod(pid, EVFILT_PROC, EV_ADD, NOTE_EXIT, 0, &s->se_callback) == -1)
-			session_reap(s);
-		return;
-	}
-
-	if (current_time > s->se_started &&
-	    current_time - s->se_started < GETTY_SPACING) {
-		syslog(LOG_WARNING, "%s repeating too quickly on port %s, sleeping",
-		        session_type, s->se_device);
-		sleep(GETTY_SLEEP);
-	}
-
-	sigemptyset(&mask);
-	sigprocmask(SIG_SETMASK, &mask, NULL);
-
-
-	if (!is_loginwindow)
-		launchd_SessionCreate();
-
-	execv(se_cmd->argv[0], se_cmd->argv);
-	stall("can't exec %s '%s' for port %s: %m", session_type,
-		se_cmd->argv[0], s->se_device);
-	exit(EXIT_FAILURE);
-}
-
-static void
-session_callback(void *obj, struct kevent *kev __attribute__((unused)))
-{
-	session_t s = obj;
-
-	session_reap(s);
-	if (s->se_flags & SE_SHUTDOWN) {
-		session_free(s);
-	} else {
-		session_launch(s);
-	}
-}
-
-static void
-session_reap(session_t s)
-{
-	char *line;
-	int status;
-
-	if (!launchd_assumes(waitpid(s->se_process, &status, 0) == s->se_process))
-		return;
-
-	if (WIFSIGNALED(status)) {
-		syslog(LOG_WARNING, "%s port %s exited abnormally: %s",
-				s->se_getty.path, s->se_device, strsignal(WTERMSIG(status)));
-		s->se_flags |= SE_ONERROR; 
-	} else if (WEXITSTATUS(status) == REALLY_EXIT_TO_CONSOLE) {
-		/* WIFEXITED(status) assumed */
-		s->se_flags |= SE_ONOPTION;
-	} else {
-		s->se_flags |= SE_ONERROR;
-	}
-
-	s->se_process = 0;
-	line = s->se_device + sizeof(_PATH_DEV) - 1;
-
-	if (logout(line))
-		logwtmp(line, "", "");
-}
-
-/*
- * This is an n-squared algorithm.  We hope it isn't run often...
- */
-void
-update_ttys(void)
-{
-	session_t sp;
-	struct ttyent *typ;
-	int session_index = 0;
-	int devlen;
-
-	devlen = sizeof(_PATH_DEV) - 1;
-	while ((typ = getttyent())) {
-		++session_index;
-
-		TAILQ_FOREACH(sp, &sessions, tqe) {
-			if (strcmp(typ->ty_name, sp->se_device + devlen) == 0)
-				break;
-		}
-
-		if (sp == NULL) {
-			session_new(session_index, typ);
-			continue;
-		}
-
-		if (sp->se_index != session_index) {
-			syslog(LOG_INFO, "port %s changed utmp index from %d to %d",
-			       sp->se_device, sp->se_index,
-			       session_index);
-			sp->se_index = session_index;
-		}
-
-		if ((typ->ty_status & TTY_ON) == 0 ||
-		    typ->ty_getty == 0) {
-			session_free(sp);
-			continue;
-		}
-
-		sp->se_flags &= ~SE_SHUTDOWN;
-
-		if (setupargv(sp, typ) == 0) {
-			syslog(LOG_WARNING, "can't parse getty for port %s",
-				sp->se_device);
-			session_free(sp);
-		}
-	}
-
-	endttyent();
-}
-
-/*
- * Block further logins.
- */
-void
-catatonia(void)
-{
-	session_t s;
-
-	TAILQ_FOREACH(s, &sessions, tqe)
-		s->se_flags |= SE_SHUTDOWN;
-}
-
-bool init_check_pid(pid_t p)
-{
-	session_t s;
-
-	TAILQ_FOREACH(s, &sessions, tqe) {
-		if (s->se_process == p)
-			return true;
-	}
-
 	if (single_user_pid == p)
 		return true;
 

Modified: trunk/launchd/src/launchctl.1
===================================================================
--- trunk/launchd/src/launchctl.1	2007-01-26 23:45:13 UTC (rev 23024)
+++ trunk/launchd/src/launchctl.1	2007-01-28 21:15:53 UTC (rev 23025)
@@ -140,10 +140,6 @@
 Tell
 .Nm launchd
 to prepare for shutdown by removing all jobs.
-.It Ar reloadttys
-Tell
-.Nm launchd
-to reread /etc/ttys. This option may go away in a future release.
 .It Ar umask Op Ar newmask
 Get or optionally set the
 .Xr umask 2

Modified: trunk/launchd/src/launchctl.c
===================================================================
--- trunk/launchd/src/launchctl.c	2007-01-26 23:45:13 UTC (rev 23024)
+++ trunk/launchd/src/launchctl.c	2007-01-28 21:15:53 UTC (rev 23025)
@@ -134,7 +134,6 @@
 static void empty_dir(const char *thedir, struct stat *psb);
 static int touch_file(const char *path, mode_t m);
 static void do_sysversion_sysctl(void);
-static void workaround4465949(void);
 static void do_application_firewall_magic(int sfd, launch_data_t thejob);
 static void preheat_page_cache_hack(void);
 static void do_bootroot_magic(void);
@@ -185,7 +184,6 @@
 	{ "stderr",	stdio_cmd,		"Redirect launchd's standard error to the given path" },
 	{ "shutdown",	fyi_cmd,		"Prepare for system shutdown" },
 	{ "singleuser",	fyi_cmd,		"Switch to single-user mode" },
-	{ "reloadttys",	fyi_cmd,		"Reload /etc/ttys" },
 	{ "getrusage",	getrusage_cmd,		"Get resource usage statistics from launchd" },
 	{ "log",	logupdate_cmd,		"Adjust the logging level or mask of launchd" },
 	{ "umask",	umask_cmd,		"Change launchd's umask" },
@@ -1279,8 +1277,6 @@
 	const char *SystemStarter_tool[] = { "SystemStarter", NULL };
 	assumes(fwexec(SystemStarter_tool, false) != -1);
 
-	workaround4465949();
-
 	if (path_check("/etc/rc.local")) {
 		const char *rc_local_tool[] = { _PATH_BSHELL, "/etc/rc.local", NULL };
 		assumes(fwexec(rc_local_tool, false) != -1);
@@ -1289,32 +1285,6 @@
 	return 0;
 }
 
-void
-workaround4465949(void)
-{
-	const char *pbs_tool[] = { "/System/Library/CoreServices/pbs", NULL };
-	const char *lca_tool[] = { "/System/Library/CoreServices/Language Chooser.app/Contents/MacOS/Language Chooser", NULL};
-	char *const reloadttys_argv[] = { "reloadttys", NULL };
-	int wstatus;
-	pid_t pbs_p;
-
-	if (path_check("/System/Library/LaunchDaemons/com.apple.loginwindow.plist")) {
-		return;
-	}
-
-	if (path_check(pbs_tool[0]) && path_check(lca_tool[0]) &&
-			!path_check("/var/db/.AppleSetupDone") &&
-			path_check("/var/db/.RunLanguageChooserToo")) {
-		if (assumes((pbs_p = fwexec(pbs_tool, false)) != -1)) {
-			assumes(fwexec(lca_tool, true) != -1);
-			assumes(kill(pbs_p, SIGTERM) != -1);
-			assumes(waitpid(pbs_p, &wstatus, 0) != -1);
-		}
-	}
-
-	assumes(fyi_cmd(1, reloadttys_argv) == 0);
-}
-
 int
 load_and_unload_cmd(int argc, char *const argv[])
 {
@@ -1763,7 +1733,7 @@
 fyi_cmd(int argc, char *const argv[])
 {
 	launch_data_t resp, msg;
-	const char *lmsgk = LAUNCH_KEY_RELOADTTYS;
+	const char *lmsgk = NULL;
 	int e, r = 0;
 
 	if (argc != 1) {
@@ -1775,6 +1745,8 @@
 		lmsgk = LAUNCH_KEY_SHUTDOWN;
 	} else if (!strcmp(argv[0], "singleuser")) {
 		lmsgk = LAUNCH_KEY_SINGLEUSER;
+	} else {
+		return 1;
 	}
 
 	msg = launch_data_new_string(lmsgk);

Modified: trunk/launchd/src/launchd.c
===================================================================
--- trunk/launchd/src/launchd.c	2007-01-26 23:45:13 UTC (rev 23024)
+++ trunk/launchd/src/launchd.c	2007-01-28 21:15:53 UTC (rev 23025)
@@ -469,10 +469,6 @@
 	rlcj = NULL;
 
 	jobmgr_remove_all_inactive(root_jobmgr);
-
-	if (getpid() == 1) {
-		catatonia();
-	}
 }
 
 void

Modified: trunk/launchd/src/launchd.h
===================================================================
--- trunk/launchd/src/launchd.h	2007-01-26 23:45:13 UTC (rev 23024)
+++ trunk/launchd/src/launchd.h	2007-01-28 21:15:53 UTC (rev 23025)
@@ -55,9 +55,6 @@
 void init_boot(bool sflag);
 void init_pre_kevent(void);
 
-void update_ttys(void);
-void catatonia(void);
-
 void mach_start_shutdown(void);
 void mach_init_init(mach_port_t);
 

Modified: trunk/launchd/src/launchd_unix_ipc.c
===================================================================
--- trunk/launchd/src/launchd_unix_ipc.c	2007-01-26 23:45:13 UTC (rev 23024)
+++ trunk/launchd/src/launchd_unix_ipc.c	2007-01-28 21:15:53 UTC (rev 23025)
@@ -352,9 +352,6 @@
 			} else {
 				resp = launch_data_new_errno(EACCES);
 			}
-		} else if (!strcmp(cmd, LAUNCH_KEY_RELOADTTYS)) {
-			update_ttys();
-			resp = launch_data_new_errno(0);
 		} else if (!strcmp(cmd, LAUNCH_KEY_SHUTDOWN)) {
 			launchd_shutdown();
 			resp = launch_data_new_errno(0);

Modified: trunk/launchd/src/liblaunch_private.h
===================================================================
--- trunk/launchd/src/liblaunch_private.h	2007-01-26 23:45:13 UTC (rev 23024)
+++ trunk/launchd/src/liblaunch_private.h	2007-01-28 21:15:53 UTC (rev 23025)
@@ -37,7 +37,6 @@
 #define LAUNCH_KEY_SINGLEUSER		"SingleUser"
 #define LAUNCH_KEY_GETRESOURCELIMITS	"GetResourceLimits"
 #define LAUNCH_KEY_SETRESOURCELIMITS	"SetResourceLimits"
-#define LAUNCH_KEY_RELOADTTYS		"ReloadTTYS"
 #define LAUNCH_KEY_SETLOGMASK		"SetLogMask"
 #define LAUNCH_KEY_GETLOGMASK		"GetLogMask"
 #define LAUNCH_KEY_SETUMASK		"SetUmask"

-------------- next part --------------
An HTML attachment was scrubbed...
URL: http://lists.macosforge.org/pipermail/launchd-changes/attachments/20070128/83f80ca6/attachment.html


More information about the launchd-changes mailing list