diff options
author | Richard Lowe <richlowe@richlowe.net> | 2014-04-16 02:39:14 +0100 |
---|---|---|
committer | Richard Lowe <richlowe@richlowe.net> | 2016-10-15 12:02:16 -0400 |
commit | d2a70789f056fc6c9ce3ab047b52126d80b0e3da (patch) | |
tree | bcf5eedbc5aeec80cac59ea37052e3b87108c253 /usr/src/lib/libscf | |
parent | 8ab1c3f559468e655c4eb8acce993320403dd72b (diff) | |
download | illumos-joyent-d2a70789f056fc6c9ce3ab047b52126d80b0e3da.tar.gz |
7029 want per-process exploit mitigation features (secflags)
7030 want basic address space layout randomization (ASLR)
7031 noexec_user_stack should be a security-flag
7032 want a means to forbid mappings around NULL
Reviewed by: Robert Mustacchi <rm@joyent.com>
Reviewed by: Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
Reviewed by: Patrick Mooney <pmooney@joyent.com>
Approved by: Dan McDonald <danmcd@omniti.com>
Diffstat (limited to 'usr/src/lib/libscf')
-rw-r--r-- | usr/src/lib/libscf/common/highlevel.c | 85 | ||||
-rw-r--r-- | usr/src/lib/libscf/common/mapfile-vers | 1 | ||||
-rw-r--r-- | usr/src/lib/libscf/inc/libscf.h | 27 | ||||
-rw-r--r-- | usr/src/lib/libscf/inc/libscf_priv.h | 7 |
4 files changed, 119 insertions, 1 deletions
diff --git a/usr/src/lib/libscf/common/highlevel.c b/usr/src/lib/libscf/common/highlevel.c index dddd551e51..7defe4ef51 100644 --- a/usr/src/lib/libscf/common/highlevel.c +++ b/usr/src/lib/libscf/common/highlevel.c @@ -33,10 +33,12 @@ #include <assert.h> #include <libuutil.h> #include <string.h> +#include <strings.h> #include <stdlib.h> #include <sys/systeminfo.h> #include <sys/uadmin.h> #include <sys/utsname.h> +#include <sys/secflags.h> #ifdef __x86 #include <smbios.h> @@ -353,3 +355,86 @@ scf_is_fastboot_default(void) return (boot_config & boot_config_ovr & UA_FASTREBOOT_DEFAULT); } + +/* + * Read the default security-flags from system/process-security and return a + * secflagset_t suitable for psecflags(2) + * + * Unfortunately, this symbol must _exist_ in the native build, for the sake + * of the mapfile, even though we don't ever use it, and it will never work. + */ +struct group_desc { + secflagdelta_t *delta; + char *fmri; +}; + +int +scf_default_secflags(scf_handle_t *hndl, scf_secflags_t *flags) +{ +#if !defined(NATIVE_BUILD) + scf_property_t *prop; + scf_value_t *val; + const char *flagname; + int flag; + struct group_desc *g; + struct group_desc groups[] = { + {NULL, "svc:/system/process-security/" + ":properties/default"}, + {NULL, "svc:/system/process-security/" + ":properties/lower"}, + {NULL, "svc:/system/process-security/" + ":properties/upper"}, + {NULL, NULL} + }; + + bzero(flags, sizeof (*flags)); + + groups[0].delta = &flags->ss_default; + groups[1].delta = &flags->ss_lower; + groups[2].delta = &flags->ss_upper; + + for (g = groups; g->delta != NULL; g++) { + for (flag = 0; (flagname = secflag_to_str(flag)) != NULL; + flag++) { + char *pfmri; + uint8_t flagval = 0; + + if ((val = scf_value_create(hndl)) == NULL) + return (-1); + + if ((prop = scf_property_create(hndl)) == NULL) { + scf_value_destroy(val); + return (-1); + } + + if ((pfmri = uu_msprintf("%s/%s", g->fmri, + flagname)) == NULL) + uu_die("Allocation failure\n"); + + if (scf_handle_decode_fmri(hndl, pfmri, + NULL, NULL, NULL, NULL, prop, NULL) != 0) + goto next; + + if (scf_property_get_value(prop, val) != 0) + goto next; + + (void) scf_value_get_boolean(val, &flagval); + + if (flagval != 0) + secflag_set(&g->delta->psd_add, flag); + else + secflag_set(&g->delta->psd_rem, flag); + +next: + uu_free(pfmri); + scf_value_destroy(val); + scf_property_destroy(prop); + } + } + + return (0); +#else + assert(0); + abort(); +#endif /* !NATIVE_BUILD */ +} diff --git a/usr/src/lib/libscf/common/mapfile-vers b/usr/src/lib/libscf/common/mapfile-vers index 643f5424f2..049912185c 100644 --- a/usr/src/lib/libscf/common/mapfile-vers +++ b/usr/src/lib/libscf/common/mapfile-vers @@ -328,6 +328,7 @@ SYMBOL_VERSION SUNWprivate_1.1 { scf_get_boot_config_ovr; scf_is_fastboot_default; scf_fastreboot_default_set_transient; + scf_default_secflags; _check_services; _scf_handle_create_and_bind; _smf_refresh_all_instances; diff --git a/usr/src/lib/libscf/inc/libscf.h b/usr/src/lib/libscf/inc/libscf.h index c00a59dc5d..cf2db82bf3 100644 --- a/usr/src/lib/libscf/inc/libscf.h +++ b/usr/src/lib/libscf/inc/libscf.h @@ -28,9 +28,13 @@ #include <stddef.h> -#include <sys/types.h> #include <libnvpair.h> +#ifndef NATIVE_BUILD +#include <sys/secflags.h> +#endif /* NATIVE_BUILD */ +#include <sys/types.h> + #ifdef __cplusplus extern "C" { #endif @@ -197,6 +201,26 @@ typedef enum scf_tmpl_error_type { typedef struct scf_tmpl_error scf_tmpl_error_t; /* + * This unfortunately needs to be public, because consumers of librestart must + * deal with it + */ +typedef struct { +#ifndef NATIVE_BUILD + secflagdelta_t ss_default; + secflagdelta_t ss_lower; + secflagdelta_t ss_upper; +#else + /* + * This is never used, but is necessary for bootstrapping. + * Not even the size matters. + */ + void *ss_default; + void *ss_lower; + void *ss_upper; +#endif /* NATIVE_BUILD */ +} scf_secflags_t; + +/* * scf_tmpl_strerror() human readable flag */ #define SCF_TMPL_STRERROR_HUMAN 0x1 @@ -328,6 +352,7 @@ typedef struct scf_tmpl_error scf_tmpl_error_t; #define SCF_PROPERTY_RESTART_INTERVAL ((const char *)"restart_interval") #define SCF_PROPERTY_RESTART_ON ((const char *)"restart_on") #define SCF_PROPERTY_RESTORE ((const char *)"restore") +#define SCF_PROPERTY_SECFLAGS ((const char *)"security_flags") #define SCF_PROPERTY_SINGLE_INSTANCE ((const char *)"single_instance") #define SCF_PROPERTY_START_METHOD_TIMESTAMP \ ((const char *)"start_method_timestamp") diff --git a/usr/src/lib/libscf/inc/libscf_priv.h b/usr/src/lib/libscf/inc/libscf_priv.h index 3e05042e0c..3ad2564322 100644 --- a/usr/src/lib/libscf/inc/libscf_priv.h +++ b/usr/src/lib/libscf/inc/libscf_priv.h @@ -29,6 +29,9 @@ #include <libscf.h> #include <unistd.h> +#if !defined(NATIVE_BUILD) +#include <sys/secflags.h> +#endif #ifdef __cplusplus extern "C" { @@ -592,6 +595,10 @@ int _scf_get_svc_notify_params(const char *, nvlist_t *, int32_t, int, int); */ int _scf_notify_get_params(scf_propertygroup_t *, nvlist_t *); +#if !defined(NATIVE_BUILD) +int scf_default_secflags(scf_handle_t *, scf_secflags_t *); +#endif + #define SCF_NOTIFY_PARAMS_SOURCE_NAME ((const char *)"preference_source") #ifdef __cplusplus |