diff --git a/target/arm/ptw.c b/target/arm/ptw.c index 3302376e42..691110f70c 100644 --- a/target/arm/ptw.c +++ b/target/arm/ptw.c @@ -1050,7 +1050,7 @@ static bool get_phys_addr_lpae(CPUARMState *env, S1Translate *ptw, hwaddr descaddr, indexmask, indexmask_grainsize; uint32_t tableattrs; target_ulong page_size; - uint32_t attrs; + uint64_t attrs; int32_t stride; int addrsize, inputsize, outputsize; uint64_t tcr = regime_tcr(env, mmu_idx); @@ -1324,49 +1324,48 @@ static bool get_phys_addr_lpae(CPUARMState *env, S1Translate *ptw, descaddr &= ~(hwaddr)(page_size - 1); descaddr |= (address & (page_size - 1)); /* Extract attributes from the descriptor */ - attrs = extract64(descriptor, 2, 10) - | (extract64(descriptor, 52, 12) << 10); + attrs = descriptor & (MAKE_64BIT_MASK(2, 10) | MAKE_64BIT_MASK(52, 12)); if (regime_is_stage2(mmu_idx)) { /* Stage 2 table descriptors do not include any attribute fields */ goto skip_attrs; } /* Merge in attributes from table descriptors */ - attrs |= nstable << 3; /* NS */ + attrs |= nstable << 5; /* NS */ guarded = extract64(descriptor, 50, 1); /* GP */ if (param.hpd) { /* HPD disables all the table attributes except NSTable. */ goto skip_attrs; } - attrs |= extract32(tableattrs, 0, 2) << 11; /* XN, PXN */ + attrs |= extract64(tableattrs, 0, 2) << 53; /* XN, PXN */ /* * The sense of AP[1] vs APTable[0] is reversed, as APTable[0] == 1 * means "force PL1 access only", which means forcing AP[1] to 0. */ - attrs &= ~(extract32(tableattrs, 2, 1) << 4); /* !APT[0] => AP[1] */ - attrs |= extract32(tableattrs, 3, 1) << 5; /* APT[1] => AP[2] */ + attrs &= ~(extract64(tableattrs, 2, 1) << 6); /* !APT[0] => AP[1] */ + attrs |= extract32(tableattrs, 3, 1) << 7; /* APT[1] => AP[2] */ skip_attrs: /* * Here descaddr is the final physical address, and attributes * are all in attrs. */ - if ((attrs & (1 << 8)) == 0) { + if ((attrs & (1 << 10)) == 0) { /* Access flag */ fi->type = ARMFault_AccessFlag; goto do_fault; } - ap = extract32(attrs, 4, 2); + ap = extract32(attrs, 6, 2); if (regime_is_stage2(mmu_idx)) { ns = mmu_idx == ARMMMUIdx_Stage2; - xn = extract32(attrs, 11, 2); + xn = extract64(attrs, 53, 2); result->f.prot = get_S2prot(env, ap, xn, s1_is_el0); } else { - ns = extract32(attrs, 3, 1); - xn = extract32(attrs, 12, 1); - pxn = extract32(attrs, 11, 1); + ns = extract32(attrs, 5, 1); + xn = extract64(attrs, 54, 1); + pxn = extract64(attrs, 53, 1); result->f.prot = get_S1prot(env, mmu_idx, aarch64, ap, ns, xn, pxn); } @@ -1391,10 +1390,10 @@ static bool get_phys_addr_lpae(CPUARMState *env, S1Translate *ptw, if (regime_is_stage2(mmu_idx)) { result->cacheattrs.is_s2_format = true; - result->cacheattrs.attrs = extract32(attrs, 0, 4); + result->cacheattrs.attrs = extract32(attrs, 2, 4); } else { /* Index into MAIR registers for cache attributes */ - uint8_t attrindx = extract32(attrs, 0, 3); + uint8_t attrindx = extract32(attrs, 2, 3); uint64_t mair = env->cp15.mair_el[regime_el(env, mmu_idx)]; assert(attrindx <= 7); result->cacheattrs.is_s2_format = false; @@ -1409,7 +1408,7 @@ static bool get_phys_addr_lpae(CPUARMState *env, S1Translate *ptw, if (param.ds) { result->cacheattrs.shareability = param.sh; } else { - result->cacheattrs.shareability = extract32(attrs, 6, 2); + result->cacheattrs.shareability = extract32(attrs, 8, 2); } result->f.phys_addr = descaddr;