Skip to content

Commit

Permalink
arm: Move gic_handle_redist_access unmodified
Browse files Browse the repository at this point in the history
We will need it earlier in the module.

Signed-off-by: Jan Kiszka <jan.kiszka@siemens.com>
  • Loading branch information
jan-kiszka committed Aug 14, 2015
1 parent 2a4f65d commit 1cb54c0
Showing 1 changed file with 61 additions and 61 deletions.
122 changes: 61 additions & 61 deletions hypervisor/arch/arm/gic-v3.c
Expand Up @@ -213,6 +213,67 @@ static void gic_route_spis(struct cell *config_cell, struct cell *dest_cell)
}
}

static int gic_handle_redist_access(struct mmio_access *mmio)
{
struct cell *cell = this_cell();
unsigned int cpu;
unsigned int reg;
int ret = TRAP_UNHANDLED;
unsigned int virt_id;
void *virt_redist = 0;
void *phys_redist = 0;
unsigned int redist_size = (gic_version == 4) ? 0x40000 : 0x20000;
void *address = (void *)mmio->address;

/*
* The redistributor accessed by the cell is not the one stored in these
* cpu_datas, but the one associated to its virtual id. So we first
* need to translate the redistributor address.
*/
for_each_cpu(cpu, cell->cpu_set) {
virt_id = arm_cpu_phys2virt(cpu);
virt_redist = per_cpu(virt_id)->gicr_base;
if (address >= virt_redist && address < virt_redist
+ redist_size) {
phys_redist = per_cpu(cpu)->gicr_base;
break;
}
}

if (phys_redist == NULL)
return TRAP_FORBIDDEN;

reg = address - virt_redist;
mmio->address = (unsigned long)phys_redist + reg;

/* Change the ID register, all other accesses are allowed. */
if (!mmio->is_write) {
switch (reg) {
case GICR_TYPER:
if (virt_id == cell->arch.last_virt_id)
mmio->value = GICR_TYPER_Last;
else
mmio->value = 0;
/* AArch64 can use a writeq for this register */
if (mmio->size == 8)
mmio->value |= (u64)virt_id << 32;

ret = TRAP_HANDLED;
break;
case GICR_TYPER + 4:
/* Upper bits contain the affinity */
mmio->value = virt_id;
ret = TRAP_HANDLED;
break;
}
}
if (ret == TRAP_HANDLED)
return ret;

arm_mmio_perform_access(mmio);
return TRAP_HANDLED;
}

static int gic_cell_init(struct cell *cell)
{
gic_route_spis(cell, cell);
Expand Down Expand Up @@ -339,67 +400,6 @@ static int gic_inject_irq(struct per_cpu *cpu_data, struct pending_irq *irq)
return 0;
}

static int gic_handle_redist_access(struct mmio_access *mmio)
{
struct cell *cell = this_cell();
unsigned int cpu;
unsigned int reg;
int ret = TRAP_UNHANDLED;
unsigned int virt_id;
void *virt_redist = 0;
void *phys_redist = 0;
unsigned int redist_size = (gic_version == 4) ? 0x40000 : 0x20000;
void *address = (void *)mmio->address;

/*
* The redistributor accessed by the cell is not the one stored in these
* cpu_datas, but the one associated to its virtual id. So we first
* need to translate the redistributor address.
*/
for_each_cpu(cpu, cell->cpu_set) {
virt_id = arm_cpu_phys2virt(cpu);
virt_redist = per_cpu(virt_id)->gicr_base;
if (address >= virt_redist && address < virt_redist
+ redist_size) {
phys_redist = per_cpu(cpu)->gicr_base;
break;
}
}

if (phys_redist == NULL)
return TRAP_FORBIDDEN;

reg = address - virt_redist;
mmio->address = (unsigned long)phys_redist + reg;

/* Change the ID register, all other accesses are allowed. */
if (!mmio->is_write) {
switch (reg) {
case GICR_TYPER:
if (virt_id == cell->arch.last_virt_id)
mmio->value = GICR_TYPER_Last;
else
mmio->value = 0;
/* AArch64 can use a writeq for this register */
if (mmio->size == 8)
mmio->value |= (u64)virt_id << 32;

ret = TRAP_HANDLED;
break;
case GICR_TYPER + 4:
/* Upper bits contain the affinity */
mmio->value = virt_id;
ret = TRAP_HANDLED;
break;
}
}
if (ret == TRAP_HANDLED)
return ret;

arm_mmio_perform_access(mmio);
return TRAP_HANDLED;
}

static int gic_mmio_access(struct mmio_access *mmio)
{
void *address = (void *)mmio->address;
Expand Down

0 comments on commit 1cb54c0

Please sign in to comment.