Fix C15 FSR (C5) domain setting
PATCH 1/1 Fix C15 FSR (C5) domain setting
During Xvisor development, it was noted that qemu did not return the correct domain value in the C15 [Data] FSR register (C5).
This patch is a proposal to fix it.
Signed-off-by Jean-Christophe DUBOIS<[email protected]>
---
target-arm/helper.c 2011-11-04 00:49:03.247062518 +0100 renamed from target-arm/helper.c 2011-10-12 18:41:43.000000000 +0200 +13 -10
@@ -924,12 +924,12 @@ /* Check section/page access permissions. Returns the page protection flags, or zero if the access is not permitted. */ -static inline int check_ap(CPUState *env, int ap, int domain, int access_type, +static inline int check_ap(CPUState *env, int ap, int domain_prot, int access_type, int is_user) { int prot_ro; - if (domain == 3) + if (domain_prot == 3) return PAGE_READ | PAGE_WRITE; if (access_type == 1)
@@ -996,6 +996,7 @@ int type; int ap; int domain; + int domain_prot; uint32_t phys_addr; /* Pagetable walk. */
@@ -1003,13 +1004,14 @@ table = get_level1_table_address(env, address); desc = ldl_phys(table); type = (desc & 3); - domain = (env->cp15.c3 >> ((desc >> 4) & 0x1e)) & 3; + domain = (desc >> 5) & 0x0f; + domain_prot = (env->cp15.c3 >> (domain * 2)) & 3; if (type == 0) { /* Section translation fault. */ code = 5; goto do_fault; } - if (domain == 0 || domain == 2) { + if (domain_prot == 0 || domain_prot == 2) { if (type == 2) code = 9; /* Section domain fault. */ else
@@ -1067,7 +1069,7 @@ } code = 15; } - *prot = check_ap(env, ap, domain, access_type, is_user); + *prot = check_ap(env, ap, domain_prot, access_type, is_user); if (!*prot) { /* Access permission fault. */ goto do_fault;
@@ -1090,6 +1092,7 @@ int type; int ap; int domain; + int domain_prot; uint32_t phys_addr; /* Pagetable walk. */
@@ -1107,10 +1110,10 @@ domain = 0; } else { /* Section or page. */ - domain = (desc >> 4) & 0x1e; + domain = (desc >> 5) & 0x0f; } - domain = (env->cp15.c3 >> domain) & 3; - if (domain == 0 || domain == 2) { + domain_prot = (env->cp15.c3 >> (domain * 2)) & 3; + if (domain_prot == 0 || domain_prot == 2) { if (type == 2) code = 9; /* Section domain fault. */ else
@@ -1155,7 +1158,7 @@ } code = 15; } - if (domain == 3) { + if (domain_prot == 3) { *prot = PAGE_READ | PAGE_WRITE | PAGE_EXEC; } else { if (xn && access_type == 2)
@@ -1167,7 +1170,7 @@ code = (code == 15) ? 6 : 3; goto do_fault; } - *prot = check_ap(env, ap, domain, access_type, is_user); + *prot = check_ap(env, ap, domain_prot, access_type, is_user); if (!*prot) { /* Access permission fault. */ goto do_fault;