|
@@ -165,6 +165,27 @@ static bool access_sctlr(struct kvm_vcpu *vcpu,
|
|
return true;
|
|
return true;
|
|
}
|
|
}
|
|
|
|
|
|
|
|
+/*
|
|
|
|
+ * Trap handler for the GICv3 SGI generation system register.
|
|
|
|
+ * Forward the request to the VGIC emulation.
|
|
|
|
+ * The cp15_64 code makes sure this automatically works
|
|
|
|
+ * for both AArch64 and AArch32 accesses.
|
|
|
|
+ */
|
|
|
|
+static bool access_gic_sgi(struct kvm_vcpu *vcpu,
|
|
|
|
+ const struct sys_reg_params *p,
|
|
|
|
+ const struct sys_reg_desc *r)
|
|
|
|
+{
|
|
|
|
+ u64 val;
|
|
|
|
+
|
|
|
|
+ if (!p->is_write)
|
|
|
|
+ return read_from_write_only(vcpu, p);
|
|
|
|
+
|
|
|
|
+ val = *vcpu_reg(vcpu, p->Rt);
|
|
|
|
+ vgic_v3_dispatch_sgi(vcpu, val);
|
|
|
|
+
|
|
|
|
+ return true;
|
|
|
|
+}
|
|
|
|
+
|
|
static bool trap_raz_wi(struct kvm_vcpu *vcpu,
|
|
static bool trap_raz_wi(struct kvm_vcpu *vcpu,
|
|
const struct sys_reg_params *p,
|
|
const struct sys_reg_params *p,
|
|
const struct sys_reg_desc *r)
|
|
const struct sys_reg_desc *r)
|
|
@@ -434,6 +455,9 @@ static const struct sys_reg_desc sys_reg_descs[] = {
|
|
{ Op0(0b11), Op1(0b000), CRn(0b1100), CRm(0b0000), Op2(0b000),
|
|
{ Op0(0b11), Op1(0b000), CRn(0b1100), CRm(0b0000), Op2(0b000),
|
|
NULL, reset_val, VBAR_EL1, 0 },
|
|
NULL, reset_val, VBAR_EL1, 0 },
|
|
|
|
|
|
|
|
+ /* ICC_SGI1R_EL1 */
|
|
|
|
+ { Op0(0b11), Op1(0b000), CRn(0b1100), CRm(0b1011), Op2(0b101),
|
|
|
|
+ access_gic_sgi },
|
|
/* ICC_SRE_EL1 */
|
|
/* ICC_SRE_EL1 */
|
|
{ Op0(0b11), Op1(0b000), CRn(0b1100), CRm(0b1100), Op2(0b101),
|
|
{ Op0(0b11), Op1(0b000), CRn(0b1100), CRm(0b1100), Op2(0b101),
|
|
trap_raz_wi },
|
|
trap_raz_wi },
|
|
@@ -666,6 +690,8 @@ static const struct sys_reg_desc cp14_64_regs[] = {
|
|
* register).
|
|
* register).
|
|
*/
|
|
*/
|
|
static const struct sys_reg_desc cp15_regs[] = {
|
|
static const struct sys_reg_desc cp15_regs[] = {
|
|
|
|
+ { Op1( 0), CRn( 0), CRm(12), Op2( 0), access_gic_sgi },
|
|
|
|
+
|
|
{ Op1( 0), CRn( 1), CRm( 0), Op2( 0), access_sctlr, NULL, c1_SCTLR },
|
|
{ Op1( 0), CRn( 1), CRm( 0), Op2( 0), access_sctlr, NULL, c1_SCTLR },
|
|
{ Op1( 0), CRn( 2), CRm( 0), Op2( 0), access_vm_reg, NULL, c2_TTBR0 },
|
|
{ Op1( 0), CRn( 2), CRm( 0), Op2( 0), access_vm_reg, NULL, c2_TTBR0 },
|
|
{ Op1( 0), CRn( 2), CRm( 0), Op2( 1), access_vm_reg, NULL, c2_TTBR1 },
|
|
{ Op1( 0), CRn( 2), CRm( 0), Op2( 1), access_vm_reg, NULL, c2_TTBR1 },
|
|
@@ -713,6 +739,7 @@ static const struct sys_reg_desc cp15_regs[] = {
|
|
|
|
|
|
static const struct sys_reg_desc cp15_64_regs[] = {
|
|
static const struct sys_reg_desc cp15_64_regs[] = {
|
|
{ Op1( 0), CRn( 0), CRm( 2), Op2( 0), access_vm_reg, NULL, c2_TTBR0 },
|
|
{ Op1( 0), CRn( 0), CRm( 2), Op2( 0), access_vm_reg, NULL, c2_TTBR0 },
|
|
|
|
+ { Op1( 0), CRn( 0), CRm(12), Op2( 0), access_gic_sgi },
|
|
{ Op1( 1), CRn( 0), CRm( 2), Op2( 0), access_vm_reg, NULL, c2_TTBR1 },
|
|
{ Op1( 1), CRn( 0), CRm( 2), Op2( 0), access_vm_reg, NULL, c2_TTBR1 },
|
|
};
|
|
};
|
|
|
|
|