mirror of
https://github.com/Motorhead1991/qemu.git
synced 2025-08-25 19:13:26 -06:00
target/arm: Move TLBI range insns
Move the TLBI invalidate-range insns across to tlb-insns.c. Signed-off-by: Peter Maydell <peter.maydell@linaro.org> Reviewed-by: Richard Henderson <richard.henderson@linaro.org> Message-id: 20241210160452.2427965-7-peter.maydell@linaro.org
This commit is contained in:
parent
5991e5abe3
commit
6559379957
3 changed files with 333 additions and 328 deletions
|
@ -1142,6 +1142,8 @@ CPAccessResult access_ttlb(CPUARMState *env, const ARMCPRegInfo *ri,
|
||||||
bool isread);
|
bool isread);
|
||||||
CPAccessResult access_ttlbis(CPUARMState *env, const ARMCPRegInfo *ri,
|
CPAccessResult access_ttlbis(CPUARMState *env, const ARMCPRegInfo *ri,
|
||||||
bool isread);
|
bool isread);
|
||||||
|
CPAccessResult access_ttlbos(CPUARMState *env, const ARMCPRegInfo *ri,
|
||||||
|
bool isread);
|
||||||
bool tlb_force_broadcast(CPUARMState *env);
|
bool tlb_force_broadcast(CPUARMState *env);
|
||||||
int tlbbits_for_regime(CPUARMState *env, ARMMMUIdx mmu_idx,
|
int tlbbits_for_regime(CPUARMState *env, ARMMMUIdx mmu_idx,
|
||||||
uint64_t addr);
|
uint64_t addr);
|
||||||
|
|
|
@ -388,8 +388,8 @@ CPAccessResult access_ttlbis(CPUARMState *env, const ARMCPRegInfo *ri,
|
||||||
|
|
||||||
#ifdef TARGET_AARCH64
|
#ifdef TARGET_AARCH64
|
||||||
/* Check for traps from EL1 due to HCR_EL2.TTLB or TTLBOS. */
|
/* Check for traps from EL1 due to HCR_EL2.TTLB or TTLBOS. */
|
||||||
static CPAccessResult access_ttlbos(CPUARMState *env, const ARMCPRegInfo *ri,
|
CPAccessResult access_ttlbos(CPUARMState *env, const ARMCPRegInfo *ri,
|
||||||
bool isread)
|
bool isread)
|
||||||
{
|
{
|
||||||
if (arm_current_el(env) == 1 &&
|
if (arm_current_el(env) == 1 &&
|
||||||
(arm_hcr_el2_eff(env) & (HCR_TTLB | HCR_TTLBOS))) {
|
(arm_hcr_el2_eff(env) & (HCR_TTLB | HCR_TTLBOS))) {
|
||||||
|
@ -4856,202 +4856,6 @@ int ipas2e1_tlbmask(CPUARMState *env, int64_t value)
|
||||||
: ARMMMUIdxBit_Stage2);
|
: ARMMMUIdxBit_Stage2);
|
||||||
}
|
}
|
||||||
|
|
||||||
#ifdef TARGET_AARCH64
|
|
||||||
typedef struct {
|
|
||||||
uint64_t base;
|
|
||||||
uint64_t length;
|
|
||||||
} TLBIRange;
|
|
||||||
|
|
||||||
static ARMGranuleSize tlbi_range_tg_to_gran_size(int tg)
|
|
||||||
{
|
|
||||||
/*
|
|
||||||
* Note that the TLBI range TG field encoding differs from both
|
|
||||||
* TG0 and TG1 encodings.
|
|
||||||
*/
|
|
||||||
switch (tg) {
|
|
||||||
case 1:
|
|
||||||
return Gran4K;
|
|
||||||
case 2:
|
|
||||||
return Gran16K;
|
|
||||||
case 3:
|
|
||||||
return Gran64K;
|
|
||||||
default:
|
|
||||||
return GranInvalid;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
static TLBIRange tlbi_aa64_get_range(CPUARMState *env, ARMMMUIdx mmuidx,
|
|
||||||
uint64_t value)
|
|
||||||
{
|
|
||||||
unsigned int page_size_granule, page_shift, num, scale, exponent;
|
|
||||||
/* Extract one bit to represent the va selector in use. */
|
|
||||||
uint64_t select = sextract64(value, 36, 1);
|
|
||||||
ARMVAParameters param = aa64_va_parameters(env, select, mmuidx, true, false);
|
|
||||||
TLBIRange ret = { };
|
|
||||||
ARMGranuleSize gran;
|
|
||||||
|
|
||||||
page_size_granule = extract64(value, 46, 2);
|
|
||||||
gran = tlbi_range_tg_to_gran_size(page_size_granule);
|
|
||||||
|
|
||||||
/* The granule encoded in value must match the granule in use. */
|
|
||||||
if (gran != param.gran) {
|
|
||||||
qemu_log_mask(LOG_GUEST_ERROR, "Invalid tlbi page size granule %d\n",
|
|
||||||
page_size_granule);
|
|
||||||
return ret;
|
|
||||||
}
|
|
||||||
|
|
||||||
page_shift = arm_granule_bits(gran);
|
|
||||||
num = extract64(value, 39, 5);
|
|
||||||
scale = extract64(value, 44, 2);
|
|
||||||
exponent = (5 * scale) + 1;
|
|
||||||
|
|
||||||
ret.length = (num + 1) << (exponent + page_shift);
|
|
||||||
|
|
||||||
if (param.select) {
|
|
||||||
ret.base = sextract64(value, 0, 37);
|
|
||||||
} else {
|
|
||||||
ret.base = extract64(value, 0, 37);
|
|
||||||
}
|
|
||||||
if (param.ds) {
|
|
||||||
/*
|
|
||||||
* With DS=1, BaseADDR is always shifted 16 so that it is able
|
|
||||||
* to address all 52 va bits. The input address is perforce
|
|
||||||
* aligned on a 64k boundary regardless of translation granule.
|
|
||||||
*/
|
|
||||||
page_shift = 16;
|
|
||||||
}
|
|
||||||
ret.base <<= page_shift;
|
|
||||||
|
|
||||||
return ret;
|
|
||||||
}
|
|
||||||
|
|
||||||
static void do_rvae_write(CPUARMState *env, uint64_t value,
|
|
||||||
int idxmap, bool synced)
|
|
||||||
{
|
|
||||||
ARMMMUIdx one_idx = ARM_MMU_IDX_A | ctz32(idxmap);
|
|
||||||
TLBIRange range;
|
|
||||||
int bits;
|
|
||||||
|
|
||||||
range = tlbi_aa64_get_range(env, one_idx, value);
|
|
||||||
bits = tlbbits_for_regime(env, one_idx, range.base);
|
|
||||||
|
|
||||||
if (synced) {
|
|
||||||
tlb_flush_range_by_mmuidx_all_cpus_synced(env_cpu(env),
|
|
||||||
range.base,
|
|
||||||
range.length,
|
|
||||||
idxmap,
|
|
||||||
bits);
|
|
||||||
} else {
|
|
||||||
tlb_flush_range_by_mmuidx(env_cpu(env), range.base,
|
|
||||||
range.length, idxmap, bits);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
static void tlbi_aa64_rvae1_write(CPUARMState *env,
|
|
||||||
const ARMCPRegInfo *ri,
|
|
||||||
uint64_t value)
|
|
||||||
{
|
|
||||||
/*
|
|
||||||
* Invalidate by VA range, EL1&0.
|
|
||||||
* Currently handles all of RVAE1, RVAAE1, RVAALE1 and RVALE1,
|
|
||||||
* since we don't support flush-for-specific-ASID-only or
|
|
||||||
* flush-last-level-only.
|
|
||||||
*/
|
|
||||||
|
|
||||||
do_rvae_write(env, value, vae1_tlbmask(env),
|
|
||||||
tlb_force_broadcast(env));
|
|
||||||
}
|
|
||||||
|
|
||||||
static void tlbi_aa64_rvae1is_write(CPUARMState *env,
|
|
||||||
const ARMCPRegInfo *ri,
|
|
||||||
uint64_t value)
|
|
||||||
{
|
|
||||||
/*
|
|
||||||
* Invalidate by VA range, Inner/Outer Shareable EL1&0.
|
|
||||||
* Currently handles all of RVAE1IS, RVAE1OS, RVAAE1IS, RVAAE1OS,
|
|
||||||
* RVAALE1IS, RVAALE1OS, RVALE1IS and RVALE1OS, since we don't support
|
|
||||||
* flush-for-specific-ASID-only, flush-last-level-only or inner/outer
|
|
||||||
* shareable specific flushes.
|
|
||||||
*/
|
|
||||||
|
|
||||||
do_rvae_write(env, value, vae1_tlbmask(env), true);
|
|
||||||
}
|
|
||||||
|
|
||||||
static void tlbi_aa64_rvae2_write(CPUARMState *env,
|
|
||||||
const ARMCPRegInfo *ri,
|
|
||||||
uint64_t value)
|
|
||||||
{
|
|
||||||
/*
|
|
||||||
* Invalidate by VA range, EL2.
|
|
||||||
* Currently handles all of RVAE2 and RVALE2,
|
|
||||||
* since we don't support flush-for-specific-ASID-only or
|
|
||||||
* flush-last-level-only.
|
|
||||||
*/
|
|
||||||
|
|
||||||
do_rvae_write(env, value, vae2_tlbmask(env),
|
|
||||||
tlb_force_broadcast(env));
|
|
||||||
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
static void tlbi_aa64_rvae2is_write(CPUARMState *env,
|
|
||||||
const ARMCPRegInfo *ri,
|
|
||||||
uint64_t value)
|
|
||||||
{
|
|
||||||
/*
|
|
||||||
* Invalidate by VA range, Inner/Outer Shareable, EL2.
|
|
||||||
* Currently handles all of RVAE2IS, RVAE2OS, RVALE2IS and RVALE2OS,
|
|
||||||
* since we don't support flush-for-specific-ASID-only,
|
|
||||||
* flush-last-level-only or inner/outer shareable specific flushes.
|
|
||||||
*/
|
|
||||||
|
|
||||||
do_rvae_write(env, value, vae2_tlbmask(env), true);
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
static void tlbi_aa64_rvae3_write(CPUARMState *env,
|
|
||||||
const ARMCPRegInfo *ri,
|
|
||||||
uint64_t value)
|
|
||||||
{
|
|
||||||
/*
|
|
||||||
* Invalidate by VA range, EL3.
|
|
||||||
* Currently handles all of RVAE3 and RVALE3,
|
|
||||||
* since we don't support flush-for-specific-ASID-only or
|
|
||||||
* flush-last-level-only.
|
|
||||||
*/
|
|
||||||
|
|
||||||
do_rvae_write(env, value, ARMMMUIdxBit_E3, tlb_force_broadcast(env));
|
|
||||||
}
|
|
||||||
|
|
||||||
static void tlbi_aa64_rvae3is_write(CPUARMState *env,
|
|
||||||
const ARMCPRegInfo *ri,
|
|
||||||
uint64_t value)
|
|
||||||
{
|
|
||||||
/*
|
|
||||||
* Invalidate by VA range, EL3, Inner/Outer Shareable.
|
|
||||||
* Currently handles all of RVAE3IS, RVAE3OS, RVALE3IS and RVALE3OS,
|
|
||||||
* since we don't support flush-for-specific-ASID-only,
|
|
||||||
* flush-last-level-only or inner/outer specific flushes.
|
|
||||||
*/
|
|
||||||
|
|
||||||
do_rvae_write(env, value, ARMMMUIdxBit_E3, true);
|
|
||||||
}
|
|
||||||
|
|
||||||
static void tlbi_aa64_ripas2e1_write(CPUARMState *env, const ARMCPRegInfo *ri,
|
|
||||||
uint64_t value)
|
|
||||||
{
|
|
||||||
do_rvae_write(env, value, ipas2e1_tlbmask(env, value),
|
|
||||||
tlb_force_broadcast(env));
|
|
||||||
}
|
|
||||||
|
|
||||||
static void tlbi_aa64_ripas2e1is_write(CPUARMState *env,
|
|
||||||
const ARMCPRegInfo *ri,
|
|
||||||
uint64_t value)
|
|
||||||
{
|
|
||||||
do_rvae_write(env, value, ipas2e1_tlbmask(env, value), true);
|
|
||||||
}
|
|
||||||
#endif
|
|
||||||
|
|
||||||
static CPAccessResult aa64_zva_access(CPUARMState *env, const ARMCPRegInfo *ri,
|
static CPAccessResult aa64_zva_access(CPUARMState *env, const ARMCPRegInfo *ri,
|
||||||
bool isread)
|
bool isread)
|
||||||
{
|
{
|
||||||
|
@ -7312,133 +7116,6 @@ static const ARMCPRegInfo pauth_reginfo[] = {
|
||||||
.fieldoffset = offsetof(CPUARMState, keys.apib.hi) },
|
.fieldoffset = offsetof(CPUARMState, keys.apib.hi) },
|
||||||
};
|
};
|
||||||
|
|
||||||
static const ARMCPRegInfo tlbirange_reginfo[] = {
|
|
||||||
{ .name = "TLBI_RVAE1IS", .state = ARM_CP_STATE_AA64,
|
|
||||||
.opc0 = 1, .opc1 = 0, .crn = 8, .crm = 2, .opc2 = 1,
|
|
||||||
.access = PL1_W, .accessfn = access_ttlbis, .type = ARM_CP_NO_RAW,
|
|
||||||
.fgt = FGT_TLBIRVAE1IS,
|
|
||||||
.writefn = tlbi_aa64_rvae1is_write },
|
|
||||||
{ .name = "TLBI_RVAAE1IS", .state = ARM_CP_STATE_AA64,
|
|
||||||
.opc0 = 1, .opc1 = 0, .crn = 8, .crm = 2, .opc2 = 3,
|
|
||||||
.access = PL1_W, .accessfn = access_ttlbis, .type = ARM_CP_NO_RAW,
|
|
||||||
.fgt = FGT_TLBIRVAAE1IS,
|
|
||||||
.writefn = tlbi_aa64_rvae1is_write },
|
|
||||||
{ .name = "TLBI_RVALE1IS", .state = ARM_CP_STATE_AA64,
|
|
||||||
.opc0 = 1, .opc1 = 0, .crn = 8, .crm = 2, .opc2 = 5,
|
|
||||||
.access = PL1_W, .accessfn = access_ttlbis, .type = ARM_CP_NO_RAW,
|
|
||||||
.fgt = FGT_TLBIRVALE1IS,
|
|
||||||
.writefn = tlbi_aa64_rvae1is_write },
|
|
||||||
{ .name = "TLBI_RVAALE1IS", .state = ARM_CP_STATE_AA64,
|
|
||||||
.opc0 = 1, .opc1 = 0, .crn = 8, .crm = 2, .opc2 = 7,
|
|
||||||
.access = PL1_W, .accessfn = access_ttlbis, .type = ARM_CP_NO_RAW,
|
|
||||||
.fgt = FGT_TLBIRVAALE1IS,
|
|
||||||
.writefn = tlbi_aa64_rvae1is_write },
|
|
||||||
{ .name = "TLBI_RVAE1OS", .state = ARM_CP_STATE_AA64,
|
|
||||||
.opc0 = 1, .opc1 = 0, .crn = 8, .crm = 5, .opc2 = 1,
|
|
||||||
.access = PL1_W, .accessfn = access_ttlbos, .type = ARM_CP_NO_RAW,
|
|
||||||
.fgt = FGT_TLBIRVAE1OS,
|
|
||||||
.writefn = tlbi_aa64_rvae1is_write },
|
|
||||||
{ .name = "TLBI_RVAAE1OS", .state = ARM_CP_STATE_AA64,
|
|
||||||
.opc0 = 1, .opc1 = 0, .crn = 8, .crm = 5, .opc2 = 3,
|
|
||||||
.access = PL1_W, .accessfn = access_ttlbos, .type = ARM_CP_NO_RAW,
|
|
||||||
.fgt = FGT_TLBIRVAAE1OS,
|
|
||||||
.writefn = tlbi_aa64_rvae1is_write },
|
|
||||||
{ .name = "TLBI_RVALE1OS", .state = ARM_CP_STATE_AA64,
|
|
||||||
.opc0 = 1, .opc1 = 0, .crn = 8, .crm = 5, .opc2 = 5,
|
|
||||||
.access = PL1_W, .accessfn = access_ttlbos, .type = ARM_CP_NO_RAW,
|
|
||||||
.fgt = FGT_TLBIRVALE1OS,
|
|
||||||
.writefn = tlbi_aa64_rvae1is_write },
|
|
||||||
{ .name = "TLBI_RVAALE1OS", .state = ARM_CP_STATE_AA64,
|
|
||||||
.opc0 = 1, .opc1 = 0, .crn = 8, .crm = 5, .opc2 = 7,
|
|
||||||
.access = PL1_W, .accessfn = access_ttlbos, .type = ARM_CP_NO_RAW,
|
|
||||||
.fgt = FGT_TLBIRVAALE1OS,
|
|
||||||
.writefn = tlbi_aa64_rvae1is_write },
|
|
||||||
{ .name = "TLBI_RVAE1", .state = ARM_CP_STATE_AA64,
|
|
||||||
.opc0 = 1, .opc1 = 0, .crn = 8, .crm = 6, .opc2 = 1,
|
|
||||||
.access = PL1_W, .accessfn = access_ttlb, .type = ARM_CP_NO_RAW,
|
|
||||||
.fgt = FGT_TLBIRVAE1,
|
|
||||||
.writefn = tlbi_aa64_rvae1_write },
|
|
||||||
{ .name = "TLBI_RVAAE1", .state = ARM_CP_STATE_AA64,
|
|
||||||
.opc0 = 1, .opc1 = 0, .crn = 8, .crm = 6, .opc2 = 3,
|
|
||||||
.access = PL1_W, .accessfn = access_ttlb, .type = ARM_CP_NO_RAW,
|
|
||||||
.fgt = FGT_TLBIRVAAE1,
|
|
||||||
.writefn = tlbi_aa64_rvae1_write },
|
|
||||||
{ .name = "TLBI_RVALE1", .state = ARM_CP_STATE_AA64,
|
|
||||||
.opc0 = 1, .opc1 = 0, .crn = 8, .crm = 6, .opc2 = 5,
|
|
||||||
.access = PL1_W, .accessfn = access_ttlb, .type = ARM_CP_NO_RAW,
|
|
||||||
.fgt = FGT_TLBIRVALE1,
|
|
||||||
.writefn = tlbi_aa64_rvae1_write },
|
|
||||||
{ .name = "TLBI_RVAALE1", .state = ARM_CP_STATE_AA64,
|
|
||||||
.opc0 = 1, .opc1 = 0, .crn = 8, .crm = 6, .opc2 = 7,
|
|
||||||
.access = PL1_W, .accessfn = access_ttlb, .type = ARM_CP_NO_RAW,
|
|
||||||
.fgt = FGT_TLBIRVAALE1,
|
|
||||||
.writefn = tlbi_aa64_rvae1_write },
|
|
||||||
{ .name = "TLBI_RIPAS2E1IS", .state = ARM_CP_STATE_AA64,
|
|
||||||
.opc0 = 1, .opc1 = 4, .crn = 8, .crm = 0, .opc2 = 2,
|
|
||||||
.access = PL2_W, .type = ARM_CP_NO_RAW,
|
|
||||||
.writefn = tlbi_aa64_ripas2e1is_write },
|
|
||||||
{ .name = "TLBI_RIPAS2LE1IS", .state = ARM_CP_STATE_AA64,
|
|
||||||
.opc0 = 1, .opc1 = 4, .crn = 8, .crm = 0, .opc2 = 6,
|
|
||||||
.access = PL2_W, .type = ARM_CP_NO_RAW,
|
|
||||||
.writefn = tlbi_aa64_ripas2e1is_write },
|
|
||||||
{ .name = "TLBI_RVAE2IS", .state = ARM_CP_STATE_AA64,
|
|
||||||
.opc0 = 1, .opc1 = 4, .crn = 8, .crm = 2, .opc2 = 1,
|
|
||||||
.access = PL2_W, .type = ARM_CP_NO_RAW | ARM_CP_EL3_NO_EL2_UNDEF,
|
|
||||||
.writefn = tlbi_aa64_rvae2is_write },
|
|
||||||
{ .name = "TLBI_RVALE2IS", .state = ARM_CP_STATE_AA64,
|
|
||||||
.opc0 = 1, .opc1 = 4, .crn = 8, .crm = 2, .opc2 = 5,
|
|
||||||
.access = PL2_W, .type = ARM_CP_NO_RAW | ARM_CP_EL3_NO_EL2_UNDEF,
|
|
||||||
.writefn = tlbi_aa64_rvae2is_write },
|
|
||||||
{ .name = "TLBI_RIPAS2E1", .state = ARM_CP_STATE_AA64,
|
|
||||||
.opc0 = 1, .opc1 = 4, .crn = 8, .crm = 4, .opc2 = 2,
|
|
||||||
.access = PL2_W, .type = ARM_CP_NO_RAW,
|
|
||||||
.writefn = tlbi_aa64_ripas2e1_write },
|
|
||||||
{ .name = "TLBI_RIPAS2LE1", .state = ARM_CP_STATE_AA64,
|
|
||||||
.opc0 = 1, .opc1 = 4, .crn = 8, .crm = 4, .opc2 = 6,
|
|
||||||
.access = PL2_W, .type = ARM_CP_NO_RAW,
|
|
||||||
.writefn = tlbi_aa64_ripas2e1_write },
|
|
||||||
{ .name = "TLBI_RVAE2OS", .state = ARM_CP_STATE_AA64,
|
|
||||||
.opc0 = 1, .opc1 = 4, .crn = 8, .crm = 5, .opc2 = 1,
|
|
||||||
.access = PL2_W, .type = ARM_CP_NO_RAW | ARM_CP_EL3_NO_EL2_UNDEF,
|
|
||||||
.writefn = tlbi_aa64_rvae2is_write },
|
|
||||||
{ .name = "TLBI_RVALE2OS", .state = ARM_CP_STATE_AA64,
|
|
||||||
.opc0 = 1, .opc1 = 4, .crn = 8, .crm = 5, .opc2 = 5,
|
|
||||||
.access = PL2_W, .type = ARM_CP_NO_RAW | ARM_CP_EL3_NO_EL2_UNDEF,
|
|
||||||
.writefn = tlbi_aa64_rvae2is_write },
|
|
||||||
{ .name = "TLBI_RVAE2", .state = ARM_CP_STATE_AA64,
|
|
||||||
.opc0 = 1, .opc1 = 4, .crn = 8, .crm = 6, .opc2 = 1,
|
|
||||||
.access = PL2_W, .type = ARM_CP_NO_RAW | ARM_CP_EL3_NO_EL2_UNDEF,
|
|
||||||
.writefn = tlbi_aa64_rvae2_write },
|
|
||||||
{ .name = "TLBI_RVALE2", .state = ARM_CP_STATE_AA64,
|
|
||||||
.opc0 = 1, .opc1 = 4, .crn = 8, .crm = 6, .opc2 = 5,
|
|
||||||
.access = PL2_W, .type = ARM_CP_NO_RAW | ARM_CP_EL3_NO_EL2_UNDEF,
|
|
||||||
.writefn = tlbi_aa64_rvae2_write },
|
|
||||||
{ .name = "TLBI_RVAE3IS", .state = ARM_CP_STATE_AA64,
|
|
||||||
.opc0 = 1, .opc1 = 6, .crn = 8, .crm = 2, .opc2 = 1,
|
|
||||||
.access = PL3_W, .type = ARM_CP_NO_RAW,
|
|
||||||
.writefn = tlbi_aa64_rvae3is_write },
|
|
||||||
{ .name = "TLBI_RVALE3IS", .state = ARM_CP_STATE_AA64,
|
|
||||||
.opc0 = 1, .opc1 = 6, .crn = 8, .crm = 2, .opc2 = 5,
|
|
||||||
.access = PL3_W, .type = ARM_CP_NO_RAW,
|
|
||||||
.writefn = tlbi_aa64_rvae3is_write },
|
|
||||||
{ .name = "TLBI_RVAE3OS", .state = ARM_CP_STATE_AA64,
|
|
||||||
.opc0 = 1, .opc1 = 6, .crn = 8, .crm = 5, .opc2 = 1,
|
|
||||||
.access = PL3_W, .type = ARM_CP_NO_RAW,
|
|
||||||
.writefn = tlbi_aa64_rvae3is_write },
|
|
||||||
{ .name = "TLBI_RVALE3OS", .state = ARM_CP_STATE_AA64,
|
|
||||||
.opc0 = 1, .opc1 = 6, .crn = 8, .crm = 5, .opc2 = 5,
|
|
||||||
.access = PL3_W, .type = ARM_CP_NO_RAW,
|
|
||||||
.writefn = tlbi_aa64_rvae3is_write },
|
|
||||||
{ .name = "TLBI_RVAE3", .state = ARM_CP_STATE_AA64,
|
|
||||||
.opc0 = 1, .opc1 = 6, .crn = 8, .crm = 6, .opc2 = 1,
|
|
||||||
.access = PL3_W, .type = ARM_CP_NO_RAW,
|
|
||||||
.writefn = tlbi_aa64_rvae3_write },
|
|
||||||
{ .name = "TLBI_RVALE3", .state = ARM_CP_STATE_AA64,
|
|
||||||
.opc0 = 1, .opc1 = 6, .crn = 8, .crm = 6, .opc2 = 5,
|
|
||||||
.access = PL3_W, .type = ARM_CP_NO_RAW,
|
|
||||||
.writefn = tlbi_aa64_rvae3_write },
|
|
||||||
};
|
|
||||||
|
|
||||||
static const ARMCPRegInfo tlbios_reginfo[] = {
|
static const ARMCPRegInfo tlbios_reginfo[] = {
|
||||||
{ .name = "TLBI_VMALLE1OS", .state = ARM_CP_STATE_AA64,
|
{ .name = "TLBI_VMALLE1OS", .state = ARM_CP_STATE_AA64,
|
||||||
.opc0 = 1, .opc1 = 0, .crn = 8, .crm = 1, .opc2 = 0,
|
.opc0 = 1, .opc1 = 0, .crn = 8, .crm = 1, .opc2 = 0,
|
||||||
|
@ -9389,9 +9066,6 @@ void register_cp_regs_for_features(ARMCPU *cpu)
|
||||||
if (cpu_isar_feature(aa64_rndr, cpu)) {
|
if (cpu_isar_feature(aa64_rndr, cpu)) {
|
||||||
define_arm_cp_regs(cpu, rndr_reginfo);
|
define_arm_cp_regs(cpu, rndr_reginfo);
|
||||||
}
|
}
|
||||||
if (cpu_isar_feature(aa64_tlbirange, cpu)) {
|
|
||||||
define_arm_cp_regs(cpu, tlbirange_reginfo);
|
|
||||||
}
|
|
||||||
if (cpu_isar_feature(aa64_tlbios, cpu)) {
|
if (cpu_isar_feature(aa64_tlbios, cpu)) {
|
||||||
define_arm_cp_regs(cpu, tlbios_reginfo);
|
define_arm_cp_regs(cpu, tlbios_reginfo);
|
||||||
}
|
}
|
||||||
|
|
|
@ -6,6 +6,7 @@
|
||||||
* SPDX-License-Identifier: GPL-2.0-or-later
|
* SPDX-License-Identifier: GPL-2.0-or-later
|
||||||
*/
|
*/
|
||||||
#include "qemu/osdep.h"
|
#include "qemu/osdep.h"
|
||||||
|
#include "qemu/log.h"
|
||||||
#include "exec/exec-all.h"
|
#include "exec/exec-all.h"
|
||||||
#include "cpu.h"
|
#include "cpu.h"
|
||||||
#include "internals.h"
|
#include "internals.h"
|
||||||
|
@ -562,6 +563,329 @@ static const ARMCPRegInfo tlbi_el3_cp_reginfo[] = {
|
||||||
.writefn = tlbi_aa64_vae3_write },
|
.writefn = tlbi_aa64_vae3_write },
|
||||||
};
|
};
|
||||||
|
|
||||||
|
#ifdef TARGET_AARCH64
|
||||||
|
typedef struct {
|
||||||
|
uint64_t base;
|
||||||
|
uint64_t length;
|
||||||
|
} TLBIRange;
|
||||||
|
|
||||||
|
static ARMGranuleSize tlbi_range_tg_to_gran_size(int tg)
|
||||||
|
{
|
||||||
|
/*
|
||||||
|
* Note that the TLBI range TG field encoding differs from both
|
||||||
|
* TG0 and TG1 encodings.
|
||||||
|
*/
|
||||||
|
switch (tg) {
|
||||||
|
case 1:
|
||||||
|
return Gran4K;
|
||||||
|
case 2:
|
||||||
|
return Gran16K;
|
||||||
|
case 3:
|
||||||
|
return Gran64K;
|
||||||
|
default:
|
||||||
|
return GranInvalid;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
static TLBIRange tlbi_aa64_get_range(CPUARMState *env, ARMMMUIdx mmuidx,
|
||||||
|
uint64_t value)
|
||||||
|
{
|
||||||
|
unsigned int page_size_granule, page_shift, num, scale, exponent;
|
||||||
|
/* Extract one bit to represent the va selector in use. */
|
||||||
|
uint64_t select = sextract64(value, 36, 1);
|
||||||
|
ARMVAParameters param = aa64_va_parameters(env, select, mmuidx, true, false);
|
||||||
|
TLBIRange ret = { };
|
||||||
|
ARMGranuleSize gran;
|
||||||
|
|
||||||
|
page_size_granule = extract64(value, 46, 2);
|
||||||
|
gran = tlbi_range_tg_to_gran_size(page_size_granule);
|
||||||
|
|
||||||
|
/* The granule encoded in value must match the granule in use. */
|
||||||
|
if (gran != param.gran) {
|
||||||
|
qemu_log_mask(LOG_GUEST_ERROR, "Invalid tlbi page size granule %d\n",
|
||||||
|
page_size_granule);
|
||||||
|
return ret;
|
||||||
|
}
|
||||||
|
|
||||||
|
page_shift = arm_granule_bits(gran);
|
||||||
|
num = extract64(value, 39, 5);
|
||||||
|
scale = extract64(value, 44, 2);
|
||||||
|
exponent = (5 * scale) + 1;
|
||||||
|
|
||||||
|
ret.length = (num + 1) << (exponent + page_shift);
|
||||||
|
|
||||||
|
if (param.select) {
|
||||||
|
ret.base = sextract64(value, 0, 37);
|
||||||
|
} else {
|
||||||
|
ret.base = extract64(value, 0, 37);
|
||||||
|
}
|
||||||
|
if (param.ds) {
|
||||||
|
/*
|
||||||
|
* With DS=1, BaseADDR is always shifted 16 so that it is able
|
||||||
|
* to address all 52 va bits. The input address is perforce
|
||||||
|
* aligned on a 64k boundary regardless of translation granule.
|
||||||
|
*/
|
||||||
|
page_shift = 16;
|
||||||
|
}
|
||||||
|
ret.base <<= page_shift;
|
||||||
|
|
||||||
|
return ret;
|
||||||
|
}
|
||||||
|
|
||||||
|
static void do_rvae_write(CPUARMState *env, uint64_t value,
|
||||||
|
int idxmap, bool synced)
|
||||||
|
{
|
||||||
|
ARMMMUIdx one_idx = ARM_MMU_IDX_A | ctz32(idxmap);
|
||||||
|
TLBIRange range;
|
||||||
|
int bits;
|
||||||
|
|
||||||
|
range = tlbi_aa64_get_range(env, one_idx, value);
|
||||||
|
bits = tlbbits_for_regime(env, one_idx, range.base);
|
||||||
|
|
||||||
|
if (synced) {
|
||||||
|
tlb_flush_range_by_mmuidx_all_cpus_synced(env_cpu(env),
|
||||||
|
range.base,
|
||||||
|
range.length,
|
||||||
|
idxmap,
|
||||||
|
bits);
|
||||||
|
} else {
|
||||||
|
tlb_flush_range_by_mmuidx(env_cpu(env), range.base,
|
||||||
|
range.length, idxmap, bits);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
static void tlbi_aa64_rvae1_write(CPUARMState *env,
|
||||||
|
const ARMCPRegInfo *ri,
|
||||||
|
uint64_t value)
|
||||||
|
{
|
||||||
|
/*
|
||||||
|
* Invalidate by VA range, EL1&0.
|
||||||
|
* Currently handles all of RVAE1, RVAAE1, RVAALE1 and RVALE1,
|
||||||
|
* since we don't support flush-for-specific-ASID-only or
|
||||||
|
* flush-last-level-only.
|
||||||
|
*/
|
||||||
|
|
||||||
|
do_rvae_write(env, value, vae1_tlbmask(env),
|
||||||
|
tlb_force_broadcast(env));
|
||||||
|
}
|
||||||
|
|
||||||
|
static void tlbi_aa64_rvae1is_write(CPUARMState *env,
|
||||||
|
const ARMCPRegInfo *ri,
|
||||||
|
uint64_t value)
|
||||||
|
{
|
||||||
|
/*
|
||||||
|
* Invalidate by VA range, Inner/Outer Shareable EL1&0.
|
||||||
|
* Currently handles all of RVAE1IS, RVAE1OS, RVAAE1IS, RVAAE1OS,
|
||||||
|
* RVAALE1IS, RVAALE1OS, RVALE1IS and RVALE1OS, since we don't support
|
||||||
|
* flush-for-specific-ASID-only, flush-last-level-only or inner/outer
|
||||||
|
* shareable specific flushes.
|
||||||
|
*/
|
||||||
|
|
||||||
|
do_rvae_write(env, value, vae1_tlbmask(env), true);
|
||||||
|
}
|
||||||
|
|
||||||
|
static void tlbi_aa64_rvae2_write(CPUARMState *env,
|
||||||
|
const ARMCPRegInfo *ri,
|
||||||
|
uint64_t value)
|
||||||
|
{
|
||||||
|
/*
|
||||||
|
* Invalidate by VA range, EL2.
|
||||||
|
* Currently handles all of RVAE2 and RVALE2,
|
||||||
|
* since we don't support flush-for-specific-ASID-only or
|
||||||
|
* flush-last-level-only.
|
||||||
|
*/
|
||||||
|
|
||||||
|
do_rvae_write(env, value, vae2_tlbmask(env),
|
||||||
|
tlb_force_broadcast(env));
|
||||||
|
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
static void tlbi_aa64_rvae2is_write(CPUARMState *env,
|
||||||
|
const ARMCPRegInfo *ri,
|
||||||
|
uint64_t value)
|
||||||
|
{
|
||||||
|
/*
|
||||||
|
* Invalidate by VA range, Inner/Outer Shareable, EL2.
|
||||||
|
* Currently handles all of RVAE2IS, RVAE2OS, RVALE2IS and RVALE2OS,
|
||||||
|
* since we don't support flush-for-specific-ASID-only,
|
||||||
|
* flush-last-level-only or inner/outer shareable specific flushes.
|
||||||
|
*/
|
||||||
|
|
||||||
|
do_rvae_write(env, value, vae2_tlbmask(env), true);
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
static void tlbi_aa64_rvae3_write(CPUARMState *env,
|
||||||
|
const ARMCPRegInfo *ri,
|
||||||
|
uint64_t value)
|
||||||
|
{
|
||||||
|
/*
|
||||||
|
* Invalidate by VA range, EL3.
|
||||||
|
* Currently handles all of RVAE3 and RVALE3,
|
||||||
|
* since we don't support flush-for-specific-ASID-only or
|
||||||
|
* flush-last-level-only.
|
||||||
|
*/
|
||||||
|
|
||||||
|
do_rvae_write(env, value, ARMMMUIdxBit_E3, tlb_force_broadcast(env));
|
||||||
|
}
|
||||||
|
|
||||||
|
static void tlbi_aa64_rvae3is_write(CPUARMState *env,
|
||||||
|
const ARMCPRegInfo *ri,
|
||||||
|
uint64_t value)
|
||||||
|
{
|
||||||
|
/*
|
||||||
|
* Invalidate by VA range, EL3, Inner/Outer Shareable.
|
||||||
|
* Currently handles all of RVAE3IS, RVAE3OS, RVALE3IS and RVALE3OS,
|
||||||
|
* since we don't support flush-for-specific-ASID-only,
|
||||||
|
* flush-last-level-only or inner/outer specific flushes.
|
||||||
|
*/
|
||||||
|
|
||||||
|
do_rvae_write(env, value, ARMMMUIdxBit_E3, true);
|
||||||
|
}
|
||||||
|
|
||||||
|
static void tlbi_aa64_ripas2e1_write(CPUARMState *env, const ARMCPRegInfo *ri,
|
||||||
|
uint64_t value)
|
||||||
|
{
|
||||||
|
do_rvae_write(env, value, ipas2e1_tlbmask(env, value),
|
||||||
|
tlb_force_broadcast(env));
|
||||||
|
}
|
||||||
|
|
||||||
|
static void tlbi_aa64_ripas2e1is_write(CPUARMState *env,
|
||||||
|
const ARMCPRegInfo *ri,
|
||||||
|
uint64_t value)
|
||||||
|
{
|
||||||
|
do_rvae_write(env, value, ipas2e1_tlbmask(env, value), true);
|
||||||
|
}
|
||||||
|
|
||||||
|
static const ARMCPRegInfo tlbirange_reginfo[] = {
|
||||||
|
{ .name = "TLBI_RVAE1IS", .state = ARM_CP_STATE_AA64,
|
||||||
|
.opc0 = 1, .opc1 = 0, .crn = 8, .crm = 2, .opc2 = 1,
|
||||||
|
.access = PL1_W, .accessfn = access_ttlbis, .type = ARM_CP_NO_RAW,
|
||||||
|
.fgt = FGT_TLBIRVAE1IS,
|
||||||
|
.writefn = tlbi_aa64_rvae1is_write },
|
||||||
|
{ .name = "TLBI_RVAAE1IS", .state = ARM_CP_STATE_AA64,
|
||||||
|
.opc0 = 1, .opc1 = 0, .crn = 8, .crm = 2, .opc2 = 3,
|
||||||
|
.access = PL1_W, .accessfn = access_ttlbis, .type = ARM_CP_NO_RAW,
|
||||||
|
.fgt = FGT_TLBIRVAAE1IS,
|
||||||
|
.writefn = tlbi_aa64_rvae1is_write },
|
||||||
|
{ .name = "TLBI_RVALE1IS", .state = ARM_CP_STATE_AA64,
|
||||||
|
.opc0 = 1, .opc1 = 0, .crn = 8, .crm = 2, .opc2 = 5,
|
||||||
|
.access = PL1_W, .accessfn = access_ttlbis, .type = ARM_CP_NO_RAW,
|
||||||
|
.fgt = FGT_TLBIRVALE1IS,
|
||||||
|
.writefn = tlbi_aa64_rvae1is_write },
|
||||||
|
{ .name = "TLBI_RVAALE1IS", .state = ARM_CP_STATE_AA64,
|
||||||
|
.opc0 = 1, .opc1 = 0, .crn = 8, .crm = 2, .opc2 = 7,
|
||||||
|
.access = PL1_W, .accessfn = access_ttlbis, .type = ARM_CP_NO_RAW,
|
||||||
|
.fgt = FGT_TLBIRVAALE1IS,
|
||||||
|
.writefn = tlbi_aa64_rvae1is_write },
|
||||||
|
{ .name = "TLBI_RVAE1OS", .state = ARM_CP_STATE_AA64,
|
||||||
|
.opc0 = 1, .opc1 = 0, .crn = 8, .crm = 5, .opc2 = 1,
|
||||||
|
.access = PL1_W, .accessfn = access_ttlbos, .type = ARM_CP_NO_RAW,
|
||||||
|
.fgt = FGT_TLBIRVAE1OS,
|
||||||
|
.writefn = tlbi_aa64_rvae1is_write },
|
||||||
|
{ .name = "TLBI_RVAAE1OS", .state = ARM_CP_STATE_AA64,
|
||||||
|
.opc0 = 1, .opc1 = 0, .crn = 8, .crm = 5, .opc2 = 3,
|
||||||
|
.access = PL1_W, .accessfn = access_ttlbos, .type = ARM_CP_NO_RAW,
|
||||||
|
.fgt = FGT_TLBIRVAAE1OS,
|
||||||
|
.writefn = tlbi_aa64_rvae1is_write },
|
||||||
|
{ .name = "TLBI_RVALE1OS", .state = ARM_CP_STATE_AA64,
|
||||||
|
.opc0 = 1, .opc1 = 0, .crn = 8, .crm = 5, .opc2 = 5,
|
||||||
|
.access = PL1_W, .accessfn = access_ttlbos, .type = ARM_CP_NO_RAW,
|
||||||
|
.fgt = FGT_TLBIRVALE1OS,
|
||||||
|
.writefn = tlbi_aa64_rvae1is_write },
|
||||||
|
{ .name = "TLBI_RVAALE1OS", .state = ARM_CP_STATE_AA64,
|
||||||
|
.opc0 = 1, .opc1 = 0, .crn = 8, .crm = 5, .opc2 = 7,
|
||||||
|
.access = PL1_W, .accessfn = access_ttlbos, .type = ARM_CP_NO_RAW,
|
||||||
|
.fgt = FGT_TLBIRVAALE1OS,
|
||||||
|
.writefn = tlbi_aa64_rvae1is_write },
|
||||||
|
{ .name = "TLBI_RVAE1", .state = ARM_CP_STATE_AA64,
|
||||||
|
.opc0 = 1, .opc1 = 0, .crn = 8, .crm = 6, .opc2 = 1,
|
||||||
|
.access = PL1_W, .accessfn = access_ttlb, .type = ARM_CP_NO_RAW,
|
||||||
|
.fgt = FGT_TLBIRVAE1,
|
||||||
|
.writefn = tlbi_aa64_rvae1_write },
|
||||||
|
{ .name = "TLBI_RVAAE1", .state = ARM_CP_STATE_AA64,
|
||||||
|
.opc0 = 1, .opc1 = 0, .crn = 8, .crm = 6, .opc2 = 3,
|
||||||
|
.access = PL1_W, .accessfn = access_ttlb, .type = ARM_CP_NO_RAW,
|
||||||
|
.fgt = FGT_TLBIRVAAE1,
|
||||||
|
.writefn = tlbi_aa64_rvae1_write },
|
||||||
|
{ .name = "TLBI_RVALE1", .state = ARM_CP_STATE_AA64,
|
||||||
|
.opc0 = 1, .opc1 = 0, .crn = 8, .crm = 6, .opc2 = 5,
|
||||||
|
.access = PL1_W, .accessfn = access_ttlb, .type = ARM_CP_NO_RAW,
|
||||||
|
.fgt = FGT_TLBIRVALE1,
|
||||||
|
.writefn = tlbi_aa64_rvae1_write },
|
||||||
|
{ .name = "TLBI_RVAALE1", .state = ARM_CP_STATE_AA64,
|
||||||
|
.opc0 = 1, .opc1 = 0, .crn = 8, .crm = 6, .opc2 = 7,
|
||||||
|
.access = PL1_W, .accessfn = access_ttlb, .type = ARM_CP_NO_RAW,
|
||||||
|
.fgt = FGT_TLBIRVAALE1,
|
||||||
|
.writefn = tlbi_aa64_rvae1_write },
|
||||||
|
{ .name = "TLBI_RIPAS2E1IS", .state = ARM_CP_STATE_AA64,
|
||||||
|
.opc0 = 1, .opc1 = 4, .crn = 8, .crm = 0, .opc2 = 2,
|
||||||
|
.access = PL2_W, .type = ARM_CP_NO_RAW,
|
||||||
|
.writefn = tlbi_aa64_ripas2e1is_write },
|
||||||
|
{ .name = "TLBI_RIPAS2LE1IS", .state = ARM_CP_STATE_AA64,
|
||||||
|
.opc0 = 1, .opc1 = 4, .crn = 8, .crm = 0, .opc2 = 6,
|
||||||
|
.access = PL2_W, .type = ARM_CP_NO_RAW,
|
||||||
|
.writefn = tlbi_aa64_ripas2e1is_write },
|
||||||
|
{ .name = "TLBI_RVAE2IS", .state = ARM_CP_STATE_AA64,
|
||||||
|
.opc0 = 1, .opc1 = 4, .crn = 8, .crm = 2, .opc2 = 1,
|
||||||
|
.access = PL2_W, .type = ARM_CP_NO_RAW | ARM_CP_EL3_NO_EL2_UNDEF,
|
||||||
|
.writefn = tlbi_aa64_rvae2is_write },
|
||||||
|
{ .name = "TLBI_RVALE2IS", .state = ARM_CP_STATE_AA64,
|
||||||
|
.opc0 = 1, .opc1 = 4, .crn = 8, .crm = 2, .opc2 = 5,
|
||||||
|
.access = PL2_W, .type = ARM_CP_NO_RAW | ARM_CP_EL3_NO_EL2_UNDEF,
|
||||||
|
.writefn = tlbi_aa64_rvae2is_write },
|
||||||
|
{ .name = "TLBI_RIPAS2E1", .state = ARM_CP_STATE_AA64,
|
||||||
|
.opc0 = 1, .opc1 = 4, .crn = 8, .crm = 4, .opc2 = 2,
|
||||||
|
.access = PL2_W, .type = ARM_CP_NO_RAW,
|
||||||
|
.writefn = tlbi_aa64_ripas2e1_write },
|
||||||
|
{ .name = "TLBI_RIPAS2LE1", .state = ARM_CP_STATE_AA64,
|
||||||
|
.opc0 = 1, .opc1 = 4, .crn = 8, .crm = 4, .opc2 = 6,
|
||||||
|
.access = PL2_W, .type = ARM_CP_NO_RAW,
|
||||||
|
.writefn = tlbi_aa64_ripas2e1_write },
|
||||||
|
{ .name = "TLBI_RVAE2OS", .state = ARM_CP_STATE_AA64,
|
||||||
|
.opc0 = 1, .opc1 = 4, .crn = 8, .crm = 5, .opc2 = 1,
|
||||||
|
.access = PL2_W, .type = ARM_CP_NO_RAW | ARM_CP_EL3_NO_EL2_UNDEF,
|
||||||
|
.writefn = tlbi_aa64_rvae2is_write },
|
||||||
|
{ .name = "TLBI_RVALE2OS", .state = ARM_CP_STATE_AA64,
|
||||||
|
.opc0 = 1, .opc1 = 4, .crn = 8, .crm = 5, .opc2 = 5,
|
||||||
|
.access = PL2_W, .type = ARM_CP_NO_RAW | ARM_CP_EL3_NO_EL2_UNDEF,
|
||||||
|
.writefn = tlbi_aa64_rvae2is_write },
|
||||||
|
{ .name = "TLBI_RVAE2", .state = ARM_CP_STATE_AA64,
|
||||||
|
.opc0 = 1, .opc1 = 4, .crn = 8, .crm = 6, .opc2 = 1,
|
||||||
|
.access = PL2_W, .type = ARM_CP_NO_RAW | ARM_CP_EL3_NO_EL2_UNDEF,
|
||||||
|
.writefn = tlbi_aa64_rvae2_write },
|
||||||
|
{ .name = "TLBI_RVALE2", .state = ARM_CP_STATE_AA64,
|
||||||
|
.opc0 = 1, .opc1 = 4, .crn = 8, .crm = 6, .opc2 = 5,
|
||||||
|
.access = PL2_W, .type = ARM_CP_NO_RAW | ARM_CP_EL3_NO_EL2_UNDEF,
|
||||||
|
.writefn = tlbi_aa64_rvae2_write },
|
||||||
|
{ .name = "TLBI_RVAE3IS", .state = ARM_CP_STATE_AA64,
|
||||||
|
.opc0 = 1, .opc1 = 6, .crn = 8, .crm = 2, .opc2 = 1,
|
||||||
|
.access = PL3_W, .type = ARM_CP_NO_RAW,
|
||||||
|
.writefn = tlbi_aa64_rvae3is_write },
|
||||||
|
{ .name = "TLBI_RVALE3IS", .state = ARM_CP_STATE_AA64,
|
||||||
|
.opc0 = 1, .opc1 = 6, .crn = 8, .crm = 2, .opc2 = 5,
|
||||||
|
.access = PL3_W, .type = ARM_CP_NO_RAW,
|
||||||
|
.writefn = tlbi_aa64_rvae3is_write },
|
||||||
|
{ .name = "TLBI_RVAE3OS", .state = ARM_CP_STATE_AA64,
|
||||||
|
.opc0 = 1, .opc1 = 6, .crn = 8, .crm = 5, .opc2 = 1,
|
||||||
|
.access = PL3_W, .type = ARM_CP_NO_RAW,
|
||||||
|
.writefn = tlbi_aa64_rvae3is_write },
|
||||||
|
{ .name = "TLBI_RVALE3OS", .state = ARM_CP_STATE_AA64,
|
||||||
|
.opc0 = 1, .opc1 = 6, .crn = 8, .crm = 5, .opc2 = 5,
|
||||||
|
.access = PL3_W, .type = ARM_CP_NO_RAW,
|
||||||
|
.writefn = tlbi_aa64_rvae3is_write },
|
||||||
|
{ .name = "TLBI_RVAE3", .state = ARM_CP_STATE_AA64,
|
||||||
|
.opc0 = 1, .opc1 = 6, .crn = 8, .crm = 6, .opc2 = 1,
|
||||||
|
.access = PL3_W, .type = ARM_CP_NO_RAW,
|
||||||
|
.writefn = tlbi_aa64_rvae3_write },
|
||||||
|
{ .name = "TLBI_RVALE3", .state = ARM_CP_STATE_AA64,
|
||||||
|
.opc0 = 1, .opc1 = 6, .crn = 8, .crm = 6, .opc2 = 5,
|
||||||
|
.access = PL3_W, .type = ARM_CP_NO_RAW,
|
||||||
|
.writefn = tlbi_aa64_rvae3_write },
|
||||||
|
};
|
||||||
|
#endif
|
||||||
|
|
||||||
void define_tlb_insn_regs(ARMCPU *cpu)
|
void define_tlb_insn_regs(ARMCPU *cpu)
|
||||||
{
|
{
|
||||||
CPUARMState *env = &cpu->env;
|
CPUARMState *env = &cpu->env;
|
||||||
|
@ -591,4 +915,9 @@ void define_tlb_insn_regs(ARMCPU *cpu)
|
||||||
if (arm_feature(env, ARM_FEATURE_EL3)) {
|
if (arm_feature(env, ARM_FEATURE_EL3)) {
|
||||||
define_arm_cp_regs(cpu, tlbi_el3_cp_reginfo);
|
define_arm_cp_regs(cpu, tlbi_el3_cp_reginfo);
|
||||||
}
|
}
|
||||||
|
#ifdef TARGET_AARCH64
|
||||||
|
if (cpu_isar_feature(aa64_tlbirange, cpu)) {
|
||||||
|
define_arm_cp_regs(cpu, tlbirange_reginfo);
|
||||||
|
}
|
||||||
|
#endif
|
||||||
}
|
}
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue