From fae75e940641d1248d2cffde9ed568f121a755f5 Mon Sep 17 00:00:00 2001 From: Michal Orzel Date: Tue, 12 Mar 2024 13:03:42 +0100 Subject: [PATCH] xen: Add support for specifying XSM FLASK label for dom0less domUs At the moment, it is not possible to create dom0less domUs with XSM FLASK policy (enforcing). This is because they are not being assigned any usable default label (neither in flask_domain_alloc_security() nor by setting initial ssidref in domain creation flags) and as such, they are of type unlabeled_t. Introduce a new XSM op called seclabel_to_sid together with hooks xsm_seclabel_to_sid() and flask_seclabel_to_sid(). In the latter case, this results in calling security_context_to_sid() that converts a security label into SID. Add support for specifying a security label (just like in xl.cfg) for dom0less domUs by adding a new device tree string property 'seclabel'. Signed-off-by: Michal Orzel --- docs/misc/arm/device-tree/booting.txt | 6 ++++++ xen/arch/arm/dom0less-build.c | 12 ++++++++++++ xen/include/xsm/dummy.h | 6 ++++++ xen/include/xsm/xsm.h | 7 +++++++ xen/xsm/dummy.c | 1 + xen/xsm/flask/hooks.c | 7 +++++++ 6 files changed, 39 insertions(+) diff --git a/docs/misc/arm/device-tree/booting.txt b/docs/misc/arm/device-tree/booting.txt index bbd955e9c2f6..4eba0524ad41 100644 --- a/docs/misc/arm/device-tree/booting.txt +++ b/docs/misc/arm/device-tree/booting.txt @@ -260,6 +260,12 @@ with the following properties: value specified by Xen command line parameter gnttab_max_maptrack_frames (or its default value if unspecified, i.e. 1024) is used. +- seclabel + + Optional. A string property specifying XSM FLASK security label for + the domain in format user:role:type (e.g. system_u:system_r:domU_t). + If this property is missing, the domain will be of type unlabeled_t. + Under the "xen,domain" compatible node, one or more sub-nodes are present for the DomU kernel and ramdisk. diff --git a/xen/arch/arm/dom0less-build.c b/xen/arch/arm/dom0less-build.c index fb63ec6fd111..b6c762d6ee3d 100644 --- a/xen/arch/arm/dom0less-build.c +++ b/xen/arch/arm/dom0less-build.c @@ -10,6 +10,8 @@ #include #include +#include + #include #include #include @@ -869,6 +871,7 @@ void __init create_domUs(void) .grant_opts = XEN_DOMCTL_GRANT_version(opt_gnttab_max_version), }; unsigned int flags = 0U; + const char *seclabel; uint32_t val; int rc; @@ -987,6 +990,15 @@ void __init create_domUs(void) #endif } + if ( !dt_property_read_string(node, "seclabel", &seclabel) ) + { + rc = xsm_seclabel_to_sid(seclabel, strlen(seclabel), + &d_cfg.ssidref); + if ( rc ) + panic("Could not convert seclabel \"%s\" to sid (%d)\n", + seclabel, rc); + } + /* * The variable max_init_domid is initialized with zero, so here it's * very important to use the pre-increment operator to call diff --git a/xen/include/xsm/dummy.h b/xen/include/xsm/dummy.h index 8671af1ba4d3..4b63b6c36241 100644 --- a/xen/include/xsm/dummy.h +++ b/xen/include/xsm/dummy.h @@ -815,6 +815,12 @@ static XSM_INLINE int cf_check xsm_argo_send( #endif /* CONFIG_ARGO */ +static XSM_INLINE int cf_check xsm_seclabel_to_sid( + const char *seclabel, size_t len, uint32_t *sid) +{ + return -ENOSYS; +} + #include static XSM_INLINE int cf_check xsm_xen_version(XSM_DEFAULT_ARG uint32_t op) { diff --git a/xen/include/xsm/xsm.h b/xen/include/xsm/xsm.h index 8dad03fd3d45..575a141ee26a 100644 --- a/xen/include/xsm/xsm.h +++ b/xen/include/xsm/xsm.h @@ -201,6 +201,7 @@ struct xsm_ops { int (*argo_register_any_source)(const struct domain *d); int (*argo_send)(const struct domain *d, const struct domain *t); #endif + int (*seclabel_to_sid)(const char *seclabel, size_t len, uint32_t *sid); }; #ifdef CONFIG_XSM @@ -774,6 +775,12 @@ static inline int xsm_argo_send(const struct domain *d, const struct domain *t) #endif /* CONFIG_ARGO */ +static inline int xsm_seclabel_to_sid( + const char *seclabel, size_t len, uint32_t *sid) +{ + return alternative_call(xsm_ops.seclabel_to_sid, seclabel, len, sid); +} + #endif /* XSM_NO_WRAPPERS */ #ifdef CONFIG_MULTIBOOT diff --git a/xen/xsm/dummy.c b/xen/xsm/dummy.c index e6ffa948f7c5..ba1b3def52db 100644 --- a/xen/xsm/dummy.c +++ b/xen/xsm/dummy.c @@ -148,6 +148,7 @@ static const struct xsm_ops __initconst_cf_clobber dummy_ops = { .argo_register_any_source = xsm_argo_register_any_source, .argo_send = xsm_argo_send, #endif + .seclabel_to_sid = xsm_seclabel_to_sid, }; void __init xsm_fixup_ops(struct xsm_ops *ops) diff --git a/xen/xsm/flask/hooks.c b/xen/xsm/flask/hooks.c index 78225f68c15c..bc1520b4b5dd 100644 --- a/xen/xsm/flask/hooks.c +++ b/xen/xsm/flask/hooks.c @@ -1838,6 +1838,12 @@ static int cf_check flask_argo_send( #endif +static int cf_check flask_seclabel_to_sid( + const char *seclabel, size_t len, uint32_t *sid) +{ + return security_context_to_sid((char *)seclabel, len, sid); +} + static const struct xsm_ops __initconst_cf_clobber flask_ops = { .set_system_active = flask_set_system_active, .security_domaininfo = flask_security_domaininfo, @@ -1974,6 +1980,7 @@ static const struct xsm_ops __initconst_cf_clobber flask_ops = { .argo_register_any_source = flask_argo_register_any_source, .argo_send = flask_argo_send, #endif + .seclabel_to_sid = flask_seclabel_to_sid, }; const struct xsm_ops *__init flask_init( -- 2.25.1