mirror of
https://github.com/xen-project/xen.git
synced 2026-10-29 10:40:03 +01:00
xen/arm: io: Extend write/read handler to pass private data
Some handlers may require to use private data in order to get quickly information related to the region emulated. Signed-off-by: Julien Grall <julien.grall@citrix.com> Acked-by: Ian Campbell <ian.campbell@citrix.com>
This commit is contained in:
1 parent
c1be0b102e
commit
ea7d70ef27
5 files changed
+39
-25
No files matched your search
+13
-8
@@ -27,7 +27,7 @@ int handle_mmio(mmio_info_t *info)
|
||||
{
|
||||
struct vcpu *v = current;
|
||||
int i;
|
||||
const struct mmio_handler *mmio_handler;
|
||||
const struct mmio_handler *mmio_handler = NULL;
|
||||
const struct io_handler *io_handlers = &v->domain->arch.io_handlers;
|
||||
|
||||
for ( i = 0; i < io_handlers->num_entries; i++ )
|
||||
@@ -36,19 +36,23 @@ int handle_mmio(mmio_info_t *info)
|
||||
|
||||
if ( (info->gpa >= mmio_handler->addr) &&
|
||||
(info->gpa < (mmio_handler->addr + mmio_handler->size)) )
|
||||
{
|
||||
return info->dabt.write ?
|
||||
mmio_handler->mmio_handler_ops->write_handler(v, info) :
|
||||
mmio_handler->mmio_handler_ops->read_handler(v, info);
|
||||
}
|
||||
break;
|
||||
}
|
||||
|
||||
return 0;
|
||||
if ( i == io_handlers->num_entries )
|
||||
return 0;
|
||||
|
||||
if ( info->dabt.write )
|
||||
return mmio_handler->mmio_handler_ops->write_handler(v, info,
|
||||
mmio_handler->priv);
|
||||
else
|
||||
return mmio_handler->mmio_handler_ops->read_handler(v, info,
|
||||
mmio_handler->priv);
|
||||
}
|
||||
|
||||
void register_mmio_handler(struct domain *d,
|
||||
const struct mmio_handler_ops *handle,
|
||||
paddr_t addr, paddr_t size)
|
||||
paddr_t addr, paddr_t size, void *priv)
|
||||
{
|
||||
struct io_handler *handler = &d->arch.io_handlers;
|
||||
|
||||
@@ -59,6 +63,7 @@ void register_mmio_handler(struct domain *d,
|
||||
handler->mmio_handlers[handler->num_entries].mmio_handler_ops = handle;
|
||||
handler->mmio_handlers[handler->num_entries].addr = addr;
|
||||
handler->mmio_handlers[handler->num_entries].size = size;
|
||||
handler->mmio_handlers[handler->num_entries].priv = priv;
|
||||
dsb(ish);
|
||||
handler->num_entries++;
|
||||
|
||||
|
||||
@@ -50,7 +50,8 @@ void vgic_v2_setup_hw(paddr_t dbase, paddr_t cbase, paddr_t vbase)
|
||||
vgic_v2_hw.vbase = vbase;
|
||||
}
|
||||
|
||||
static int vgic_v2_distr_mmio_read(struct vcpu *v, mmio_info_t *info)
|
||||
static int vgic_v2_distr_mmio_read(struct vcpu *v, mmio_info_t *info,
|
||||
void *priv)
|
||||
{
|
||||
struct hsr_dabt dabt = info->dabt;
|
||||
struct cpu_user_regs *regs = guest_cpu_user_regs();
|
||||
@@ -247,7 +248,8 @@ static int vgic_v2_to_sgi(struct vcpu *v, register_t sgir)
|
||||
return vgic_to_sgi(v, sgir, sgi_mode, virq, &target);
|
||||
}
|
||||
|
||||
static int vgic_v2_distr_mmio_write(struct vcpu *v, mmio_info_t *info)
|
||||
static int vgic_v2_distr_mmio_write(struct vcpu *v, mmio_info_t *info,
|
||||
void *priv)
|
||||
{
|
||||
struct hsr_dabt dabt = info->dabt;
|
||||
struct cpu_user_regs *regs = guest_cpu_user_regs();
|
||||
@@ -590,7 +592,7 @@ static int vgic_v2_domain_init(struct domain *d)
|
||||
sizeof(d->arch.vgic.shared_irqs[i].v2.itargets));
|
||||
|
||||
register_mmio_handler(d, &vgic_v2_distr_mmio_handler, d->arch.vgic.dbase,
|
||||
PAGE_SIZE);
|
||||
PAGE_SIZE, NULL);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
+11
-6
@@ -634,7 +634,8 @@ static inline struct vcpu *get_vcpu_from_rdist(paddr_t gpa,
|
||||
return d->vcpu[vcpu_id];
|
||||
}
|
||||
|
||||
static int vgic_v3_rdistr_mmio_read(struct vcpu *v, mmio_info_t *info)
|
||||
static int vgic_v3_rdistr_mmio_read(struct vcpu *v, mmio_info_t *info,
|
||||
void *priv)
|
||||
{
|
||||
uint32_t offset;
|
||||
|
||||
@@ -656,7 +657,8 @@ static int vgic_v3_rdistr_mmio_read(struct vcpu *v, mmio_info_t *info)
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int vgic_v3_rdistr_mmio_write(struct vcpu *v, mmio_info_t *info)
|
||||
static int vgic_v3_rdistr_mmio_write(struct vcpu *v, mmio_info_t *info,
|
||||
void *priv)
|
||||
{
|
||||
uint32_t offset;
|
||||
|
||||
@@ -678,7 +680,8 @@ static int vgic_v3_rdistr_mmio_write(struct vcpu *v, mmio_info_t *info)
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int vgic_v3_distr_mmio_read(struct vcpu *v, mmio_info_t *info)
|
||||
static int vgic_v3_distr_mmio_read(struct vcpu *v, mmio_info_t *info,
|
||||
void *priv)
|
||||
{
|
||||
struct hsr_dabt dabt = info->dabt;
|
||||
struct cpu_user_regs *regs = guest_cpu_user_regs();
|
||||
@@ -835,7 +838,8 @@ read_as_zero:
|
||||
return 1;
|
||||
}
|
||||
|
||||
static int vgic_v3_distr_mmio_write(struct vcpu *v, mmio_info_t *info)
|
||||
static int vgic_v3_distr_mmio_write(struct vcpu *v, mmio_info_t *info,
|
||||
void *priv)
|
||||
{
|
||||
struct hsr_dabt dabt = info->dabt;
|
||||
struct cpu_user_regs *regs = guest_cpu_user_regs();
|
||||
@@ -1200,7 +1204,7 @@ static int vgic_v3_domain_init(struct domain *d)
|
||||
|
||||
/* Register mmio handle for the Distributor */
|
||||
register_mmio_handler(d, &vgic_distr_mmio_handler, d->arch.vgic.dbase,
|
||||
SZ_64K);
|
||||
SZ_64K, NULL);
|
||||
|
||||
/*
|
||||
* Register mmio handler per contiguous region occupied by the
|
||||
@@ -1210,7 +1214,8 @@ static int vgic_v3_domain_init(struct domain *d)
|
||||
for ( i = 0; i < d->arch.vgic.nr_regions; i++ )
|
||||
register_mmio_handler(d, &vgic_rdistr_mmio_handler,
|
||||
d->arch.vgic.rdist_regions[i].base,
|
||||
d->arch.vgic.rdist_regions[i].size);
|
||||
d->arch.vgic.rdist_regions[i].size,
|
||||
NULL);
|
||||
|
||||
d->arch.vgic.ctlr = VGICD_CTLR_DEFAULT;
|
||||
|
||||
|
||||
@@ -45,8 +45,8 @@
|
||||
|
||||
#define domain_has_vuart(d) ((d)->arch.vuart.info != NULL)
|
||||
|
||||
static int vuart_mmio_read(struct vcpu *v, mmio_info_t *info);
|
||||
static int vuart_mmio_write(struct vcpu *v, mmio_info_t *info);
|
||||
static int vuart_mmio_read(struct vcpu *v, mmio_info_t *info, void *priv);
|
||||
static int vuart_mmio_write(struct vcpu *v, mmio_info_t *info, void *priv);
|
||||
|
||||
static const struct mmio_handler_ops vuart_mmio_handler = {
|
||||
.read_handler = vuart_mmio_read,
|
||||
@@ -70,7 +70,8 @@ int domain_vuart_init(struct domain *d)
|
||||
|
||||
register_mmio_handler(d, &vuart_mmio_handler,
|
||||
d->arch.vuart.info->base_addr,
|
||||
d->arch.vuart.info->size);
|
||||
d->arch.vuart.info->size,
|
||||
NULL);
|
||||
|
||||
return 0;
|
||||
}
|
||||
@@ -105,7 +106,7 @@ static void vuart_print_char(struct vcpu *v, char c)
|
||||
spin_unlock(&uart->lock);
|
||||
}
|
||||
|
||||
static int vuart_mmio_read(struct vcpu *v, mmio_info_t *info)
|
||||
static int vuart_mmio_read(struct vcpu *v, mmio_info_t *info, void *priv)
|
||||
{
|
||||
struct domain *d = v->domain;
|
||||
struct hsr_dabt dabt = info->dabt;
|
||||
@@ -125,7 +126,7 @@ static int vuart_mmio_read(struct vcpu *v, mmio_info_t *info)
|
||||
return 1;
|
||||
}
|
||||
|
||||
static int vuart_mmio_write(struct vcpu *v, mmio_info_t *info)
|
||||
static int vuart_mmio_write(struct vcpu *v, mmio_info_t *info, void *priv)
|
||||
{
|
||||
struct domain *d = v->domain;
|
||||
struct hsr_dabt dabt = info->dabt;
|
||||
|
||||
@@ -32,8 +32,8 @@ typedef struct
|
||||
paddr_t gpa;
|
||||
} mmio_info_t;
|
||||
|
||||
typedef int (*mmio_read_t)(struct vcpu *v, mmio_info_t *info);
|
||||
typedef int (*mmio_write_t)(struct vcpu *v, mmio_info_t *info);
|
||||
typedef int (*mmio_read_t)(struct vcpu *v, mmio_info_t *info, void *priv);
|
||||
typedef int (*mmio_write_t)(struct vcpu *v, mmio_info_t *info, void *priv);
|
||||
typedef int (*mmio_check_t)(struct vcpu *v, paddr_t addr);
|
||||
|
||||
struct mmio_handler_ops {
|
||||
@@ -45,6 +45,7 @@ struct mmio_handler {
|
||||
paddr_t addr;
|
||||
paddr_t size;
|
||||
const struct mmio_handler_ops *mmio_handler_ops;
|
||||
void *priv;
|
||||
};
|
||||
|
||||
struct io_handler {
|
||||
@@ -56,7 +57,7 @@ struct io_handler {
|
||||
extern int handle_mmio(mmio_info_t *info);
|
||||
void register_mmio_handler(struct domain *d,
|
||||
const struct mmio_handler_ops *handle,
|
||||
paddr_t addr, paddr_t size);
|
||||
paddr_t addr, paddr_t size, void *priv);
|
||||
int domain_io_init(struct domain *d);
|
||||
|
||||
#endif /* __ASM_ARM_MMIO_H__ */
|
||||
|
||||