From 0364bb2c84bff631e0f765254fc6bf3353950128 Mon Sep 17 00:00:00 2001 From: Roy Marples Date: Tue, 19 Feb 2008 14:15:53 +0000 Subject: Add the nojail keyword which excludes services marked as such from the dependency tree when in a jail, #bug 22 --- src/librc/librc-depend.c | 53 +++++++++++++++++++++++++++++++++++++++++------- src/librc/librc.c | 33 ++++++++++++++++++++++++++++++ src/librc/librc.h | 1 + src/librc/rc.h | 10 +++++++++ src/librc/rc.map | 1 + 5 files changed, 91 insertions(+), 7 deletions(-) (limited to 'src/librc') diff --git a/src/librc/librc-depend.c b/src/librc/librc-depend.c index 59284344..c7c782c7 100644 --- a/src/librc/librc-depend.c +++ b/src/librc/librc-depend.c @@ -741,24 +741,23 @@ bool rc_deptree_update (void) rc_deptype_t *dt; rc_deptype_t *last_deptype = NULL; char *line; - int len; - int i; - int j; - int k; + size_t len; + size_t i; + size_t j; + size_t k; bool already_added; + const char *sys = rc_sys (); /* Some init scripts need RC_LIBDIR to source stuff Ideally we should be setting our full env instead */ if (! getenv ("RC_LIBDIR")) setenv ("RC_LIBDIR", RC_LIBDIR, 0); - /* Phase 1 */ + /* Phase 1 - source all init scripts and print dependencies */ if (! (fp = popen (GENDEP, "r"))) return (false); deptree = xzalloc (sizeof (*deptree)); - - /* Phase 2 */ while ((line = rc_getline (fp))) { depends = line; @@ -865,6 +864,46 @@ next: } pclose (fp); + /* Phase 2 - if we're a special system, remove services that don't + * work for them. This doesn't stop them from being run directly. */ + if (sys) { + char *nosys; + + len = strlen (sys); + nosys = xmalloc (len + 3); + nosys[0] = 'n'; + nosys[1] = 'o'; + for (i = 0; i < len; i++) + nosys[i + 2] = tolower (sys[i]); + nosys[i + 2] = '\0'; + + last_depinfo = NULL; + for (depinfo = deptree; depinfo; depinfo = depinfo->next) + { + bool removed = false; + if ((deptype = get_deptype (depinfo, "keywords"))) { + STRLIST_FOREACH (deptype->services, service, i) + if (strcmp (service, nosys) == 0) { + if (last_depinfo) + last_depinfo->next = depinfo->next; + else + deptree = depinfo->next; + removed = true; + break; + } + } + if (removed) { + for (di = deptree; di; di = di->next) { + for (dt = di->depends; dt; dt = dt->next) + rc_strlist_delete (&dt->services, depinfo->service); + } + } else + last_depinfo = depinfo; + } + + free (nosys); + } + /* Phase 3 - add our providors to the tree */ for (depinfo = deptree; depinfo; depinfo = depinfo->next) { diff --git a/src/librc/librc.c b/src/librc/librc.c index 75019eec..f323d0fd 100644 --- a/src/librc/librc.c +++ b/src/librc/librc.c @@ -32,6 +32,9 @@ const char librc_copyright[] = "Copyright (c) 2007-2008 Roy Marples"; #include "librc.h" +#ifdef __FreeBSD__ +#include +#endif #include #define SOFTLEVEL RC_SVCDIR "/softlevel" @@ -144,6 +147,36 @@ static bool rm_dir (const char *pathname, bool top) return (true); } +const char *rc_sys (void) +{ +#ifdef __FreeBSD__ + int jailed = 0; + size_t len = sizeof (jailed); + + if (sysctlbyname ("security.jail.jailed", &jailed, &len, NULL, 0) == 0) + if (jailed == 1) + return (RC_SYS_JAIL); +#endif + +#ifdef __linux__ + if (exists ("/proc/xen")) { + if ((fp = fopen ("/proc/xen/capabilities", "r"))) { + fclose (fp); + if (file_regex ("/proc/xen/capabilities", "control_d")) + return (RC_SYS_XEN0); + } + if (! sys[0]) + return (RC_SYS_XENU); + } else if (file_regex ("/proc/cpuinfo", "UML")) + return (RC_SYS_UML); + else if (file_regex ("/proc/self/status", + "(s_context|VxID|envID):[[:space:]]*[1-9]")) + return (RC_SYS_VPS); +#endif + + return (NULL); +} + static const char *rc_parse_service_state (rc_service_state_t state) { int i; diff --git a/src/librc/librc.h b/src/librc/librc.h index 7a5d9a0e..7e917e3a 100644 --- a/src/librc/librc.h +++ b/src/librc/librc.h @@ -40,6 +40,7 @@ #include #include +#include #include #include #include diff --git a/src/librc/rc.h b/src/librc/rc.h index 1f1a9a76..690b14f6 100644 --- a/src/librc/rc.h +++ b/src/librc/rc.h @@ -228,6 +228,16 @@ char **rc_services_scheduled (const char *service); * @return true if all daemons started are still running, otherwise false */ bool rc_service_daemons_crashed (const char *service); +/*! @name System types + * OpenRC can support some special sub system types, normally virtualization. + * Some services cannot work in these systems, or we do something else. */ +#define RC_SYS_JAIL "JAIL" +#define RC_SYS_UML "UML" +#define RC_SYS_VPS "VPS" +#define RC_SYS_XEN0 "XEN0" +#define RC_SYS_XENU "XENU" +const char *rc_sys (void); + /*! @name Dependency options * These options can change the services found by the rc_get_depinfo and * rc_get_depends functions. */ diff --git a/src/librc/rc.map b/src/librc/rc.map index e60ea183..e5fd350b 100644 --- a/src/librc/rc.map +++ b/src/librc/rc.map @@ -52,6 +52,7 @@ global: rc_strlist_free; rc_strlist_join; rc_strlist_reverse; + rc_sys; rc_yesno; local: -- cgit v1.2.3