xen/arm: Add way to disable traps on accesses to unmapped addresses

Add a per-domain way to optionally disable traps for accesses
to unmapped addresses.

The domain flag is general but it's only implemented for Arm for now.

Signed-off-by: Edgar E. Iglesias <edgar.iglesias@amd.com>
Reviewed-by: Stefano Stabellini <sstabellini@kernel.org>
This commit is contained in:
Edgar E. Iglesias authored and Stefano Stabellini committed 2025-06-17 10:59:04 -07:00
1 parent 14c57887f3
commit 980aff4e8f
8 files changed
+57 -6

No files matched your search

+3
View File
@@ -233,6 +233,9 @@ int libxl__arch_domain_prepare_config(libxl__gc *gc,
config->arch.sve_vl = d_config->b_info.arch_arm.sve_vl / 128U;
}
/* Trap accesses to unmapped areas. */
config->flags |= XEN_DOMCTL_CDF_trap_unmapped_accesses;
return 0;
}
+3
View File
@@ -343,6 +343,9 @@ void __init arch_create_domUs(struct dt_device_node *node,
panic("'sve' property found, but CONFIG_ARM64_SVE not selected\n");
#endif
}
/* Trap accesses to unmapped areas. */
d_cfg->flags |= XEN_DOMCTL_CDF_trap_unmapped_accesses;
}
int __init init_intc_phandle(struct kernel_info *kinfo, const char *name,
+2 -1
View File
@@ -612,7 +612,8 @@ int arch_sanitise_domain_config(struct xen_domctl_createdomain *config)
unsigned int max_vcpus;
unsigned int flags_required = (XEN_DOMCTL_CDF_hvm | XEN_DOMCTL_CDF_hap);
unsigned int flags_optional = (XEN_DOMCTL_CDF_iommu | XEN_DOMCTL_CDF_vpmu |
XEN_DOMCTL_CDF_xs_domain );
XEN_DOMCTL_CDF_xs_domain |
XEN_DOMCTL_CDF_trap_unmapped_accesses );
unsigned int sve_vl_bits = sve_decode_vl(config->arch.sve_vl);
if ( (config->flags & ~flags_optional) != flags_required )
+2 -1
View File
@@ -1971,7 +1971,8 @@ void __init create_dom0(void)
{
struct domain *dom0;
struct xen_domctl_createdomain dom0_cfg = {
.flags = XEN_DOMCTL_CDF_hvm | XEN_DOMCTL_CDF_hap,
.flags = XEN_DOMCTL_CDF_hvm | XEN_DOMCTL_CDF_hap |
XEN_DOMCTL_CDF_trap_unmapped_accesses,
.max_evtchn_port = -1,
.max_grant_frames = gnttab_dom0_frames(),
.max_maptrack_frames = -1,
+35 -2
View File
@@ -21,6 +21,32 @@
#include "decode.h"
/* Handler for unmapped ranges. Writes ignored, reads return all ones. */
static int unmapped_read(struct vcpu *v, mmio_info_t *info, register_t *r,
void *priv)
{
uint64_t mask = GENMASK((1U << info->dabt.size) * 8 - 1, 0);
/* Mask off upper bits. */
*r = UINT64_MAX & mask;
return 1;
}
static int unmapped_write(struct vcpu *v, mmio_info_t *info, register_t r,
void *priv)
{
return 1;
}
static const struct mmio_handler_ops unmapped_ops = {
.read = unmapped_read,
.write = unmapped_write
};
static const struct mmio_handler unmapped_handler = {
.ops = &unmapped_ops
};
static enum io_state handle_read(const struct mmio_handler *handler,
struct vcpu *v,
mmio_info_t *info)
@@ -175,11 +201,18 @@ enum io_state try_handle_mmio(struct cpu_user_regs *regs,
handler = find_mmio_handler(v->domain, info->gpa);
if ( !handler )
{
bool trap_unmapped = v->domain->options &
XEN_DOMCTL_CDF_trap_unmapped_accesses;
rc = try_fwd_ioserv(regs, v, info);
if ( rc == IO_HANDLED )
return handle_ioserv(regs, v);
return rc;
else if ( rc == IO_UNHANDLED && !trap_unmapped )
{
/* Fallback to the unmapped handler. */
handler = &unmapped_handler;
} else {
return rc;
}
}
/*
+7
View File
@@ -713,6 +713,13 @@ int arch_sanitise_domain_config(struct xen_domctl_createdomain *config)
}
}
if ( config->flags & XEN_DOMCTL_CDF_trap_unmapped_accesses )
{
dprintk(XENLOG_INFO, "Unsupported trap_unmapped_accesses flag %#x\n",
config->flags);
return -EINVAL;
}
if ( config->arch.misc_flags & ~XEN_X86_MSR_RELAXED )
{
dprintk(XENLOG_INFO, "Invalid arch misc flags %#x\n",
+2 -1
View File
@@ -721,7 +721,8 @@ static int sanitise_domain_config(struct xen_domctl_createdomain *config)
~(XEN_DOMCTL_CDF_hvm | XEN_DOMCTL_CDF_hap |
XEN_DOMCTL_CDF_s3_integrity | XEN_DOMCTL_CDF_oos_off |
XEN_DOMCTL_CDF_xs_domain | XEN_DOMCTL_CDF_iommu |
XEN_DOMCTL_CDF_nested_virt | XEN_DOMCTL_CDF_vpmu) )
XEN_DOMCTL_CDF_nested_virt | XEN_DOMCTL_CDF_vpmu |
XEN_DOMCTL_CDF_trap_unmapped_accesses) )
{
dprintk(XENLOG_INFO, "Unknown CDF flags %#x\n", config->flags);
return -EINVAL;
+3 -1
View File
@@ -66,9 +66,11 @@ struct xen_domctl_createdomain {
#define XEN_DOMCTL_CDF_nested_virt (1U << _XEN_DOMCTL_CDF_nested_virt)
/* Should we expose the vPMU to the guest? */
#define XEN_DOMCTL_CDF_vpmu (1U << 7)
/* Should we trap guest accesses to unmapped addresses? */
#define XEN_DOMCTL_CDF_trap_unmapped_accesses (1U << 8)
/* Max XEN_DOMCTL_CDF_* constant. Used for ABI checking. */
#define XEN_DOMCTL_CDF_MAX XEN_DOMCTL_CDF_vpmu
#define XEN_DOMCTL_CDF_MAX XEN_DOMCTL_CDF_trap_unmapped_accesses
uint32_t flags;
Reference in new issue
Block a user
Blocking a user prevents them from interacting with repositories, such as opening or commenting on pull requests or issues. Learn more about blocking a user.