1
target-arm queue of various easier things that had piled
1
Hi; this is the latest target-arm queue; most of this is a refactoring
2
up while I was on holiday.
2
patchset from RTH for the arm page-table-walk emulation.
3
3
4
thanks
4
thanks
5
-- PMM
5
-- PMM
6
6
7
The following changes since commit 506e4a00de01e0b29fa83db5cbbc3d154253b4ea:
7
The following changes since commit f1d33f55c47dfdaf8daacd618588ad3ae4c452d1:
8
8
9
Merge remote-tracking branch 'remotes/dgibson/tags/ppc-for-3.1-20180925' into staging (2018-09-25 13:30:45 +0100)
9
Merge tag 'pull-testing-gdbstub-plugins-gitdm-061022-3' of https://github.com/stsquad/qemu into staging (2022-10-06 07:11:56 -0400)
10
10
11
are available in the Git repository at:
11
are available in the Git repository at:
12
12
13
https://git.linaro.org/people/pmaydell/qemu-arm.git tags/pull-target-arm-20180925
13
https://git.linaro.org/people/pmaydell/qemu-arm.git tags/pull-target-arm-20221010
14
14
15
for you to fetch changes up to 4a87106b160a3e72152443065fb92f8a1313c23d:
15
for you to fetch changes up to 915f62844cf62e428c7c178149b5ff1cbe129b07:
16
16
17
target/arm: Start AArch32 CPUs with EL2 but not EL3 in Hyp mode (2018-09-25 14:14:07 +0100)
17
docs/system/arm/emulation.rst: Report FEAT_GTG support (2022-10-10 14:52:25 +0100)
18
18
19
----------------------------------------------------------------
19
----------------------------------------------------------------
20
target-arm queue:
20
target-arm queue:
21
* target/arm: Fix cpu_get_tb_cpu_state() for non-SVE CPUs
21
* Retry KVM_CREATE_VM call if it fails EINTR
22
* hw/arm/exynos4210: fix Exynos4210 UART support
22
* allow setting SCR_EL3.EnTP2 when FEAT_SME is implemented
23
* hw/arm/virt-acpi-build: Add a check for memory-less NUMA nodes
23
* docs/nuvoton: Update URL for images
24
* arm: Add BBC micro:bit machine
24
* refactoring of page table walk code
25
* aspeed/i2c: Fix interrupt handling bugs
25
* hw/arm/boot: set CPTR_EL3.ESM and SCR_EL3.EnTP2 when booting Linux with EL3
26
* hw/arm/smmu-common: Fix the name of the iommu memory regions
26
* Don't allow guest to use unimplemented granule sizes
27
* hw/arm/smmuv3: fix eventq recording and IRQ triggerring
27
* Report FEAT_GTG support
28
* hw/intc/arm_gic: Document QEMU interface
29
* hw/intc/arm_gic: Drop GIC_BASE_IRQ macro
30
* hw/net/pcnet-pci: Convert away from old_mmio accessors
31
* hw/timer/cmsdk-apb-dualtimer: Add missing 'break' statements
32
* aspeed/timer: fix compile breakage with clang 3.4.2
33
* hw/arm/aspeed: change the FMC flash model of the AST2500 evb
34
* hw/arm/aspeed: Minor code cleanups
35
* target/arm: Start AArch32 CPUs with EL2 but not EL3 in Hyp mode
36
28
37
----------------------------------------------------------------
29
----------------------------------------------------------------
38
Bartlomiej Zolnierkiewicz (1):
30
Jerome Forissier (2):
39
hw/arm/exynos4210: fix Exynos4210 UART support
31
target/arm: allow setting SCR_EL3.EnTP2 when FEAT_SME is implemented
32
hw/arm/boot: set CPTR_EL3.ESM and SCR_EL3.EnTP2 when booting Linux with EL3
40
33
41
Cédric Le Goater (5):
34
Joel Stanley (1):
42
aspeed/i2c: interrupts should be cleared by software only
35
docs/nuvoton: Update URL for images
43
aspeed/timer: fix compile breakage with clang 3.4.2
44
hw/arm/aspeed: change the FMC flash model of the AST2500 evb
45
hw/arm/aspeed: Add an Aspeed machine class
46
aspeed/smc: fix some alignment issues
47
36
48
Eric Auger (2):
37
Peter Maydell (4):
49
hw/arm/smmu-common: Fix the name of the iommu memory regions
38
target/arm/kvm: Retry KVM_CREATE_VM call if it fails EINTR
50
hw/arm/smmuv3: fix eventq recording and IRQ triggerring
39
target/arm: Don't allow guest to use unimplemented granule sizes
40
target/arm: Use ARMGranuleSize in ARMVAParameters
41
docs/system/arm/emulation.rst: Report FEAT_GTG support
51
42
52
Guenter Roeck (2):
43
Richard Henderson (21):
53
aspeed/i2c: Handle receive command in separate function
44
target/arm: Split s2walk_secure from ipa_secure in get_phys_addr
54
aspeed/i2c: Fix receive done interrupt handling
45
target/arm: Make the final stage1+2 write to secure be unconditional
46
target/arm: Add is_secure parameter to get_phys_addr_lpae
47
target/arm: Fix S2 disabled check in S1_ptw_translate
48
target/arm: Add is_secure parameter to regime_translation_disabled
49
target/arm: Split out get_phys_addr_with_secure
50
target/arm: Add is_secure parameter to v7m_read_half_insn
51
target/arm: Add TBFLAG_M32.SECURE
52
target/arm: Merge regime_is_secure into get_phys_addr
53
target/arm: Add is_secure parameter to do_ats_write
54
target/arm: Fold secure and non-secure a-profile mmu indexes
55
target/arm: Reorg regime_translation_disabled
56
target/arm: Drop secure check for HCR.TGE vs SCTLR_EL1.M
57
target/arm: Introduce arm_hcr_el2_eff_secstate
58
target/arm: Hoist read of *is_secure in S1_ptw_translate
59
target/arm: Remove env argument from combined_attrs_fwb
60
target/arm: Pass HCR to attribute subroutines.
61
target/arm: Fix ATS12NSO* from S PL1
62
target/arm: Split out get_phys_addr_disabled
63
target/arm: Fix cacheattr in get_phys_addr_disabled
64
target/arm: Use tlb_set_page_full
55
65
56
Joel Stanley (3):
66
docs/system/arm/emulation.rst | 1 +
57
MAINTAINERS: Add NRF51 entry
67
docs/system/arm/nuvoton.rst | 4 +-
58
arm: Add Nordic Semiconductor nRF51 SoC
68
target/arm/cpu-param.h | 2 +-
59
arm: Add BBC micro:bit machine
69
target/arm/cpu.h | 181 ++++++++------
60
70
target/arm/internals.h | 150 ++++++-----
61
Peter Maydell (6):
71
hw/arm/boot.c | 4 +
62
hw/intc/arm_gic: Document QEMU interface
72
target/arm/helper.c | 332 ++++++++++++++----------
63
hw/intc/arm_gic: Drop GIC_BASE_IRQ macro
73
target/arm/kvm.c | 4 +-
64
hw/net/pcnet-pci: Convert away from old_mmio accessors
74
target/arm/m_helper.c | 29 ++-
65
hw/net/pcnet-pci: Unify pcnet_ioport_read/write and pcnet_mmio_read/write
75
target/arm/ptw.c | 570 ++++++++++++++++++++++--------------------
66
hw/timer/cmsdk-apb-dualtimer: Add missing 'break' statements
76
target/arm/tlb_helper.c | 9 +-
67
target/arm: Start AArch32 CPUs with EL2 but not EL3 in Hyp mode
77
target/arm/translate-a64.c | 8 -
68
78
target/arm/translate.c | 9 +-
69
Richard Henderson (1):
79
13 files changed, 717 insertions(+), 586 deletions(-)
70
target/arm: Fix cpu_get_tb_cpu_state() for non-SVE CPUs
71
72
Shannon Zhao (1):
73
hw/arm/virt-acpi-build: Add a check for memory-less NUMA nodes
74
75
hw/arm/Makefile.objs | 1 +
76
hw/arm/smmuv3-internal.h | 26 ++---
77
hw/intc/gic_internal.h | 2 -
78
include/hw/arm/aspeed.h | 46 +++++++++
79
include/hw/arm/nrf51_soc.h | 41 ++++++++
80
include/hw/intc/arm_gic.h | 43 ++++++++
81
include/hw/timer/aspeed_timer.h | 3 +-
82
hw/arm/aspeed.c | 212 +++++++++++++---------------------------
83
hw/arm/exynos4210.c | 8 +-
84
hw/arm/microbit.c | 67 +++++++++++++
85
hw/arm/nrf51_soc.c | 133 +++++++++++++++++++++++++
86
hw/arm/smmu-common.c | 6 +-
87
hw/arm/smmuv3.c | 2 +-
88
hw/arm/virt-acpi-build.c | 10 +-
89
hw/i2c/aspeed_i2c.c | 63 ++++++++----
90
hw/intc/arm_gic.c | 31 +++---
91
hw/intc/arm_gic_common.c | 1 -
92
hw/net/pcnet-pci.c | 98 ++-----------------
93
hw/ssi/aspeed_smc.c | 8 +-
94
hw/timer/aspeed_timer.c | 1 -
95
hw/timer/cmsdk-apb-dualtimer.c | 2 +
96
target/arm/cpu.c | 14 ++-
97
target/arm/helper.c | 45 +++++----
98
MAINTAINERS | 8 ++
99
default-configs/arm-softmmu.mak | 1 +
100
hw/net/trace-events | 6 --
101
26 files changed, 542 insertions(+), 336 deletions(-)
102
create mode 100644 include/hw/arm/aspeed.h
103
create mode 100644 include/hw/arm/nrf51_soc.h
104
create mode 100644 hw/arm/microbit.c
105
create mode 100644 hw/arm/nrf51_soc.c
106
diff view generated by jsdifflib
New patch
1
Occasionally the KVM_CREATE_VM ioctl can return EINTR, even though
2
there is no pending signal to be taken. In commit 94ccff13382055
3
we added a retry-on-EINTR loop to the KVM_CREATE_VM call in the
4
generic KVM code. Adopt the same approach for the use of the
5
ioctl in the Arm-specific KVM code (where we use it to create a
6
scratch VM for probing for various things).
1
7
8
For more information, see the mailing list thread:
9
https://lore.kernel.org/qemu-devel/8735e0s1zw.wl-maz@kernel.org/
10
11
Reported-by: Vitaly Chikunov <vt@altlinux.org>
12
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
13
Reviewed-by: Vitaly Chikunov <vt@altlinux.org>
14
Reviewed-by: Eric Auger <eric.auger@redhat.com>
15
Acked-by: Marc Zyngier <maz@kernel.org>
16
Message-id: 20220930113824.1933293-1-peter.maydell@linaro.org
17
---
18
target/arm/kvm.c | 4 +++-
19
1 file changed, 3 insertions(+), 1 deletion(-)
20
21
diff --git a/target/arm/kvm.c b/target/arm/kvm.c
22
index XXXXXXX..XXXXXXX 100644
23
--- a/target/arm/kvm.c
24
+++ b/target/arm/kvm.c
25
@@ -XXX,XX +XXX,XX @@ bool kvm_arm_create_scratch_host_vcpu(const uint32_t *cpus_to_try,
26
if (max_vm_pa_size < 0) {
27
max_vm_pa_size = 0;
28
}
29
- vmfd = ioctl(kvmfd, KVM_CREATE_VM, max_vm_pa_size);
30
+ do {
31
+ vmfd = ioctl(kvmfd, KVM_CREATE_VM, max_vm_pa_size);
32
+ } while (vmfd == -1 && errno == EINTR);
33
if (vmfd < 0) {
34
goto err;
35
}
36
--
37
2.25.1
diff view generated by jsdifflib
New patch
1
From: Jerome Forissier <jerome.forissier@linaro.org>
1
2
3
Updates write_scr() to allow setting SCR_EL3.EnTP2 when FEAT_SME is
4
implemented. SCR_EL3 being a 64-bit register, valid_mask is changed
5
to uint64_t and the SCR_* constants in target/arm/cpu.h are extended
6
to 64-bit so that masking and bitwise not (~) behave as expected.
7
8
This enables booting Linux with Trusted Firmware-A at EL3 with
9
"-M virt,secure=on -cpu max".
10
11
Cc: qemu-stable@nongnu.org
12
Fixes: 78cb9776662a ("target/arm: Enable SME for -cpu max")
13
Signed-off-by: Jerome Forissier <jerome.forissier@linaro.org>
14
Reviewed-by: Andre Przywara <andre.przywara@arm.com>
15
Reviewed-by: Richard Henderson <richard.henderson@linaro.org>
16
Message-id: 20221004072354.27037-1-jerome.forissier@linaro.org
17
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
18
---
19
target/arm/cpu.h | 54 ++++++++++++++++++++++-----------------------
20
target/arm/helper.c | 5 ++++-
21
2 files changed, 31 insertions(+), 28 deletions(-)
22
23
diff --git a/target/arm/cpu.h b/target/arm/cpu.h
24
index XXXXXXX..XXXXXXX 100644
25
--- a/target/arm/cpu.h
26
+++ b/target/arm/cpu.h
27
@@ -XXX,XX +XXX,XX @@ static inline void xpsr_write(CPUARMState *env, uint32_t val, uint32_t mask)
28
29
#define HPFAR_NS (1ULL << 63)
30
31
-#define SCR_NS (1U << 0)
32
-#define SCR_IRQ (1U << 1)
33
-#define SCR_FIQ (1U << 2)
34
-#define SCR_EA (1U << 3)
35
-#define SCR_FW (1U << 4)
36
-#define SCR_AW (1U << 5)
37
-#define SCR_NET (1U << 6)
38
-#define SCR_SMD (1U << 7)
39
-#define SCR_HCE (1U << 8)
40
-#define SCR_SIF (1U << 9)
41
-#define SCR_RW (1U << 10)
42
-#define SCR_ST (1U << 11)
43
-#define SCR_TWI (1U << 12)
44
-#define SCR_TWE (1U << 13)
45
-#define SCR_TLOR (1U << 14)
46
-#define SCR_TERR (1U << 15)
47
-#define SCR_APK (1U << 16)
48
-#define SCR_API (1U << 17)
49
-#define SCR_EEL2 (1U << 18)
50
-#define SCR_EASE (1U << 19)
51
-#define SCR_NMEA (1U << 20)
52
-#define SCR_FIEN (1U << 21)
53
-#define SCR_ENSCXT (1U << 25)
54
-#define SCR_ATA (1U << 26)
55
-#define SCR_FGTEN (1U << 27)
56
-#define SCR_ECVEN (1U << 28)
57
-#define SCR_TWEDEN (1U << 29)
58
+#define SCR_NS (1ULL << 0)
59
+#define SCR_IRQ (1ULL << 1)
60
+#define SCR_FIQ (1ULL << 2)
61
+#define SCR_EA (1ULL << 3)
62
+#define SCR_FW (1ULL << 4)
63
+#define SCR_AW (1ULL << 5)
64
+#define SCR_NET (1ULL << 6)
65
+#define SCR_SMD (1ULL << 7)
66
+#define SCR_HCE (1ULL << 8)
67
+#define SCR_SIF (1ULL << 9)
68
+#define SCR_RW (1ULL << 10)
69
+#define SCR_ST (1ULL << 11)
70
+#define SCR_TWI (1ULL << 12)
71
+#define SCR_TWE (1ULL << 13)
72
+#define SCR_TLOR (1ULL << 14)
73
+#define SCR_TERR (1ULL << 15)
74
+#define SCR_APK (1ULL << 16)
75
+#define SCR_API (1ULL << 17)
76
+#define SCR_EEL2 (1ULL << 18)
77
+#define SCR_EASE (1ULL << 19)
78
+#define SCR_NMEA (1ULL << 20)
79
+#define SCR_FIEN (1ULL << 21)
80
+#define SCR_ENSCXT (1ULL << 25)
81
+#define SCR_ATA (1ULL << 26)
82
+#define SCR_FGTEN (1ULL << 27)
83
+#define SCR_ECVEN (1ULL << 28)
84
+#define SCR_TWEDEN (1ULL << 29)
85
#define SCR_TWEDEL MAKE_64BIT_MASK(30, 4)
86
#define SCR_TME (1ULL << 34)
87
#define SCR_AMVOFFEN (1ULL << 35)
88
diff --git a/target/arm/helper.c b/target/arm/helper.c
89
index XXXXXXX..XXXXXXX 100644
90
--- a/target/arm/helper.c
91
+++ b/target/arm/helper.c
92
@@ -XXX,XX +XXX,XX @@ static void vbar_write(CPUARMState *env, const ARMCPRegInfo *ri,
93
static void scr_write(CPUARMState *env, const ARMCPRegInfo *ri, uint64_t value)
94
{
95
/* Begin with base v8.0 state. */
96
- uint32_t valid_mask = 0x3fff;
97
+ uint64_t valid_mask = 0x3fff;
98
ARMCPU *cpu = env_archcpu(env);
99
100
/*
101
@@ -XXX,XX +XXX,XX @@ static void scr_write(CPUARMState *env, const ARMCPRegInfo *ri, uint64_t value)
102
if (cpu_isar_feature(aa64_doublefault, cpu)) {
103
valid_mask |= SCR_EASE | SCR_NMEA;
104
}
105
+ if (cpu_isar_feature(aa64_sme, cpu)) {
106
+ valid_mask |= SCR_ENTP2;
107
+ }
108
} else {
109
valid_mask &= ~(SCR_RW | SCR_ST);
110
if (cpu_isar_feature(aa32_ras, cpu)) {
111
--
112
2.25.1
diff view generated by jsdifflib
1
From: Joel Stanley <joel@jms.id.au>
1
From: Joel Stanley <joel@jms.id.au>
2
2
3
This contains the NRF51, and the machine that uses it, the BBC
3
openpower.xyz was retired some time ago. The OpenBMC Jenkins is where
4
micro:bit.
4
images can be found these days.
5
5
6
Reviewed-by: Stefan Hajnoczi <stefanha@redhat.com>
7
Reviewed-by: Peter Maydell <peter.maydell@linaro.org>
8
Signed-off-by: Joel Stanley <joel@jms.id.au>
6
Signed-off-by: Joel Stanley <joel@jms.id.au>
9
Message-id: 20180831220920.27113-2-joel@jms.id.au
7
Reviewed-by: Hao Wu <wuhaotsh@google.com>
8
Reviewed-by: Philippe Mathieu-Daudé <f4bug@amsat.org>
9
Tested-by: Philippe Mathieu-Daudé <f4bug@amsat.org>
10
Message-id: 20221004050042.22681-1-joel@jms.id.au
10
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
11
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
11
---
12
---
12
MAINTAINERS | 8 ++++++++
13
docs/system/arm/nuvoton.rst | 4 ++--
13
1 file changed, 8 insertions(+)
14
1 file changed, 2 insertions(+), 2 deletions(-)
14
15
15
diff --git a/MAINTAINERS b/MAINTAINERS
16
diff --git a/docs/system/arm/nuvoton.rst b/docs/system/arm/nuvoton.rst
16
index XXXXXXX..XXXXXXX 100644
17
index XXXXXXX..XXXXXXX 100644
17
--- a/MAINTAINERS
18
--- a/docs/system/arm/nuvoton.rst
18
+++ b/MAINTAINERS
19
+++ b/docs/system/arm/nuvoton.rst
19
@@ -XXX,XX +XXX,XX @@ F: include/hw/*/*aspeed*
20
@@ -XXX,XX +XXX,XX @@ Boot options
20
F: hw/net/ftgmac100.c
21
21
F: include/hw/net/ftgmac100.h
22
The Nuvoton machines can boot from an OpenBMC firmware image, or directly into
22
23
a kernel using the ``-kernel`` option. OpenBMC images for ``quanta-gsj`` and
23
+NRF51
24
-possibly others can be downloaded from the OpenPOWER jenkins :
24
+M: Joel Stanley <joel@jms.id.au>
25
+possibly others can be downloaded from the OpenBMC jenkins :
25
+L: qemu-arm@nongnu.org
26
26
+S: Maintained
27
- https://openpower.xyz/
27
+F: hw/arm/nrf51_soc.c
28
+ https://jenkins.openbmc.org/
28
+F: hw/arm/microbit.c
29
29
+F: include/hw/arm/nrf51_soc.h
30
The firmware image should be attached as an MTD drive. Example :
30
+
31
31
CRIS Machines
32
-------------
33
Axis Dev88
34
--
32
--
35
2.19.0
33
2.25.1
36
34
37
35
diff view generated by jsdifflib
New patch
1
From: Richard Henderson <richard.henderson@linaro.org>
1
2
3
The starting security state comes with the translation regime,
4
not the current state of arm_is_secure_below_el3().
5
6
Create a new local variable, s2walk_secure, which does not need
7
to be written back to result->attrs.secure -- we compute that
8
value later, after the S2 walk is complete.
9
10
Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
11
Reviewed-by: Peter Maydell <peter.maydell@linaro.org>
12
Message-id: 20221001162318.153420-2-richard.henderson@linaro.org
13
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
14
---
15
target/arm/ptw.c | 18 +++++++++---------
16
1 file changed, 9 insertions(+), 9 deletions(-)
17
18
diff --git a/target/arm/ptw.c b/target/arm/ptw.c
19
index XXXXXXX..XXXXXXX 100644
20
--- a/target/arm/ptw.c
21
+++ b/target/arm/ptw.c
22
@@ -XXX,XX +XXX,XX @@ bool get_phys_addr(CPUARMState *env, target_ulong address,
23
hwaddr ipa;
24
int s1_prot;
25
int ret;
26
- bool ipa_secure;
27
+ bool ipa_secure, s2walk_secure;
28
ARMCacheAttrs cacheattrs1;
29
ARMMMUIdx s2_mmu_idx;
30
bool is_el0;
31
@@ -XXX,XX +XXX,XX @@ bool get_phys_addr(CPUARMState *env, target_ulong address,
32
33
ipa = result->phys;
34
ipa_secure = result->attrs.secure;
35
- if (arm_is_secure_below_el3(env)) {
36
- if (ipa_secure) {
37
- result->attrs.secure = !(env->cp15.vstcr_el2 & VSTCR_SW);
38
- } else {
39
- result->attrs.secure = !(env->cp15.vtcr_el2 & VTCR_NSW);
40
- }
41
+ if (is_secure) {
42
+ /* Select TCR based on the NS bit from the S1 walk. */
43
+ s2walk_secure = !(ipa_secure
44
+ ? env->cp15.vstcr_el2 & VSTCR_SW
45
+ : env->cp15.vtcr_el2 & VTCR_NSW);
46
} else {
47
assert(!ipa_secure);
48
+ s2walk_secure = false;
49
}
50
51
- s2_mmu_idx = (result->attrs.secure
52
+ s2_mmu_idx = (s2walk_secure
53
? ARMMMUIdx_Stage2_S : ARMMMUIdx_Stage2);
54
is_el0 = mmu_idx == ARMMMUIdx_E10_0 || mmu_idx == ARMMMUIdx_SE10_0;
55
56
@@ -XXX,XX +XXX,XX @@ bool get_phys_addr(CPUARMState *env, target_ulong address,
57
result->cacheattrs);
58
59
/* Check if IPA translates to secure or non-secure PA space. */
60
- if (arm_is_secure_below_el3(env)) {
61
+ if (is_secure) {
62
if (ipa_secure) {
63
result->attrs.secure =
64
!(env->cp15.vstcr_el2 & (VSTCR_SA | VSTCR_SW));
65
--
66
2.25.1
diff view generated by jsdifflib
1
From: Cédric Le Goater <clg@kaod.org>
1
From: Richard Henderson <richard.henderson@linaro.org>
2
2
3
The AST2500 evb is shipped with a W25Q256 which has a non volatile bit
3
While the stage2 call to get_phys_addr_lpae should never set
4
to make the chip operate in 4 Byte address mode at power up. This
4
attrs.secure when given a non-secure input, it's just as easy
5
should be an interesting feature to model as it will exercise a bit
5
to make the final update to attrs.secure be unconditional and
6
more the SMC controllers and MMIO execution at boot time.
6
false in the case of non-secure input.
7
7
8
Signed-off-by: Cédric Le Goater <clg@kaod.org>
8
Suggested-by: Peter Maydell <peter.maydell@linaro.org>
9
Message-id: 20180921161939.822-3-clg@kaod.org
9
Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
10
Message-id: 20221007152159.1414065-1-richard.henderson@linaro.org
10
Reviewed-by: Peter Maydell <peter.maydell@linaro.org>
11
Reviewed-by: Peter Maydell <peter.maydell@linaro.org>
11
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
12
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
12
---
13
---
13
hw/arm/aspeed.c | 2 +-
14
target/arm/ptw.c | 21 ++++++++++-----------
14
1 file changed, 1 insertion(+), 1 deletion(-)
15
1 file changed, 10 insertions(+), 11 deletions(-)
15
16
16
diff --git a/hw/arm/aspeed.c b/hw/arm/aspeed.c
17
diff --git a/target/arm/ptw.c b/target/arm/ptw.c
17
index XXXXXXX..XXXXXXX 100644
18
index XXXXXXX..XXXXXXX 100644
18
--- a/hw/arm/aspeed.c
19
--- a/target/arm/ptw.c
19
+++ b/hw/arm/aspeed.c
20
+++ b/target/arm/ptw.c
20
@@ -XXX,XX +XXX,XX @@ static const AspeedBoardConfig aspeed_boards[] = {
21
@@ -XXX,XX +XXX,XX @@ bool get_phys_addr(CPUARMState *env, target_ulong address,
21
[AST2500_EVB] = {
22
result->cacheattrs = combine_cacheattrs(env, cacheattrs1,
22
.soc_name = "ast2500-a1",
23
result->cacheattrs);
23
.hw_strap1 = AST2500_EVB_HW_STRAP1,
24
24
- .fmc_model = "n25q256a",
25
- /* Check if IPA translates to secure or non-secure PA space. */
25
+ .fmc_model = "w25q256",
26
- if (is_secure) {
26
.spi_model = "mx25l25635e",
27
- if (ipa_secure) {
27
.num_cs = 1,
28
- result->attrs.secure =
28
.i2c_init = ast2500_evb_i2c_init,
29
- !(env->cp15.vstcr_el2 & (VSTCR_SA | VSTCR_SW));
30
- } else {
31
- result->attrs.secure =
32
- !((env->cp15.vtcr_el2 & (VTCR_NSA | VTCR_NSW))
33
- || (env->cp15.vstcr_el2 & (VSTCR_SA | VSTCR_SW)));
34
- }
35
- }
36
+ /*
37
+ * Check if IPA translates to secure or non-secure PA space.
38
+ * Note that VSTCR overrides VTCR and {N}SW overrides {N}SA.
39
+ */
40
+ result->attrs.secure =
41
+ (is_secure
42
+ && !(env->cp15.vstcr_el2 & (VSTCR_SA | VSTCR_SW))
43
+ && (ipa_secure
44
+ || !(env->cp15.vtcr_el2 & (VTCR_NSA | VTCR_NSW))));
45
+
46
return 0;
47
} else {
48
/*
29
--
49
--
30
2.19.0
50
2.25.1
31
32
diff view generated by jsdifflib
1
The GIC_BASE_IRQ macro is a leftover from when we shared code
1
From: Richard Henderson <richard.henderson@linaro.org>
2
between the GICv2 and the v7M NVIC. Since the NVIC is now
3
split off, GIC_BASE_IRQ is always 0, and we can just delete it.
4
2
3
Remove the use of regime_is_secure from get_phys_addr_lpae,
4
using the new parameter instead.
5
6
Reviewed-by: Alex Bennée <alex.bennee@linaro.org>
7
Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
8
Message-id: 20221001162318.153420-3-richard.henderson@linaro.org
5
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
9
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
6
Reviewed-by: Philippe Mathieu-Daudé <f4bug@amsat.org>
7
Reviewed-by: Luc Michel <luc.michel@greensocs.com>
8
Message-id: 20180824161819.11085-1-peter.maydell@linaro.org
9
---
10
---
10
hw/intc/gic_internal.h | 2 --
11
target/arm/ptw.c | 20 ++++++++++----------
11
hw/intc/arm_gic.c | 31 ++++++++++++++-----------------
12
1 file changed, 10 insertions(+), 10 deletions(-)
12
hw/intc/arm_gic_common.c | 1 -
13
3 files changed, 14 insertions(+), 20 deletions(-)
14
13
15
diff --git a/hw/intc/gic_internal.h b/hw/intc/gic_internal.h
14
diff --git a/target/arm/ptw.c b/target/arm/ptw.c
16
index XXXXXXX..XXXXXXX 100644
15
index XXXXXXX..XXXXXXX 100644
17
--- a/hw/intc/gic_internal.h
16
--- a/target/arm/ptw.c
18
+++ b/hw/intc/gic_internal.h
17
+++ b/target/arm/ptw.c
19
@@ -XXX,XX +XXX,XX @@
18
@@ -XXX,XX +XXX,XX @@
20
19
21
#define ALL_CPU_MASK ((unsigned)(((1 << GIC_NCPU) - 1)))
20
static bool get_phys_addr_lpae(CPUARMState *env, uint64_t address,
22
21
MMUAccessType access_type, ARMMMUIdx mmu_idx,
23
-#define GIC_BASE_IRQ 0
22
- bool s1_is_el0, GetPhysAddrResult *result,
24
-
23
- ARMMMUFaultInfo *fi)
25
#define GIC_DIST_SET_ENABLED(irq, cm) (s->irq_state[irq].enabled |= (cm))
24
+ bool is_secure, bool s1_is_el0,
26
#define GIC_DIST_CLEAR_ENABLED(irq, cm) (s->irq_state[irq].enabled &= ~(cm))
25
+ GetPhysAddrResult *result, ARMMMUFaultInfo *fi)
27
#define GIC_DIST_TEST_ENABLED(irq, cm) ((s->irq_state[irq].enabled & (cm)) != 0)
26
__attribute__((nonnull));
28
diff --git a/hw/intc/arm_gic.c b/hw/intc/arm_gic.c
27
29
index XXXXXXX..XXXXXXX 100644
28
/* This mapping is common between ID_AA64MMFR0.PARANGE and TCR_ELx.{I}PS. */
30
--- a/hw/intc/arm_gic.c
29
@@ -XXX,XX +XXX,XX @@ static hwaddr S1_ptw_translate(CPUARMState *env, ARMMMUIdx mmu_idx,
31
+++ b/hw/intc/arm_gic.c
30
GetPhysAddrResult s2 = {};
32
@@ -XXX,XX +XXX,XX @@ static uint32_t gic_dist_readb(void *opaque, hwaddr offset, MemTxAttrs attrs)
31
int ret;
33
res = 0;
32
34
if (!(s->security_extn && !attrs.secure) && gic_has_groups(s)) {
33
- ret = get_phys_addr_lpae(env, addr, MMU_DATA_LOAD, s2_mmu_idx, false,
35
/* Every byte offset holds 8 group status bits */
34
- &s2, fi);
36
- irq = (offset - 0x080) * 8 + GIC_BASE_IRQ;
35
+ ret = get_phys_addr_lpae(env, addr, MMU_DATA_LOAD, s2_mmu_idx,
37
+ irq = (offset - 0x080) * 8;
36
+ *is_secure, false, &s2, fi);
38
if (irq >= s->num_irq) {
37
if (ret) {
39
goto bad_reg;
38
assert(fi->type != ARMFault_None);
40
}
39
fi->s2addr = addr;
41
@@ -XXX,XX +XXX,XX @@ static uint32_t gic_dist_readb(void *opaque, hwaddr offset, MemTxAttrs attrs)
40
@@ -XXX,XX +XXX,XX @@ static bool check_s2_mmu_setup(ARMCPU *cpu, bool is_aa64, int level,
42
irq = (offset - 0x100) * 8;
41
*/
43
else
42
static bool get_phys_addr_lpae(CPUARMState *env, uint64_t address,
44
irq = (offset - 0x180) * 8;
43
MMUAccessType access_type, ARMMMUIdx mmu_idx,
45
- irq += GIC_BASE_IRQ;
44
- bool s1_is_el0, GetPhysAddrResult *result,
46
if (irq >= s->num_irq)
45
- ARMMMUFaultInfo *fi)
47
goto bad_reg;
46
+ bool is_secure, bool s1_is_el0,
48
res = 0;
47
+ GetPhysAddrResult *result, ARMMMUFaultInfo *fi)
49
@@ -XXX,XX +XXX,XX @@ static uint32_t gic_dist_readb(void *opaque, hwaddr offset, MemTxAttrs attrs)
48
{
50
irq = (offset - 0x200) * 8;
49
ARMCPU *cpu = env_archcpu(env);
51
else
50
/* Read an LPAE long-descriptor translation table. */
52
irq = (offset - 0x280) * 8;
51
@@ -XXX,XX +XXX,XX @@ static bool get_phys_addr_lpae(CPUARMState *env, uint64_t address,
53
- irq += GIC_BASE_IRQ;
52
* remain non-secure. We implement this by just ORing in the NSTable/NS
54
if (irq >= s->num_irq)
53
* bits at each step.
55
goto bad_reg;
54
*/
56
res = 0;
55
- tableattrs = regime_is_secure(env, mmu_idx) ? 0 : (1 << 4);
57
@@ -XXX,XX +XXX,XX @@ static uint32_t gic_dist_readb(void *opaque, hwaddr offset, MemTxAttrs attrs)
56
+ tableattrs = is_secure ? 0 : (1 << 4);
58
goto bad_reg;
57
for (;;) {
59
}
58
uint64_t descriptor;
60
59
bool nstable;
61
- irq += GIC_BASE_IRQ;
60
@@ -XXX,XX +XXX,XX @@ bool get_phys_addr(CPUARMState *env, target_ulong address,
62
if (irq >= s->num_irq)
61
memset(result, 0, sizeof(*result));
63
goto bad_reg;
62
64
res = 0;
63
ret = get_phys_addr_lpae(env, ipa, access_type, s2_mmu_idx,
65
@@ -XXX,XX +XXX,XX @@ static uint32_t gic_dist_readb(void *opaque, hwaddr offset, MemTxAttrs attrs)
64
- is_el0, result, fi);
66
}
65
+ s2walk_secure, is_el0, result, fi);
67
} else if (offset < 0x800) {
66
fi->s2addr = ipa;
68
/* Interrupt Priority. */
67
69
- irq = (offset - 0x400) + GIC_BASE_IRQ;
68
/* Combine the S1 and S2 perms. */
70
+ irq = (offset - 0x400);
69
@@ -XXX,XX +XXX,XX @@ bool get_phys_addr(CPUARMState *env, target_ulong address,
71
if (irq >= s->num_irq)
72
goto bad_reg;
73
res = gic_dist_get_priority(s, cpu, irq, attrs);
74
@@ -XXX,XX +XXX,XX @@ static uint32_t gic_dist_readb(void *opaque, hwaddr offset, MemTxAttrs attrs)
75
/* For uniprocessor GICs these RAZ/WI */
76
res = 0;
77
} else {
78
- irq = (offset - 0x800) + GIC_BASE_IRQ;
79
+ irq = (offset - 0x800);
80
if (irq >= s->num_irq) {
81
goto bad_reg;
82
}
83
@@ -XXX,XX +XXX,XX @@ static uint32_t gic_dist_readb(void *opaque, hwaddr offset, MemTxAttrs attrs)
84
}
85
} else if (offset < 0xf00) {
86
/* Interrupt Configuration. */
87
- irq = (offset - 0xc00) * 4 + GIC_BASE_IRQ;
88
+ irq = (offset - 0xc00) * 4;
89
if (irq >= s->num_irq)
90
goto bad_reg;
91
res = 0;
92
@@ -XXX,XX +XXX,XX @@ static void gic_dist_writeb(void *opaque, hwaddr offset,
93
*/
94
if (!(s->security_extn && !attrs.secure) && gic_has_groups(s)) {
95
/* Every byte offset holds 8 group status bits */
96
- irq = (offset - 0x80) * 8 + GIC_BASE_IRQ;
97
+ irq = (offset - 0x80) * 8;
98
if (irq >= s->num_irq) {
99
goto bad_reg;
100
}
101
@@ -XXX,XX +XXX,XX @@ static void gic_dist_writeb(void *opaque, hwaddr offset,
102
}
103
} else if (offset < 0x180) {
104
/* Interrupt Set Enable. */
105
- irq = (offset - 0x100) * 8 + GIC_BASE_IRQ;
106
+ irq = (offset - 0x100) * 8;
107
if (irq >= s->num_irq)
108
goto bad_reg;
109
if (irq < GIC_NR_SGIS) {
110
@@ -XXX,XX +XXX,XX @@ static void gic_dist_writeb(void *opaque, hwaddr offset,
111
}
112
} else if (offset < 0x200) {
113
/* Interrupt Clear Enable. */
114
- irq = (offset - 0x180) * 8 + GIC_BASE_IRQ;
115
+ irq = (offset - 0x180) * 8;
116
if (irq >= s->num_irq)
117
goto bad_reg;
118
if (irq < GIC_NR_SGIS) {
119
@@ -XXX,XX +XXX,XX @@ static void gic_dist_writeb(void *opaque, hwaddr offset,
120
}
121
} else if (offset < 0x280) {
122
/* Interrupt Set Pending. */
123
- irq = (offset - 0x200) * 8 + GIC_BASE_IRQ;
124
+ irq = (offset - 0x200) * 8;
125
if (irq >= s->num_irq)
126
goto bad_reg;
127
if (irq < GIC_NR_SGIS) {
128
@@ -XXX,XX +XXX,XX @@ static void gic_dist_writeb(void *opaque, hwaddr offset,
129
}
130
} else if (offset < 0x300) {
131
/* Interrupt Clear Pending. */
132
- irq = (offset - 0x280) * 8 + GIC_BASE_IRQ;
133
+ irq = (offset - 0x280) * 8;
134
if (irq >= s->num_irq)
135
goto bad_reg;
136
if (irq < GIC_NR_SGIS) {
137
@@ -XXX,XX +XXX,XX @@ static void gic_dist_writeb(void *opaque, hwaddr offset,
138
goto bad_reg;
139
}
140
141
- irq = (offset - 0x300) * 8 + GIC_BASE_IRQ;
142
+ irq = (offset - 0x300) * 8;
143
if (irq >= s->num_irq) {
144
goto bad_reg;
145
}
146
@@ -XXX,XX +XXX,XX @@ static void gic_dist_writeb(void *opaque, hwaddr offset,
147
goto bad_reg;
148
}
149
150
- irq = (offset - 0x380) * 8 + GIC_BASE_IRQ;
151
+ irq = (offset - 0x380) * 8;
152
if (irq >= s->num_irq) {
153
goto bad_reg;
154
}
155
@@ -XXX,XX +XXX,XX @@ static void gic_dist_writeb(void *opaque, hwaddr offset,
156
}
157
} else if (offset < 0x800) {
158
/* Interrupt Priority. */
159
- irq = (offset - 0x400) + GIC_BASE_IRQ;
160
+ irq = (offset - 0x400);
161
if (irq >= s->num_irq)
162
goto bad_reg;
163
gic_dist_set_priority(s, cpu, irq, value, attrs);
164
@@ -XXX,XX +XXX,XX @@ static void gic_dist_writeb(void *opaque, hwaddr offset,
165
* annoying exception of the 11MPCore's GIC.
166
*/
167
if (s->num_cpu != 1 || s->revision == REV_11MPCORE) {
168
- irq = (offset - 0x800) + GIC_BASE_IRQ;
169
+ irq = (offset - 0x800);
170
if (irq >= s->num_irq) {
171
goto bad_reg;
172
}
173
@@ -XXX,XX +XXX,XX @@ static void gic_dist_writeb(void *opaque, hwaddr offset,
174
}
175
} else if (offset < 0xf00) {
176
/* Interrupt Configuration. */
177
- irq = (offset - 0xc00) * 4 + GIC_BASE_IRQ;
178
+ irq = (offset - 0xc00) * 4;
179
if (irq >= s->num_irq)
180
goto bad_reg;
181
if (irq < GIC_NR_SGIS)
182
diff --git a/hw/intc/arm_gic_common.c b/hw/intc/arm_gic_common.c
183
index XXXXXXX..XXXXXXX 100644
184
--- a/hw/intc/arm_gic_common.c
185
+++ b/hw/intc/arm_gic_common.c
186
@@ -XXX,XX +XXX,XX @@ static void arm_gic_common_realize(DeviceState *dev, Error **errp)
187
s->num_cpu, GIC_NCPU);
188
return;
189
}
70
}
190
- s->num_irq += GIC_BASE_IRQ;
71
191
if (s->num_irq > GIC_MAXIRQ) {
72
if (regime_using_lpae_format(env, mmu_idx)) {
192
error_setg(errp,
73
- return get_phys_addr_lpae(env, address, access_type, mmu_idx, false,
193
"requested %u interrupt lines exceeds GIC maximum %d",
74
- result, fi);
75
+ return get_phys_addr_lpae(env, address, access_type, mmu_idx,
76
+ is_secure, false, result, fi);
77
} else if (regime_sctlr(env, mmu_idx) & SCTLR_XP) {
78
return get_phys_addr_v6(env, address, access_type, mmu_idx,
79
is_secure, result, fi);
194
--
80
--
195
2.19.0
81
2.25.1
196
82
197
83
diff view generated by jsdifflib
1
From: Eric Auger <eric.auger@redhat.com>
1
From: Richard Henderson <richard.henderson@linaro.org>
2
2
3
At the point smmu_find_add_as() gets called, the bus number might
3
Pass the correct stage2 mmu_idx to regime_translation_disabled,
4
not be computed. Let's change the name of IOMMU memory region and
4
which we computed afterward.
5
just use the devfn and an incrementing index.
6
5
7
The name only is used for debug.
6
Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
8
9
Signed-off-by: Eric Auger <eric.auger@redhat.com>
10
Message-id: 20180921070138.10114-2-eric.auger@redhat.com
11
Reviewed-by: Peter Maydell <peter.maydell@linaro.org>
7
Reviewed-by: Peter Maydell <peter.maydell@linaro.org>
8
Message-id: 20221001162318.153420-4-richard.henderson@linaro.org
12
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
9
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
13
---
10
---
14
hw/arm/smmu-common.c | 6 +++---
11
target/arm/ptw.c | 6 +++---
15
1 file changed, 3 insertions(+), 3 deletions(-)
12
1 file changed, 3 insertions(+), 3 deletions(-)
16
13
17
diff --git a/hw/arm/smmu-common.c b/hw/arm/smmu-common.c
14
diff --git a/target/arm/ptw.c b/target/arm/ptw.c
18
index XXXXXXX..XXXXXXX 100644
15
index XXXXXXX..XXXXXXX 100644
19
--- a/hw/arm/smmu-common.c
16
--- a/target/arm/ptw.c
20
+++ b/hw/arm/smmu-common.c
17
+++ b/target/arm/ptw.c
21
@@ -XXX,XX +XXX,XX @@ static AddressSpace *smmu_find_add_as(PCIBus *bus, void *opaque, int devfn)
18
@@ -XXX,XX +XXX,XX @@ static hwaddr S1_ptw_translate(CPUARMState *env, ARMMMUIdx mmu_idx,
22
SMMUState *s = opaque;
19
hwaddr addr, bool *is_secure,
23
SMMUPciBus *sbus = g_hash_table_lookup(s->smmu_pcibus_by_busptr, bus);
20
ARMMMUFaultInfo *fi)
24
SMMUDevice *sdev;
21
{
25
+ static uint index;
22
+ ARMMMUIdx s2_mmu_idx = *is_secure ? ARMMMUIdx_Stage2_S : ARMMMUIdx_Stage2;
26
27
if (!sbus) {
28
sbus = g_malloc0(sizeof(SMMUPciBus) +
29
@@ -XXX,XX +XXX,XX @@ static AddressSpace *smmu_find_add_as(PCIBus *bus, void *opaque, int devfn)
30
31
sdev = sbus->pbdev[devfn];
32
if (!sdev) {
33
- char *name = g_strdup_printf("%s-%d-%d",
34
- s->mrtypename,
35
- pci_bus_num(bus), devfn);
36
+ char *name = g_strdup_printf("%s-%d-%d", s->mrtypename, devfn, index++);
37
+
23
+
38
sdev = sbus->pbdev[devfn] = g_new0(SMMUDevice, 1);
24
if (arm_mmu_idx_is_stage1_of_2(mmu_idx) &&
39
25
- !regime_translation_disabled(env, ARMMMUIdx_Stage2)) {
40
sdev->smmu = s;
26
- ARMMMUIdx s2_mmu_idx = *is_secure ? ARMMMUIdx_Stage2_S
27
- : ARMMMUIdx_Stage2;
28
+ !regime_translation_disabled(env, s2_mmu_idx)) {
29
GetPhysAddrResult s2 = {};
30
int ret;
31
41
--
32
--
42
2.19.0
33
2.25.1
43
44
diff view generated by jsdifflib
1
The GICv2's QEMU interface (sysbus MMIO regions, IRQs,
1
From: Richard Henderson <richard.henderson@linaro.org>
2
etc) is now quite complicated with the addition of the
3
virtualization extensions. Add a comment in the header
4
file which documents it.
5
2
3
Remove the use of regime_is_secure from regime_translation_disabled,
4
using the new parameter instead.
5
6
This fixes a bug in S1_ptw_translate and get_phys_addr where we had
7
passed ARMMMUIdx_Stage2 and not ARMMMUIdx_Stage2_S to determine if
8
Stage2 is disabled, affecting FEAT_SEL2.
9
10
Reviewed-by: Peter Maydell <peter.maydell@linaro.org>
11
Reviewed-by: Alex Bennée <alex.bennee@linaro.org>
12
Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
13
Message-id: 20221001162318.153420-5-richard.henderson@linaro.org
6
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
14
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
7
Reviewed-by: Luc Michel <luc.michel@greensocs.com>
8
Message-id: 20180823103818.31189-1-peter.maydell@linaro.org
9
---
15
---
10
include/hw/intc/arm_gic.h | 43 +++++++++++++++++++++++++++++++++++++++
16
target/arm/ptw.c | 20 +++++++++++---------
11
1 file changed, 43 insertions(+)
17
1 file changed, 11 insertions(+), 9 deletions(-)
12
18
13
diff --git a/include/hw/intc/arm_gic.h b/include/hw/intc/arm_gic.h
19
diff --git a/target/arm/ptw.c b/target/arm/ptw.c
14
index XXXXXXX..XXXXXXX 100644
20
index XXXXXXX..XXXXXXX 100644
15
--- a/include/hw/intc/arm_gic.h
21
--- a/target/arm/ptw.c
16
+++ b/include/hw/intc/arm_gic.h
22
+++ b/target/arm/ptw.c
17
@@ -XXX,XX +XXX,XX @@
23
@@ -XXX,XX +XXX,XX @@ static uint64_t regime_ttbr(CPUARMState *env, ARMMMUIdx mmu_idx, int ttbrn)
18
* with this program; if not, see <http://www.gnu.org/licenses/>.
24
}
19
*/
25
20
26
/* Return true if the specified stage of address translation is disabled */
21
+/*
27
-static bool regime_translation_disabled(CPUARMState *env, ARMMMUIdx mmu_idx)
22
+ * QEMU interface:
28
+static bool regime_translation_disabled(CPUARMState *env, ARMMMUIdx mmu_idx,
23
+ * + QOM property "num-cpu": number of CPUs to support
29
+ bool is_secure)
24
+ * + QOM property "num-irq": number of IRQs (including both SPIs and PPIs)
30
{
25
+ * + QOM property "revision": GIC version (1 or 2), or 0 for the 11MPCore GIC
31
uint64_t hcr_el2;
26
+ * + QOM property "has-security-extensions": set true if the GIC should
32
27
+ * implement the security extensions
33
if (arm_feature(env, ARM_FEATURE_M)) {
28
+ * + QOM property "has-virtualization-extensions": set true if the GIC should
34
- switch (env->v7m.mpu_ctrl[regime_is_secure(env, mmu_idx)] &
29
+ * implement the virtualization extensions
35
+ switch (env->v7m.mpu_ctrl[is_secure] &
30
+ * + unnamed GPIO inputs: (where P is number of SPIs, i.e. num-irq - 32)
36
(R_V7M_MPU_CTRL_ENABLE_MASK | R_V7M_MPU_CTRL_HFNMIENA_MASK)) {
31
+ * [0..P-1] SPIs
37
case R_V7M_MPU_CTRL_ENABLE_MASK:
32
+ * [P..P+31] PPIs for CPU 0
38
/* Enabled, but not for HardFault and NMI */
33
+ * [P+32..P+63] PPIs for CPU 1
39
@@ -XXX,XX +XXX,XX @@ static bool regime_translation_disabled(CPUARMState *env, ARMMMUIdx mmu_idx)
34
+ * ...
40
35
+ * + sysbus IRQs: (in order; number will vary depending on number of cores)
41
if (hcr_el2 & HCR_TGE) {
36
+ * - IRQ for CPU 0
42
/* TGE means that NS EL0/1 act as if SCTLR_EL1.M is zero */
37
+ * - IRQ for CPU 1
43
- if (!regime_is_secure(env, mmu_idx) && regime_el(env, mmu_idx) == 1) {
38
+ * ...
44
+ if (!is_secure && regime_el(env, mmu_idx) == 1) {
39
+ * - FIQ for CPU 0
45
return true;
40
+ * - FIQ for CPU 1
46
}
41
+ * ...
47
}
42
+ * - VIRQ for CPU 0 (exists even if virt extensions not present)
48
@@ -XXX,XX +XXX,XX @@ static hwaddr S1_ptw_translate(CPUARMState *env, ARMMMUIdx mmu_idx,
43
+ * - VIRQ for CPU 1 (exists even if virt extensions not present)
49
ARMMMUIdx s2_mmu_idx = *is_secure ? ARMMMUIdx_Stage2_S : ARMMMUIdx_Stage2;
44
+ * ...
50
45
+ * - VFIQ for CPU 0 (exists even if virt extensions not present)
51
if (arm_mmu_idx_is_stage1_of_2(mmu_idx) &&
46
+ * - VFIQ for CPU 1 (exists even if virt extensions not present)
52
- !regime_translation_disabled(env, s2_mmu_idx)) {
47
+ * ...
53
+ !regime_translation_disabled(env, s2_mmu_idx, *is_secure)) {
48
+ * - maintenance IRQ for CPU i/f 0 (only if virt extensions present)
54
GetPhysAddrResult s2 = {};
49
+ * - maintenance IRQ for CPU i/f 1 (only if virt extensions present)
55
int ret;
50
+ * + sysbus MMIO regions: (in order; numbers will vary depending on
56
51
+ * whether virtualization extensions are present and on number of cores)
57
@@ -XXX,XX +XXX,XX @@ static bool get_phys_addr_pmsav5(CPUARMState *env, uint32_t address,
52
+ * - distributor registers (GICD*)
58
uint32_t base;
53
+ * - CPU interface for the accessing core (GICC*)
59
bool is_user = regime_is_user(env, mmu_idx);
54
+ * - virtual interface control registers (GICH*) (only if virt extns present)
60
55
+ * - virtual CPU interface for the accessing core (GICV*) (only if virt)
61
- if (regime_translation_disabled(env, mmu_idx)) {
56
+ * - CPU 0 CPU interface registers
62
+ if (regime_translation_disabled(env, mmu_idx, is_secure)) {
57
+ * - CPU 1 CPU interface registers
63
/* MPU disabled. */
58
+ * ...
64
result->phys = address;
59
+ * - CPU 0 virtual interface control registers (only if virt extns present)
65
result->prot = PAGE_READ | PAGE_WRITE | PAGE_EXEC;
60
+ * - CPU 1 virtual interface control registers (only if virt extns present)
66
@@ -XXX,XX +XXX,XX @@ static bool get_phys_addr_pmsav7(CPUARMState *env, uint32_t address,
61
+ * ...
67
result->page_size = TARGET_PAGE_SIZE;
62
+ */
68
result->prot = 0;
63
+
69
64
#ifndef HW_ARM_GIC_H
70
- if (regime_translation_disabled(env, mmu_idx) ||
65
#define HW_ARM_GIC_H
71
+ if (regime_translation_disabled(env, mmu_idx, secure) ||
72
m_is_ppb_region(env, address)) {
73
/*
74
* MPU disabled or M profile PPB access: use default memory map.
75
@@ -XXX,XX +XXX,XX @@ bool pmsav8_mpu_lookup(CPUARMState *env, uint32_t address,
76
* are done in arm_v7m_load_vector(), which always does a direct
77
* read using address_space_ldl(), rather than going via this function.
78
*/
79
- if (regime_translation_disabled(env, mmu_idx)) { /* MPU disabled */
80
+ if (regime_translation_disabled(env, mmu_idx, secure)) { /* MPU disabled */
81
hit = true;
82
} else if (m_is_ppb_region(env, address)) {
83
hit = true;
84
@@ -XXX,XX +XXX,XX @@ bool get_phys_addr(CPUARMState *env, target_ulong address,
85
result, fi);
86
87
/* If S1 fails or S2 is disabled, return early. */
88
- if (ret || regime_translation_disabled(env, ARMMMUIdx_Stage2)) {
89
+ if (ret || regime_translation_disabled(env, ARMMMUIdx_Stage2,
90
+ is_secure)) {
91
return ret;
92
}
93
94
@@ -XXX,XX +XXX,XX @@ bool get_phys_addr(CPUARMState *env, target_ulong address,
95
96
/* Definitely a real MMU, not an MPU */
97
98
- if (regime_translation_disabled(env, mmu_idx)) {
99
+ if (regime_translation_disabled(env, mmu_idx, is_secure)) {
100
uint64_t hcr;
101
uint8_t memattr;
66
102
67
--
103
--
68
2.19.0
104
2.25.1
69
105
70
106
diff view generated by jsdifflib
New patch
1
From: Richard Henderson <richard.henderson@linaro.org>
1
2
3
Retain the existing get_phys_addr interface using the security
4
state derived from mmu_idx. Move the kerneldoc comments to the
5
header file where they belong.
6
7
Reviewed-by: Peter Maydell <peter.maydell@linaro.org>
8
Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
9
Message-id: 20221001162318.153420-6-richard.henderson@linaro.org
10
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
11
---
12
target/arm/internals.h | 40 ++++++++++++++++++++++++++++++++++++++
13
target/arm/ptw.c | 44 ++++++++++++++----------------------------
14
2 files changed, 55 insertions(+), 29 deletions(-)
15
16
diff --git a/target/arm/internals.h b/target/arm/internals.h
17
index XXXXXXX..XXXXXXX 100644
18
--- a/target/arm/internals.h
19
+++ b/target/arm/internals.h
20
@@ -XXX,XX +XXX,XX @@ typedef struct GetPhysAddrResult {
21
ARMCacheAttrs cacheattrs;
22
} GetPhysAddrResult;
23
24
+/**
25
+ * get_phys_addr_with_secure: get the physical address for a virtual address
26
+ * @env: CPUARMState
27
+ * @address: virtual address to get physical address for
28
+ * @access_type: 0 for read, 1 for write, 2 for execute
29
+ * @mmu_idx: MMU index indicating required translation regime
30
+ * @is_secure: security state for the access
31
+ * @result: set on translation success.
32
+ * @fi: set to fault info if the translation fails
33
+ *
34
+ * Find the physical address corresponding to the given virtual address,
35
+ * by doing a translation table walk on MMU based systems or using the
36
+ * MPU state on MPU based systems.
37
+ *
38
+ * Returns false if the translation was successful. Otherwise, phys_ptr, attrs,
39
+ * prot and page_size may not be filled in, and the populated fsr value provides
40
+ * information on why the translation aborted, in the format of a
41
+ * DFSR/IFSR fault register, with the following caveats:
42
+ * * we honour the short vs long DFSR format differences.
43
+ * * the WnR bit is never set (the caller must do this).
44
+ * * for PSMAv5 based systems we don't bother to return a full FSR format
45
+ * value.
46
+ */
47
+bool get_phys_addr_with_secure(CPUARMState *env, target_ulong address,
48
+ MMUAccessType access_type,
49
+ ARMMMUIdx mmu_idx, bool is_secure,
50
+ GetPhysAddrResult *result, ARMMMUFaultInfo *fi)
51
+ __attribute__((nonnull));
52
+
53
+/**
54
+ * get_phys_addr: get the physical address for a virtual address
55
+ * @env: CPUARMState
56
+ * @address: virtual address to get physical address for
57
+ * @access_type: 0 for read, 1 for write, 2 for execute
58
+ * @mmu_idx: MMU index indicating required translation regime
59
+ * @result: set on translation success.
60
+ * @fi: set to fault info if the translation fails
61
+ *
62
+ * Similarly, but use the security regime of @mmu_idx.
63
+ */
64
bool get_phys_addr(CPUARMState *env, target_ulong address,
65
MMUAccessType access_type, ARMMMUIdx mmu_idx,
66
GetPhysAddrResult *result, ARMMMUFaultInfo *fi)
67
diff --git a/target/arm/ptw.c b/target/arm/ptw.c
68
index XXXXXXX..XXXXXXX 100644
69
--- a/target/arm/ptw.c
70
+++ b/target/arm/ptw.c
71
@@ -XXX,XX +XXX,XX @@ static ARMCacheAttrs combine_cacheattrs(CPUARMState *env,
72
return ret;
73
}
74
75
-/**
76
- * get_phys_addr - get the physical address for this virtual address
77
- *
78
- * Find the physical address corresponding to the given virtual address,
79
- * by doing a translation table walk on MMU based systems or using the
80
- * MPU state on MPU based systems.
81
- *
82
- * Returns false if the translation was successful. Otherwise, phys_ptr, attrs,
83
- * prot and page_size may not be filled in, and the populated fsr value provides
84
- * information on why the translation aborted, in the format of a
85
- * DFSR/IFSR fault register, with the following caveats:
86
- * * we honour the short vs long DFSR format differences.
87
- * * the WnR bit is never set (the caller must do this).
88
- * * for PSMAv5 based systems we don't bother to return a full FSR format
89
- * value.
90
- *
91
- * @env: CPUARMState
92
- * @address: virtual address to get physical address for
93
- * @access_type: 0 for read, 1 for write, 2 for execute
94
- * @mmu_idx: MMU index indicating required translation regime
95
- * @result: set on translation success.
96
- * @fi: set to fault info if the translation fails
97
- */
98
-bool get_phys_addr(CPUARMState *env, target_ulong address,
99
- MMUAccessType access_type, ARMMMUIdx mmu_idx,
100
- GetPhysAddrResult *result, ARMMMUFaultInfo *fi)
101
+bool get_phys_addr_with_secure(CPUARMState *env, target_ulong address,
102
+ MMUAccessType access_type, ARMMMUIdx mmu_idx,
103
+ bool is_secure, GetPhysAddrResult *result,
104
+ ARMMMUFaultInfo *fi)
105
{
106
ARMMMUIdx s1_mmu_idx = stage_1_mmu_idx(mmu_idx);
107
- bool is_secure = regime_is_secure(env, mmu_idx);
108
109
if (mmu_idx != s1_mmu_idx) {
110
/*
111
@@ -XXX,XX +XXX,XX @@ bool get_phys_addr(CPUARMState *env, target_ulong address,
112
ARMMMUIdx s2_mmu_idx;
113
bool is_el0;
114
115
- ret = get_phys_addr(env, address, access_type, s1_mmu_idx,
116
- result, fi);
117
+ ret = get_phys_addr_with_secure(env, address, access_type,
118
+ s1_mmu_idx, is_secure, result, fi);
119
120
/* If S1 fails or S2 is disabled, return early. */
121
if (ret || regime_translation_disabled(env, ARMMMUIdx_Stage2,
122
@@ -XXX,XX +XXX,XX @@ bool get_phys_addr(CPUARMState *env, target_ulong address,
123
}
124
}
125
126
+bool get_phys_addr(CPUARMState *env, target_ulong address,
127
+ MMUAccessType access_type, ARMMMUIdx mmu_idx,
128
+ GetPhysAddrResult *result, ARMMMUFaultInfo *fi)
129
+{
130
+ return get_phys_addr_with_secure(env, address, access_type, mmu_idx,
131
+ regime_is_secure(env, mmu_idx),
132
+ result, fi);
133
+}
134
+
135
hwaddr arm_cpu_get_phys_page_attrs_debug(CPUState *cs, vaddr addr,
136
MemTxAttrs *attrs)
137
{
138
--
139
2.25.1
diff view generated by jsdifflib
1
From: Guenter Roeck <linux@roeck-us.net>
1
From: Richard Henderson <richard.henderson@linaro.org>
2
2
3
The AST2500 datasheet says:
3
Remove the use of regime_is_secure from v7m_read_half_insn, using
4
the new parameter instead.
4
5
5
I2CD10 Interrupt Status Register
6
As it happens, both callers pass true, propagated from the argument
6
bit 2 Receive Done Interrupt status
7
to arm_v7m_mmu_idx_for_secstate which created the mmu_idx argument,
7
S/W needs to clear this status bit to allow next data receiving
8
but that is a detail of v7m_handle_execute_nsc we need not expose
9
to the callee.
8
10
9
The Rx interrupt done interrupt status bit needs to be cleared
11
Reviewed-by: Peter Maydell <peter.maydell@linaro.org>
10
explicitly before the next byte can be received, and must therefore
12
Reviewed-by: Alex Bennée <alex.bennee@linaro.org>
11
not be auto-cleared. Also, receiving the next byte must be delayed
13
Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
12
until the bit has been cleared.
14
Message-id: 20221001162318.153420-7-richard.henderson@linaro.org
13
14
Signed-off-by: Guenter Roeck <linux@roeck-us.net>
15
Signed-off-by: Cédric Le Goater <clg@kaod.org>
16
Message-id: 20180914063506.20815-4-clg@kaod.org
17
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
15
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
18
---
16
---
19
hw/i2c/aspeed_i2c.c | 10 +++++++++-
17
target/arm/m_helper.c | 9 ++++-----
20
1 file changed, 9 insertions(+), 1 deletion(-)
18
1 file changed, 4 insertions(+), 5 deletions(-)
21
19
22
diff --git a/hw/i2c/aspeed_i2c.c b/hw/i2c/aspeed_i2c.c
20
diff --git a/target/arm/m_helper.c b/target/arm/m_helper.c
23
index XXXXXXX..XXXXXXX 100644
21
index XXXXXXX..XXXXXXX 100644
24
--- a/hw/i2c/aspeed_i2c.c
22
--- a/target/arm/m_helper.c
25
+++ b/hw/i2c/aspeed_i2c.c
23
+++ b/target/arm/m_helper.c
26
@@ -XXX,XX +XXX,XX @@ static void aspeed_i2c_bus_handle_cmd(AspeedI2CBus *bus, uint64_t value)
24
@@ -XXX,XX +XXX,XX @@ static bool do_v7m_function_return(ARMCPU *cpu)
27
aspeed_i2c_set_state(bus, I2CD_MACTIVE);
25
return true;
26
}
27
28
-static bool v7m_read_half_insn(ARMCPU *cpu, ARMMMUIdx mmu_idx,
29
+static bool v7m_read_half_insn(ARMCPU *cpu, ARMMMUIdx mmu_idx, bool secure,
30
uint32_t addr, uint16_t *insn)
31
{
32
/*
33
@@ -XXX,XX +XXX,XX @@ static bool v7m_read_half_insn(ARMCPU *cpu, ARMMMUIdx mmu_idx,
34
ARMMMUFaultInfo fi = {};
35
MemTxResult txres;
36
37
- v8m_security_lookup(env, addr, MMU_INST_FETCH, mmu_idx,
38
- regime_is_secure(env, mmu_idx), &sattrs);
39
+ v8m_security_lookup(env, addr, MMU_INST_FETCH, mmu_idx, secure, &sattrs);
40
if (!sattrs.nsc || sattrs.ns) {
41
/*
42
* This must be the second half of the insn, and it straddles a
43
@@ -XXX,XX +XXX,XX @@ static bool v7m_handle_execute_nsc(ARMCPU *cpu)
44
/* We want to do the MPU lookup as secure; work out what mmu_idx that is */
45
mmu_idx = arm_v7m_mmu_idx_for_secstate(env, true);
46
47
- if (!v7m_read_half_insn(cpu, mmu_idx, env->regs[15], &insn)) {
48
+ if (!v7m_read_half_insn(cpu, mmu_idx, true, env->regs[15], &insn)) {
49
return false;
28
}
50
}
29
51
30
- if (bus->cmd & (I2CD_M_RX_CMD | I2CD_M_S_RX_CMD_LAST)) {
52
@@ -XXX,XX +XXX,XX @@ static bool v7m_handle_execute_nsc(ARMCPU *cpu)
31
+ if ((bus->cmd & (I2CD_M_RX_CMD | I2CD_M_S_RX_CMD_LAST)) &&
53
goto gen_invep;
32
+ !(bus->intr_status & I2CD_INTR_RX_DONE)) {
33
aspeed_i2c_handle_rx_cmd(bus);
34
}
54
}
35
55
36
@@ -XXX,XX +XXX,XX @@ static void aspeed_i2c_bus_write(void *opaque, hwaddr offset,
56
- if (!v7m_read_half_insn(cpu, mmu_idx, env->regs[15] + 2, &insn)) {
37
uint64_t value, unsigned size)
57
+ if (!v7m_read_half_insn(cpu, mmu_idx, true, env->regs[15] + 2, &insn)) {
38
{
58
return false;
39
AspeedI2CBus *bus = opaque;
59
}
40
+ bool handle_rx;
60
41
42
switch (offset) {
43
case I2CD_FUN_CTRL_REG:
44
@@ -XXX,XX +XXX,XX @@ static void aspeed_i2c_bus_write(void *opaque, hwaddr offset,
45
bus->intr_ctrl = value & 0x7FFF;
46
break;
47
case I2CD_INTR_STS_REG:
48
+ handle_rx = (bus->intr_status & I2CD_INTR_RX_DONE) &&
49
+ (value & I2CD_INTR_RX_DONE);
50
bus->intr_status &= ~(value & 0x7FFF);
51
if (!bus->intr_status) {
52
bus->controller->intr_status &= ~(1 << bus->id);
53
qemu_irq_lower(bus->controller->irq);
54
}
55
+ if (handle_rx && (bus->cmd & (I2CD_M_RX_CMD | I2CD_M_S_RX_CMD_LAST))) {
56
+ aspeed_i2c_handle_rx_cmd(bus);
57
+ aspeed_i2c_bus_raise_interrupt(bus);
58
+ }
59
break;
60
case I2CD_DEV_ADDR_REG:
61
qemu_log_mask(LOG_UNIMP, "%s: slave mode not implemented\n",
62
--
61
--
63
2.19.0
62
2.25.1
64
63
65
64
diff view generated by jsdifflib
New patch
1
From: Richard Henderson <richard.henderson@linaro.org>
1
2
3
Remove the use of regime_is_secure from arm_tr_init_disas_context.
4
Instead, provide the value of v8m_secure directly from tb_flags.
5
Rather than use regime_is_secure, use the env->v7m.secure directly,
6
as per arm_mmu_idx_el.
7
8
Reviewed-by: Peter Maydell <peter.maydell@linaro.org>
9
Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
10
Message-id: 20221001162318.153420-8-richard.henderson@linaro.org
11
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
12
---
13
target/arm/cpu.h | 2 ++
14
target/arm/helper.c | 4 ++++
15
target/arm/translate.c | 3 +--
16
3 files changed, 7 insertions(+), 2 deletions(-)
17
18
diff --git a/target/arm/cpu.h b/target/arm/cpu.h
19
index XXXXXXX..XXXXXXX 100644
20
--- a/target/arm/cpu.h
21
+++ b/target/arm/cpu.h
22
@@ -XXX,XX +XXX,XX @@ FIELD(TBFLAG_M32, NEW_FP_CTXT_NEEDED, 3, 1) /* Not cached. */
23
FIELD(TBFLAG_M32, FPCCR_S_WRONG, 4, 1) /* Not cached. */
24
/* Set if MVE insns are definitely not predicated by VPR or LTPSIZE */
25
FIELD(TBFLAG_M32, MVE_NO_PRED, 5, 1) /* Not cached. */
26
+/* Set if in secure mode */
27
+FIELD(TBFLAG_M32, SECURE, 6, 1)
28
29
/*
30
* Bit usage when in AArch64 state
31
diff --git a/target/arm/helper.c b/target/arm/helper.c
32
index XXXXXXX..XXXXXXX 100644
33
--- a/target/arm/helper.c
34
+++ b/target/arm/helper.c
35
@@ -XXX,XX +XXX,XX @@ static CPUARMTBFlags rebuild_hflags_m32(CPUARMState *env, int fp_el,
36
DP_TBFLAG_M32(flags, STACKCHECK, 1);
37
}
38
39
+ if (arm_feature(env, ARM_FEATURE_M_SECURITY) && env->v7m.secure) {
40
+ DP_TBFLAG_M32(flags, SECURE, 1);
41
+ }
42
+
43
return rebuild_hflags_common_32(env, fp_el, mmu_idx, flags);
44
}
45
46
diff --git a/target/arm/translate.c b/target/arm/translate.c
47
index XXXXXXX..XXXXXXX 100644
48
--- a/target/arm/translate.c
49
+++ b/target/arm/translate.c
50
@@ -XXX,XX +XXX,XX @@ static void arm_tr_init_disas_context(DisasContextBase *dcbase, CPUState *cs)
51
dc->vfp_enabled = 1;
52
dc->be_data = MO_TE;
53
dc->v7m_handler_mode = EX_TBFLAG_M32(tb_flags, HANDLER);
54
- dc->v8m_secure = arm_feature(env, ARM_FEATURE_M_SECURITY) &&
55
- regime_is_secure(env, dc->mmu_idx);
56
+ dc->v8m_secure = EX_TBFLAG_M32(tb_flags, SECURE);
57
dc->v8m_stackcheck = EX_TBFLAG_M32(tb_flags, STACKCHECK);
58
dc->v8m_fpccr_s_wrong = EX_TBFLAG_M32(tb_flags, FPCCR_S_WRONG);
59
dc->v7m_new_fp_ctxt_needed =
60
--
61
2.25.1
diff view generated by jsdifflib
1
From: Cédric Le Goater <clg@kaod.org>
1
From: Richard Henderson <richard.henderson@linaro.org>
2
2
3
The code looks better, it removes duplicated lines and it will ease
3
This is the last use of regime_is_secure; remove it
4
the introduction of common properties for the Aspeed machines.
4
entirely before changing the layout of ARMMMUIdx.
5
5
6
Signed-off-by: Cédric Le Goater <clg@kaod.org>
6
Reviewed-by: Peter Maydell <peter.maydell@linaro.org>
7
Reviewed-by: Philippe Mathieu-Daudé <f4bug@amsat.org>
7
Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
8
Message-id: 20180921161939.822-4-clg@kaod.org
8
Message-id: 20221001162318.153420-9-richard.henderson@linaro.org
9
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
9
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
10
---
10
---
11
include/hw/arm/aspeed.h | 46 +++++++++
11
target/arm/internals.h | 42 ----------------------------------------
12
hw/arm/aspeed.c | 212 +++++++++++++---------------------------
12
target/arm/ptw.c | 44 ++++++++++++++++++++++++++++++++++++++++--
13
2 files changed, 116 insertions(+), 142 deletions(-)
13
2 files changed, 42 insertions(+), 44 deletions(-)
14
create mode 100644 include/hw/arm/aspeed.h
15
14
16
diff --git a/include/hw/arm/aspeed.h b/include/hw/arm/aspeed.h
15
diff --git a/target/arm/internals.h b/target/arm/internals.h
17
new file mode 100644
18
index XXXXXXX..XXXXXXX
19
--- /dev/null
20
+++ b/include/hw/arm/aspeed.h
21
@@ -XXX,XX +XXX,XX @@
22
+/*
23
+ * Aspeed Machines
24
+ *
25
+ * Copyright 2018 IBM Corp.
26
+ *
27
+ * This code is licensed under the GPL version 2 or later. See
28
+ * the COPYING file in the top-level directory.
29
+ */
30
+#ifndef ARM_ASPEED_H
31
+#define ARM_ASPEED_H
32
+
33
+#include "hw/boards.h"
34
+
35
+typedef struct AspeedBoardState AspeedBoardState;
36
+
37
+typedef struct AspeedBoardConfig {
38
+ const char *name;
39
+ const char *desc;
40
+ const char *soc_name;
41
+ uint32_t hw_strap1;
42
+ const char *fmc_model;
43
+ const char *spi_model;
44
+ uint32_t num_cs;
45
+ void (*i2c_init)(AspeedBoardState *bmc);
46
+} AspeedBoardConfig;
47
+
48
+#define TYPE_ASPEED_MACHINE MACHINE_TYPE_NAME("aspeed")
49
+#define ASPEED_MACHINE(obj) \
50
+ OBJECT_CHECK(AspeedMachine, (obj), TYPE_ASPEED_MACHINE)
51
+
52
+typedef struct AspeedMachine {
53
+ MachineState parent_obj;
54
+} AspeedMachine;
55
+
56
+#define ASPEED_MACHINE_CLASS(klass) \
57
+ OBJECT_CLASS_CHECK(AspeedMachineClass, (klass), TYPE_ASPEED_MACHINE)
58
+#define ASPEED_MACHINE_GET_CLASS(obj) \
59
+ OBJECT_GET_CLASS(AspeedMachineClass, (obj), TYPE_ASPEED_MACHINE)
60
+
61
+typedef struct AspeedMachineClass {
62
+ MachineClass parent_obj;
63
+ const AspeedBoardConfig *board;
64
+} AspeedMachineClass;
65
+
66
+
67
+#endif
68
diff --git a/hw/arm/aspeed.c b/hw/arm/aspeed.c
69
index XXXXXXX..XXXXXXX 100644
16
index XXXXXXX..XXXXXXX 100644
70
--- a/hw/arm/aspeed.c
17
--- a/target/arm/internals.h
71
+++ b/hw/arm/aspeed.c
18
+++ b/target/arm/internals.h
72
@@ -XXX,XX +XXX,XX @@
19
@@ -XXX,XX +XXX,XX @@ static inline bool regime_has_2_ranges(ARMMMUIdx mmu_idx)
73
#include "cpu.h"
20
}
74
#include "exec/address-spaces.h"
75
#include "hw/arm/arm.h"
76
+#include "hw/arm/aspeed.h"
77
#include "hw/arm/aspeed_soc.h"
78
#include "hw/boards.h"
79
#include "hw/i2c/smbus.h"
80
@@ -XXX,XX +XXX,XX @@ typedef struct AspeedBoardState {
81
MemoryRegion max_ram;
82
} AspeedBoardState;
83
84
-typedef struct AspeedBoardConfig {
85
- const char *soc_name;
86
- uint32_t hw_strap1;
87
- const char *fmc_model;
88
- const char *spi_model;
89
- uint32_t num_cs;
90
- void (*i2c_init)(AspeedBoardState *bmc);
91
-} AspeedBoardConfig;
92
-
93
-enum {
94
- PALMETTO_BMC,
95
- AST2500_EVB,
96
- ROMULUS_BMC,
97
- WITHERSPOON_BMC,
98
-};
99
-
100
/* Palmetto hardware value: 0x120CE416 */
101
#define PALMETTO_BMC_HW_STRAP1 ( \
102
SCU_AST2400_HW_STRAP_DRAM_SIZE(DRAM_SIZE_256MB) | \
103
@@ -XXX,XX +XXX,XX @@ enum {
104
/* Witherspoon hardware value: 0xF10AD216 (but use romulus definition) */
105
#define WITHERSPOON_BMC_HW_STRAP1 ROMULUS_BMC_HW_STRAP1
106
107
-static void palmetto_bmc_i2c_init(AspeedBoardState *bmc);
108
-static void ast2500_evb_i2c_init(AspeedBoardState *bmc);
109
-static void romulus_bmc_i2c_init(AspeedBoardState *bmc);
110
-static void witherspoon_bmc_i2c_init(AspeedBoardState *bmc);
111
-
112
-static const AspeedBoardConfig aspeed_boards[] = {
113
- [PALMETTO_BMC] = {
114
- .soc_name = "ast2400-a1",
115
- .hw_strap1 = PALMETTO_BMC_HW_STRAP1,
116
- .fmc_model = "n25q256a",
117
- .spi_model = "mx25l25635e",
118
- .num_cs = 1,
119
- .i2c_init = palmetto_bmc_i2c_init,
120
- },
121
- [AST2500_EVB] = {
122
- .soc_name = "ast2500-a1",
123
- .hw_strap1 = AST2500_EVB_HW_STRAP1,
124
- .fmc_model = "w25q256",
125
- .spi_model = "mx25l25635e",
126
- .num_cs = 1,
127
- .i2c_init = ast2500_evb_i2c_init,
128
- },
129
- [ROMULUS_BMC] = {
130
- .soc_name = "ast2500-a1",
131
- .hw_strap1 = ROMULUS_BMC_HW_STRAP1,
132
- .fmc_model = "n25q256a",
133
- .spi_model = "mx66l1g45g",
134
- .num_cs = 2,
135
- .i2c_init = romulus_bmc_i2c_init,
136
- },
137
- [WITHERSPOON_BMC] = {
138
- .soc_name = "ast2500-a1",
139
- .hw_strap1 = WITHERSPOON_BMC_HW_STRAP1,
140
- .fmc_model = "mx25l25635e",
141
- .spi_model = "mx66l1g45g",
142
- .num_cs = 2,
143
- .i2c_init = witherspoon_bmc_i2c_init,
144
- },
145
-};
146
-
147
/*
148
* The max ram region is for firmwares that scan the address space
149
* with load/store to guess how much RAM the SoC has.
150
@@ -XXX,XX +XXX,XX @@ static void palmetto_bmc_i2c_init(AspeedBoardState *bmc)
151
object_property_set_int(OBJECT(dev), 110000, "temperature3", &error_abort);
152
}
21
}
153
22
154
-static void palmetto_bmc_init(MachineState *machine)
23
-/* Return true if this address translation regime is secure */
24
-static inline bool regime_is_secure(CPUARMState *env, ARMMMUIdx mmu_idx)
155
-{
25
-{
156
- aspeed_board_init(machine, &aspeed_boards[PALMETTO_BMC]);
26
- switch (mmu_idx) {
27
- case ARMMMUIdx_E10_0:
28
- case ARMMMUIdx_E10_1:
29
- case ARMMMUIdx_E10_1_PAN:
30
- case ARMMMUIdx_E20_0:
31
- case ARMMMUIdx_E20_2:
32
- case ARMMMUIdx_E20_2_PAN:
33
- case ARMMMUIdx_Stage1_E0:
34
- case ARMMMUIdx_Stage1_E1:
35
- case ARMMMUIdx_Stage1_E1_PAN:
36
- case ARMMMUIdx_E2:
37
- case ARMMMUIdx_Stage2:
38
- case ARMMMUIdx_MPrivNegPri:
39
- case ARMMMUIdx_MUserNegPri:
40
- case ARMMMUIdx_MPriv:
41
- case ARMMMUIdx_MUser:
42
- return false;
43
- case ARMMMUIdx_SE3:
44
- case ARMMMUIdx_SE10_0:
45
- case ARMMMUIdx_SE10_1:
46
- case ARMMMUIdx_SE10_1_PAN:
47
- case ARMMMUIdx_SE20_0:
48
- case ARMMMUIdx_SE20_2:
49
- case ARMMMUIdx_SE20_2_PAN:
50
- case ARMMMUIdx_Stage1_SE0:
51
- case ARMMMUIdx_Stage1_SE1:
52
- case ARMMMUIdx_Stage1_SE1_PAN:
53
- case ARMMMUIdx_SE2:
54
- case ARMMMUIdx_Stage2_S:
55
- case ARMMMUIdx_MSPrivNegPri:
56
- case ARMMMUIdx_MSUserNegPri:
57
- case ARMMMUIdx_MSPriv:
58
- case ARMMMUIdx_MSUser:
59
- return true;
60
- default:
61
- g_assert_not_reached();
62
- }
157
-}
63
-}
158
-
64
-
159
-static void palmetto_bmc_class_init(ObjectClass *oc, void *data)
65
static inline bool regime_is_pan(CPUARMState *env, ARMMMUIdx mmu_idx)
160
-{
161
- MachineClass *mc = MACHINE_CLASS(oc);
162
-
163
- mc->desc = "OpenPOWER Palmetto BMC (ARM926EJ-S)";
164
- mc->init = palmetto_bmc_init;
165
- mc->max_cpus = 1;
166
- mc->no_sdcard = 1;
167
- mc->no_floppy = 1;
168
- mc->no_cdrom = 1;
169
- mc->no_parallel = 1;
170
-}
171
-
172
-static const TypeInfo palmetto_bmc_type = {
173
- .name = MACHINE_TYPE_NAME("palmetto-bmc"),
174
- .parent = TYPE_MACHINE,
175
- .class_init = palmetto_bmc_class_init,
176
-};
177
-
178
static void ast2500_evb_i2c_init(AspeedBoardState *bmc)
179
{
66
{
180
AspeedSoCState *soc = &bmc->soc;
67
switch (mmu_idx) {
181
@@ -XXX,XX +XXX,XX @@ static void ast2500_evb_i2c_init(AspeedBoardState *bmc)
68
diff --git a/target/arm/ptw.c b/target/arm/ptw.c
182
i2c_create_slave(aspeed_i2c_get_bus(DEVICE(&soc->i2c), 11), "ds1338", 0x32);
69
index XXXXXXX..XXXXXXX 100644
70
--- a/target/arm/ptw.c
71
+++ b/target/arm/ptw.c
72
@@ -XXX,XX +XXX,XX @@ bool get_phys_addr(CPUARMState *env, target_ulong address,
73
MMUAccessType access_type, ARMMMUIdx mmu_idx,
74
GetPhysAddrResult *result, ARMMMUFaultInfo *fi)
75
{
76
+ bool is_secure;
77
+
78
+ switch (mmu_idx) {
79
+ case ARMMMUIdx_E10_0:
80
+ case ARMMMUIdx_E10_1:
81
+ case ARMMMUIdx_E10_1_PAN:
82
+ case ARMMMUIdx_E20_0:
83
+ case ARMMMUIdx_E20_2:
84
+ case ARMMMUIdx_E20_2_PAN:
85
+ case ARMMMUIdx_Stage1_E0:
86
+ case ARMMMUIdx_Stage1_E1:
87
+ case ARMMMUIdx_Stage1_E1_PAN:
88
+ case ARMMMUIdx_E2:
89
+ case ARMMMUIdx_Stage2:
90
+ case ARMMMUIdx_MPrivNegPri:
91
+ case ARMMMUIdx_MUserNegPri:
92
+ case ARMMMUIdx_MPriv:
93
+ case ARMMMUIdx_MUser:
94
+ is_secure = false;
95
+ break;
96
+ case ARMMMUIdx_SE3:
97
+ case ARMMMUIdx_SE10_0:
98
+ case ARMMMUIdx_SE10_1:
99
+ case ARMMMUIdx_SE10_1_PAN:
100
+ case ARMMMUIdx_SE20_0:
101
+ case ARMMMUIdx_SE20_2:
102
+ case ARMMMUIdx_SE20_2_PAN:
103
+ case ARMMMUIdx_Stage1_SE0:
104
+ case ARMMMUIdx_Stage1_SE1:
105
+ case ARMMMUIdx_Stage1_SE1_PAN:
106
+ case ARMMMUIdx_SE2:
107
+ case ARMMMUIdx_Stage2_S:
108
+ case ARMMMUIdx_MSPrivNegPri:
109
+ case ARMMMUIdx_MSUserNegPri:
110
+ case ARMMMUIdx_MSPriv:
111
+ case ARMMMUIdx_MSUser:
112
+ is_secure = true;
113
+ break;
114
+ default:
115
+ g_assert_not_reached();
116
+ }
117
return get_phys_addr_with_secure(env, address, access_type, mmu_idx,
118
- regime_is_secure(env, mmu_idx),
119
- result, fi);
120
+ is_secure, result, fi);
183
}
121
}
184
122
185
-static void ast2500_evb_init(MachineState *machine)
123
hwaddr arm_cpu_get_phys_page_attrs_debug(CPUState *cs, vaddr addr,
186
-{
187
- aspeed_board_init(machine, &aspeed_boards[AST2500_EVB]);
188
-}
189
-
190
-static void ast2500_evb_class_init(ObjectClass *oc, void *data)
191
-{
192
- MachineClass *mc = MACHINE_CLASS(oc);
193
-
194
- mc->desc = "Aspeed AST2500 EVB (ARM1176)";
195
- mc->init = ast2500_evb_init;
196
- mc->max_cpus = 1;
197
- mc->no_sdcard = 1;
198
- mc->no_floppy = 1;
199
- mc->no_cdrom = 1;
200
- mc->no_parallel = 1;
201
-}
202
-
203
-static const TypeInfo ast2500_evb_type = {
204
- .name = MACHINE_TYPE_NAME("ast2500-evb"),
205
- .parent = TYPE_MACHINE,
206
- .class_init = ast2500_evb_class_init,
207
-};
208
-
209
static void romulus_bmc_i2c_init(AspeedBoardState *bmc)
210
{
211
AspeedSoCState *soc = &bmc->soc;
212
@@ -XXX,XX +XXX,XX @@ static void romulus_bmc_i2c_init(AspeedBoardState *bmc)
213
i2c_create_slave(aspeed_i2c_get_bus(DEVICE(&soc->i2c), 11), "ds1338", 0x32);
214
}
215
216
-static void romulus_bmc_init(MachineState *machine)
217
-{
218
- aspeed_board_init(machine, &aspeed_boards[ROMULUS_BMC]);
219
-}
220
-
221
-static void romulus_bmc_class_init(ObjectClass *oc, void *data)
222
-{
223
- MachineClass *mc = MACHINE_CLASS(oc);
224
-
225
- mc->desc = "OpenPOWER Romulus BMC (ARM1176)";
226
- mc->init = romulus_bmc_init;
227
- mc->max_cpus = 1;
228
- mc->no_sdcard = 1;
229
- mc->no_floppy = 1;
230
- mc->no_cdrom = 1;
231
- mc->no_parallel = 1;
232
-}
233
-
234
-static const TypeInfo romulus_bmc_type = {
235
- .name = MACHINE_TYPE_NAME("romulus-bmc"),
236
- .parent = TYPE_MACHINE,
237
- .class_init = romulus_bmc_class_init,
238
-};
239
-
240
static void witherspoon_bmc_i2c_init(AspeedBoardState *bmc)
241
{
242
AspeedSoCState *soc = &bmc->soc;
243
@@ -XXX,XX +XXX,XX @@ static void witherspoon_bmc_i2c_init(AspeedBoardState *bmc)
244
0x60);
245
}
246
247
-static void witherspoon_bmc_init(MachineState *machine)
248
+static void aspeed_machine_init(MachineState *machine)
249
{
250
- aspeed_board_init(machine, &aspeed_boards[WITHERSPOON_BMC]);
251
+ AspeedMachineClass *amc = ASPEED_MACHINE_GET_CLASS(machine);
252
+
253
+ aspeed_board_init(machine, amc->board);
254
}
255
256
-static void witherspoon_bmc_class_init(ObjectClass *oc, void *data)
257
+static void aspeed_machine_class_init(ObjectClass *oc, void *data)
258
{
259
MachineClass *mc = MACHINE_CLASS(oc);
260
+ AspeedMachineClass *amc = ASPEED_MACHINE_CLASS(oc);
261
+ const AspeedBoardConfig *board = data;
262
263
- mc->desc = "OpenPOWER Witherspoon BMC (ARM1176)";
264
- mc->init = witherspoon_bmc_init;
265
+ mc->desc = board->desc;
266
+ mc->init = aspeed_machine_init;
267
mc->max_cpus = 1;
268
mc->no_sdcard = 1;
269
mc->no_floppy = 1;
270
mc->no_cdrom = 1;
271
mc->no_parallel = 1;
272
+ amc->board = board;
273
}
274
275
-static const TypeInfo witherspoon_bmc_type = {
276
- .name = MACHINE_TYPE_NAME("witherspoon-bmc"),
277
+static const TypeInfo aspeed_machine_type = {
278
+ .name = TYPE_ASPEED_MACHINE,
279
.parent = TYPE_MACHINE,
280
- .class_init = witherspoon_bmc_class_init,
281
+ .instance_size = sizeof(AspeedMachine),
282
+ .class_size = sizeof(AspeedMachineClass),
283
+ .abstract = true,
284
};
285
286
-static void aspeed_machine_init(void)
287
+static const AspeedBoardConfig aspeed_boards[] = {
288
+ {
289
+ .name = MACHINE_TYPE_NAME("palmetto-bmc"),
290
+ .desc = "OpenPOWER Palmetto BMC (ARM926EJ-S)",
291
+ .soc_name = "ast2400-a1",
292
+ .hw_strap1 = PALMETTO_BMC_HW_STRAP1,
293
+ .fmc_model = "n25q256a",
294
+ .spi_model = "mx25l25635e",
295
+ .num_cs = 1,
296
+ .i2c_init = palmetto_bmc_i2c_init,
297
+ }, {
298
+ .name = MACHINE_TYPE_NAME("ast2500-evb"),
299
+ .desc = "Aspeed AST2500 EVB (ARM1176)",
300
+ .soc_name = "ast2500-a1",
301
+ .hw_strap1 = AST2500_EVB_HW_STRAP1,
302
+ .fmc_model = "w25q256",
303
+ .spi_model = "mx25l25635e",
304
+ .num_cs = 1,
305
+ .i2c_init = ast2500_evb_i2c_init,
306
+ }, {
307
+ .name = MACHINE_TYPE_NAME("romulus-bmc"),
308
+ .desc = "OpenPOWER Romulus BMC (ARM1176)",
309
+ .soc_name = "ast2500-a1",
310
+ .hw_strap1 = ROMULUS_BMC_HW_STRAP1,
311
+ .fmc_model = "n25q256a",
312
+ .spi_model = "mx66l1g45g",
313
+ .num_cs = 2,
314
+ .i2c_init = romulus_bmc_i2c_init,
315
+ }, {
316
+ .name = MACHINE_TYPE_NAME("witherspoon-bmc"),
317
+ .desc = "OpenPOWER Witherspoon BMC (ARM1176)",
318
+ .soc_name = "ast2500-a1",
319
+ .hw_strap1 = WITHERSPOON_BMC_HW_STRAP1,
320
+ .fmc_model = "mx25l25635e",
321
+ .spi_model = "mx66l1g45g",
322
+ .num_cs = 2,
323
+ .i2c_init = witherspoon_bmc_i2c_init,
324
+ },
325
+};
326
+
327
+static void aspeed_machine_types(void)
328
{
329
- type_register_static(&palmetto_bmc_type);
330
- type_register_static(&ast2500_evb_type);
331
- type_register_static(&romulus_bmc_type);
332
- type_register_static(&witherspoon_bmc_type);
333
+ int i;
334
+
335
+ type_register_static(&aspeed_machine_type);
336
+ for (i = 0; i < ARRAY_SIZE(aspeed_boards); ++i) {
337
+ TypeInfo ti = {
338
+ .name = aspeed_boards[i].name,
339
+ .parent = TYPE_ASPEED_MACHINE,
340
+ .class_init = aspeed_machine_class_init,
341
+ .class_data = (void *)&aspeed_boards[i],
342
+ };
343
+ type_register(&ti);
344
+ }
345
}
346
347
-type_init(aspeed_machine_init)
348
+type_init(aspeed_machine_types)
349
--
124
--
350
2.19.0
125
2.25.1
351
352
diff view generated by jsdifflib
New patch
1
From: Richard Henderson <richard.henderson@linaro.org>
1
2
3
Use get_phys_addr_with_secure directly. For a-profile, this is the
4
one place where the value of is_secure may not equal arm_is_secure(env).
5
6
Reviewed-by: Peter Maydell <peter.maydell@linaro.org>
7
Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
8
Message-id: 20221001162318.153420-10-richard.henderson@linaro.org
9
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
10
---
11
target/arm/helper.c | 19 ++++++++++++++-----
12
1 file changed, 14 insertions(+), 5 deletions(-)
13
14
diff --git a/target/arm/helper.c b/target/arm/helper.c
15
index XXXXXXX..XXXXXXX 100644
16
--- a/target/arm/helper.c
17
+++ b/target/arm/helper.c
18
@@ -XXX,XX +XXX,XX @@ static CPAccessResult ats_access(CPUARMState *env, const ARMCPRegInfo *ri,
19
20
#ifdef CONFIG_TCG
21
static uint64_t do_ats_write(CPUARMState *env, uint64_t value,
22
- MMUAccessType access_type, ARMMMUIdx mmu_idx)
23
+ MMUAccessType access_type, ARMMMUIdx mmu_idx,
24
+ bool is_secure)
25
{
26
bool ret;
27
uint64_t par64;
28
@@ -XXX,XX +XXX,XX @@ static uint64_t do_ats_write(CPUARMState *env, uint64_t value,
29
ARMMMUFaultInfo fi = {};
30
GetPhysAddrResult res = {};
31
32
- ret = get_phys_addr(env, value, access_type, mmu_idx, &res, &fi);
33
+ ret = get_phys_addr_with_secure(env, value, access_type, mmu_idx,
34
+ is_secure, &res, &fi);
35
36
/*
37
* ATS operations only do S1 or S1+S2 translations, so we never
38
@@ -XXX,XX +XXX,XX @@ static void ats_write(CPUARMState *env, const ARMCPRegInfo *ri, uint64_t value)
39
switch (el) {
40
case 3:
41
mmu_idx = ARMMMUIdx_SE3;
42
+ secure = true;
43
break;
44
case 2:
45
g_assert(!secure); /* ARMv8.4-SecEL2 is 64-bit only */
46
@@ -XXX,XX +XXX,XX @@ static void ats_write(CPUARMState *env, const ARMCPRegInfo *ri, uint64_t value)
47
switch (el) {
48
case 3:
49
mmu_idx = ARMMMUIdx_SE10_0;
50
+ secure = true;
51
break;
52
case 2:
53
g_assert(!secure); /* ARMv8.4-SecEL2 is 64-bit only */
54
@@ -XXX,XX +XXX,XX @@ static void ats_write(CPUARMState *env, const ARMCPRegInfo *ri, uint64_t value)
55
case 4:
56
/* stage 1+2 NonSecure PL1: ATS12NSOPR, ATS12NSOPW */
57
mmu_idx = ARMMMUIdx_E10_1;
58
+ secure = false;
59
break;
60
case 6:
61
/* stage 1+2 NonSecure PL0: ATS12NSOUR, ATS12NSOUW */
62
mmu_idx = ARMMMUIdx_E10_0;
63
+ secure = false;
64
break;
65
default:
66
g_assert_not_reached();
67
}
68
69
- par64 = do_ats_write(env, value, access_type, mmu_idx);
70
+ par64 = do_ats_write(env, value, access_type, mmu_idx, secure);
71
72
A32_BANKED_CURRENT_REG_SET(env, par, par64);
73
#else
74
@@ -XXX,XX +XXX,XX @@ static void ats1h_write(CPUARMState *env, const ARMCPRegInfo *ri,
75
MMUAccessType access_type = ri->opc2 & 1 ? MMU_DATA_STORE : MMU_DATA_LOAD;
76
uint64_t par64;
77
78
- par64 = do_ats_write(env, value, access_type, ARMMMUIdx_E2);
79
+ /* There is no SecureEL2 for AArch32. */
80
+ par64 = do_ats_write(env, value, access_type, ARMMMUIdx_E2, false);
81
82
A32_BANKED_CURRENT_REG_SET(env, par, par64);
83
#else
84
@@ -XXX,XX +XXX,XX @@ static void ats_write64(CPUARMState *env, const ARMCPRegInfo *ri,
85
break;
86
case 6: /* AT S1E3R, AT S1E3W */
87
mmu_idx = ARMMMUIdx_SE3;
88
+ secure = true;
89
break;
90
default:
91
g_assert_not_reached();
92
@@ -XXX,XX +XXX,XX @@ static void ats_write64(CPUARMState *env, const ARMCPRegInfo *ri,
93
g_assert_not_reached();
94
}
95
96
- env->cp15.par_el[1] = do_ats_write(env, value, access_type, mmu_idx);
97
+ env->cp15.par_el[1] = do_ats_write(env, value, access_type,
98
+ mmu_idx, secure);
99
#else
100
/* Handled by hardware accelerator. */
101
g_assert_not_reached();
102
--
103
2.25.1
diff view generated by jsdifflib
New patch
1
From: Richard Henderson <richard.henderson@linaro.org>
1
2
3
For a-profile aarch64, which does not bank system registers, it takes
4
quite a lot of code to switch between security states. In the process,
5
registers such as TCR_EL{1,2} must be swapped, which in itself requires
6
the flushing of softmmu tlbs. Therefore it doesn't buy us anything to
7
separate tlbs by security state.
8
9
Retain the distinction between Stage2 and Stage2_S.
10
11
This will be important as we implement FEAT_RME, and do not wish to
12
add a third set of mmu indexes for Realm state.
13
14
Reviewed-by: Peter Maydell <peter.maydell@linaro.org>
15
Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
16
Message-id: 20221001162318.153420-11-richard.henderson@linaro.org
17
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
18
---
19
target/arm/cpu-param.h | 2 +-
20
target/arm/cpu.h | 72 +++++++------------
21
target/arm/internals.h | 31 +-------
22
target/arm/helper.c | 144 +++++++++++++------------------------
23
target/arm/ptw.c | 25 ++-----
24
target/arm/translate-a64.c | 8 ---
25
target/arm/translate.c | 6 +-
26
7 files changed, 85 insertions(+), 203 deletions(-)
27
28
diff --git a/target/arm/cpu-param.h b/target/arm/cpu-param.h
29
index XXXXXXX..XXXXXXX 100644
30
--- a/target/arm/cpu-param.h
31
+++ b/target/arm/cpu-param.h
32
@@ -XXX,XX +XXX,XX @@
33
# define TARGET_PAGE_BITS_MIN 10
34
#endif
35
36
-#define NB_MMU_MODES 15
37
+#define NB_MMU_MODES 8
38
39
#endif
40
diff --git a/target/arm/cpu.h b/target/arm/cpu.h
41
index XXXXXXX..XXXXXXX 100644
42
--- a/target/arm/cpu.h
43
+++ b/target/arm/cpu.h
44
@@ -XXX,XX +XXX,XX @@ bool write_cpustate_to_list(ARMCPU *cpu, bool kvm_sync);
45
* table over and over.
46
* 6. we need separate EL1/EL2 mmu_idx for handling the Privileged Access
47
* Never (PAN) bit within PSTATE.
48
+ * 7. we fold together the secure and non-secure regimes for A-profile,
49
+ * because there are no banked system registers for aarch64, so the
50
+ * process of switching between secure and non-secure is
51
+ * already heavyweight.
52
*
53
* This gives us the following list of cases:
54
*
55
- * NS EL0 EL1&0 stage 1+2 (aka NS PL0)
56
- * NS EL1 EL1&0 stage 1+2 (aka NS PL1)
57
- * NS EL1 EL1&0 stage 1+2 +PAN
58
- * NS EL0 EL2&0
59
- * NS EL2 EL2&0
60
- * NS EL2 EL2&0 +PAN
61
- * NS EL2 (aka NS PL2)
62
- * S EL0 EL1&0 (aka S PL0)
63
- * S EL1 EL1&0 (not used if EL3 is 32 bit)
64
- * S EL1 EL1&0 +PAN
65
- * S EL3 (aka S PL1)
66
+ * EL0 EL1&0 stage 1+2 (aka NS PL0)
67
+ * EL1 EL1&0 stage 1+2 (aka NS PL1)
68
+ * EL1 EL1&0 stage 1+2 +PAN
69
+ * EL0 EL2&0
70
+ * EL2 EL2&0
71
+ * EL2 EL2&0 +PAN
72
+ * EL2 (aka NS PL2)
73
+ * EL3 (aka S PL1)
74
*
75
- * for a total of 11 different mmu_idx.
76
+ * for a total of 8 different mmu_idx.
77
*
78
* R profile CPUs have an MPU, but can use the same set of MMU indexes
79
- * as A profile. They only need to distinguish NS EL0 and NS EL1 (and
80
- * NS EL2 if we ever model a Cortex-R52).
81
+ * as A profile. They only need to distinguish EL0 and EL1 (and
82
+ * EL2 if we ever model a Cortex-R52).
83
*
84
* M profile CPUs are rather different as they do not have a true MMU.
85
* They have the following different MMU indexes:
86
@@ -XXX,XX +XXX,XX @@ bool write_cpustate_to_list(ARMCPU *cpu, bool kvm_sync);
87
#define ARM_MMU_IDX_NOTLB 0x20 /* does not have a TLB */
88
#define ARM_MMU_IDX_M 0x40 /* M profile */
89
90
-/* Meanings of the bits for A profile mmu idx values */
91
-#define ARM_MMU_IDX_A_NS 0x8
92
-
93
/* Meanings of the bits for M profile mmu idx values */
94
#define ARM_MMU_IDX_M_PRIV 0x1
95
#define ARM_MMU_IDX_M_NEGPRI 0x2
96
@@ -XXX,XX +XXX,XX @@ typedef enum ARMMMUIdx {
97
/*
98
* A-profile.
99
*/
100
- ARMMMUIdx_SE10_0 = 0 | ARM_MMU_IDX_A,
101
- ARMMMUIdx_SE20_0 = 1 | ARM_MMU_IDX_A,
102
- ARMMMUIdx_SE10_1 = 2 | ARM_MMU_IDX_A,
103
- ARMMMUIdx_SE20_2 = 3 | ARM_MMU_IDX_A,
104
- ARMMMUIdx_SE10_1_PAN = 4 | ARM_MMU_IDX_A,
105
- ARMMMUIdx_SE20_2_PAN = 5 | ARM_MMU_IDX_A,
106
- ARMMMUIdx_SE2 = 6 | ARM_MMU_IDX_A,
107
- ARMMMUIdx_SE3 = 7 | ARM_MMU_IDX_A,
108
-
109
- ARMMMUIdx_E10_0 = ARMMMUIdx_SE10_0 | ARM_MMU_IDX_A_NS,
110
- ARMMMUIdx_E20_0 = ARMMMUIdx_SE20_0 | ARM_MMU_IDX_A_NS,
111
- ARMMMUIdx_E10_1 = ARMMMUIdx_SE10_1 | ARM_MMU_IDX_A_NS,
112
- ARMMMUIdx_E20_2 = ARMMMUIdx_SE20_2 | ARM_MMU_IDX_A_NS,
113
- ARMMMUIdx_E10_1_PAN = ARMMMUIdx_SE10_1_PAN | ARM_MMU_IDX_A_NS,
114
- ARMMMUIdx_E20_2_PAN = ARMMMUIdx_SE20_2_PAN | ARM_MMU_IDX_A_NS,
115
- ARMMMUIdx_E2 = ARMMMUIdx_SE2 | ARM_MMU_IDX_A_NS,
116
+ ARMMMUIdx_E10_0 = 0 | ARM_MMU_IDX_A,
117
+ ARMMMUIdx_E20_0 = 1 | ARM_MMU_IDX_A,
118
+ ARMMMUIdx_E10_1 = 2 | ARM_MMU_IDX_A,
119
+ ARMMMUIdx_E20_2 = 3 | ARM_MMU_IDX_A,
120
+ ARMMMUIdx_E10_1_PAN = 4 | ARM_MMU_IDX_A,
121
+ ARMMMUIdx_E20_2_PAN = 5 | ARM_MMU_IDX_A,
122
+ ARMMMUIdx_E2 = 6 | ARM_MMU_IDX_A,
123
+ ARMMMUIdx_E3 = 7 | ARM_MMU_IDX_A,
124
125
/*
126
* These are not allocated TLBs and are used only for AT system
127
@@ -XXX,XX +XXX,XX @@ typedef enum ARMMMUIdx {
128
ARMMMUIdx_Stage1_E0 = 0 | ARM_MMU_IDX_NOTLB,
129
ARMMMUIdx_Stage1_E1 = 1 | ARM_MMU_IDX_NOTLB,
130
ARMMMUIdx_Stage1_E1_PAN = 2 | ARM_MMU_IDX_NOTLB,
131
- ARMMMUIdx_Stage1_SE0 = 3 | ARM_MMU_IDX_NOTLB,
132
- ARMMMUIdx_Stage1_SE1 = 4 | ARM_MMU_IDX_NOTLB,
133
- ARMMMUIdx_Stage1_SE1_PAN = 5 | ARM_MMU_IDX_NOTLB,
134
/*
135
* Not allocated a TLB: used only for second stage of an S12 page
136
* table walk, or for descriptor loads during first stage of an S1
137
@@ -XXX,XX +XXX,XX @@ typedef enum ARMMMUIdx {
138
* then various TLB flush insns which currently are no-ops or flush
139
* only stage 1 MMU indexes will need to change to flush stage 2.
140
*/
141
- ARMMMUIdx_Stage2 = 6 | ARM_MMU_IDX_NOTLB,
142
- ARMMMUIdx_Stage2_S = 7 | ARM_MMU_IDX_NOTLB,
143
+ ARMMMUIdx_Stage2 = 3 | ARM_MMU_IDX_NOTLB,
144
+ ARMMMUIdx_Stage2_S = 4 | ARM_MMU_IDX_NOTLB,
145
146
/*
147
* M-profile.
148
@@ -XXX,XX +XXX,XX @@ typedef enum ARMMMUIdxBit {
149
TO_CORE_BIT(E2),
150
TO_CORE_BIT(E20_2),
151
TO_CORE_BIT(E20_2_PAN),
152
- TO_CORE_BIT(SE10_0),
153
- TO_CORE_BIT(SE20_0),
154
- TO_CORE_BIT(SE10_1),
155
- TO_CORE_BIT(SE20_2),
156
- TO_CORE_BIT(SE10_1_PAN),
157
- TO_CORE_BIT(SE20_2_PAN),
158
- TO_CORE_BIT(SE2),
159
- TO_CORE_BIT(SE3),
160
+ TO_CORE_BIT(E3),
161
162
TO_CORE_BIT(MUser),
163
TO_CORE_BIT(MPriv),
164
diff --git a/target/arm/internals.h b/target/arm/internals.h
165
index XXXXXXX..XXXXXXX 100644
166
--- a/target/arm/internals.h
167
+++ b/target/arm/internals.h
168
@@ -XXX,XX +XXX,XX @@ static inline bool regime_has_2_ranges(ARMMMUIdx mmu_idx)
169
case ARMMMUIdx_Stage1_E0:
170
case ARMMMUIdx_Stage1_E1:
171
case ARMMMUIdx_Stage1_E1_PAN:
172
- case ARMMMUIdx_Stage1_SE0:
173
- case ARMMMUIdx_Stage1_SE1:
174
- case ARMMMUIdx_Stage1_SE1_PAN:
175
case ARMMMUIdx_E10_0:
176
case ARMMMUIdx_E10_1:
177
case ARMMMUIdx_E10_1_PAN:
178
case ARMMMUIdx_E20_0:
179
case ARMMMUIdx_E20_2:
180
case ARMMMUIdx_E20_2_PAN:
181
- case ARMMMUIdx_SE10_0:
182
- case ARMMMUIdx_SE10_1:
183
- case ARMMMUIdx_SE10_1_PAN:
184
- case ARMMMUIdx_SE20_0:
185
- case ARMMMUIdx_SE20_2:
186
- case ARMMMUIdx_SE20_2_PAN:
187
return true;
188
default:
189
return false;
190
@@ -XXX,XX +XXX,XX @@ static inline bool regime_is_pan(CPUARMState *env, ARMMMUIdx mmu_idx)
191
{
192
switch (mmu_idx) {
193
case ARMMMUIdx_Stage1_E1_PAN:
194
- case ARMMMUIdx_Stage1_SE1_PAN:
195
case ARMMMUIdx_E10_1_PAN:
196
case ARMMMUIdx_E20_2_PAN:
197
- case ARMMMUIdx_SE10_1_PAN:
198
- case ARMMMUIdx_SE20_2_PAN:
199
return true;
200
default:
201
return false;
202
@@ -XXX,XX +XXX,XX @@ static inline bool regime_is_pan(CPUARMState *env, ARMMMUIdx mmu_idx)
203
static inline uint32_t regime_el(CPUARMState *env, ARMMMUIdx mmu_idx)
204
{
205
switch (mmu_idx) {
206
- case ARMMMUIdx_SE20_0:
207
- case ARMMMUIdx_SE20_2:
208
- case ARMMMUIdx_SE20_2_PAN:
209
case ARMMMUIdx_E20_0:
210
case ARMMMUIdx_E20_2:
211
case ARMMMUIdx_E20_2_PAN:
212
case ARMMMUIdx_Stage2:
213
case ARMMMUIdx_Stage2_S:
214
- case ARMMMUIdx_SE2:
215
case ARMMMUIdx_E2:
216
return 2;
217
- case ARMMMUIdx_SE3:
218
+ case ARMMMUIdx_E3:
219
return 3;
220
- case ARMMMUIdx_SE10_0:
221
- case ARMMMUIdx_Stage1_SE0:
222
- return arm_el_is_aa64(env, 3) ? 1 : 3;
223
- case ARMMMUIdx_SE10_1:
224
- case ARMMMUIdx_SE10_1_PAN:
225
+ case ARMMMUIdx_E10_0:
226
case ARMMMUIdx_Stage1_E0:
227
+ return arm_el_is_aa64(env, 3) || !arm_is_secure_below_el3(env) ? 1 : 3;
228
case ARMMMUIdx_Stage1_E1:
229
case ARMMMUIdx_Stage1_E1_PAN:
230
- case ARMMMUIdx_Stage1_SE1:
231
- case ARMMMUIdx_Stage1_SE1_PAN:
232
- case ARMMMUIdx_E10_0:
233
case ARMMMUIdx_E10_1:
234
case ARMMMUIdx_E10_1_PAN:
235
case ARMMMUIdx_MPrivNegPri:
236
@@ -XXX,XX +XXX,XX @@ static inline bool arm_mmu_idx_is_stage1_of_2(ARMMMUIdx mmu_idx)
237
case ARMMMUIdx_Stage1_E0:
238
case ARMMMUIdx_Stage1_E1:
239
case ARMMMUIdx_Stage1_E1_PAN:
240
- case ARMMMUIdx_Stage1_SE0:
241
- case ARMMMUIdx_Stage1_SE1:
242
- case ARMMMUIdx_Stage1_SE1_PAN:
243
return true;
244
default:
245
return false;
246
diff --git a/target/arm/helper.c b/target/arm/helper.c
247
index XXXXXXX..XXXXXXX 100644
248
--- a/target/arm/helper.c
249
+++ b/target/arm/helper.c
250
@@ -XXX,XX +XXX,XX @@ static void scr_write(CPUARMState *env, const ARMCPRegInfo *ri, uint64_t value)
251
/* Begin with base v8.0 state. */
252
uint64_t valid_mask = 0x3fff;
253
ARMCPU *cpu = env_archcpu(env);
254
+ uint64_t changed;
255
256
/*
257
* Because SCR_EL3 is the "real" cpreg and SCR is the alias, reset always
258
@@ -XXX,XX +XXX,XX @@ static void scr_write(CPUARMState *env, const ARMCPRegInfo *ri, uint64_t value)
259
260
/* Clear all-context RES0 bits. */
261
value &= valid_mask;
262
- raw_write(env, ri, value);
263
+ changed = env->cp15.scr_el3 ^ value;
264
+ env->cp15.scr_el3 = value;
265
+
266
+ /*
267
+ * If SCR_EL3.NS changes, i.e. arm_is_secure_below_el3, then
268
+ * we must invalidate all TLBs below EL3.
269
+ */
270
+ if (changed & SCR_NS) {
271
+ tlb_flush_by_mmuidx(env_cpu(env), (ARMMMUIdxBit_E10_0 |
272
+ ARMMMUIdxBit_E20_0 |
273
+ ARMMMUIdxBit_E10_1 |
274
+ ARMMMUIdxBit_E20_2 |
275
+ ARMMMUIdxBit_E10_1_PAN |
276
+ ARMMMUIdxBit_E20_2_PAN |
277
+ ARMMMUIdxBit_E2));
278
+ }
279
}
280
281
static void scr_reset(CPUARMState *env, const ARMCPRegInfo *ri)
282
@@ -XXX,XX +XXX,XX @@ static int gt_phys_redir_timeridx(CPUARMState *env)
283
case ARMMMUIdx_E20_0:
284
case ARMMMUIdx_E20_2:
285
case ARMMMUIdx_E20_2_PAN:
286
- case ARMMMUIdx_SE20_0:
287
- case ARMMMUIdx_SE20_2:
288
- case ARMMMUIdx_SE20_2_PAN:
289
return GTIMER_HYP;
290
default:
291
return GTIMER_PHYS;
292
@@ -XXX,XX +XXX,XX @@ static int gt_virt_redir_timeridx(CPUARMState *env)
293
case ARMMMUIdx_E20_0:
294
case ARMMMUIdx_E20_2:
295
case ARMMMUIdx_E20_2_PAN:
296
- case ARMMMUIdx_SE20_0:
297
- case ARMMMUIdx_SE20_2:
298
- case ARMMMUIdx_SE20_2_PAN:
299
return GTIMER_HYPVIRT;
300
default:
301
return GTIMER_VIRT;
302
@@ -XXX,XX +XXX,XX @@ static void ats_write(CPUARMState *env, const ARMCPRegInfo *ri, uint64_t value)
303
/* stage 1 current state PL1: ATS1CPR, ATS1CPW, ATS1CPRP, ATS1CPWP */
304
switch (el) {
305
case 3:
306
- mmu_idx = ARMMMUIdx_SE3;
307
+ mmu_idx = ARMMMUIdx_E3;
308
secure = true;
309
break;
310
case 2:
311
@@ -XXX,XX +XXX,XX @@ static void ats_write(CPUARMState *env, const ARMCPRegInfo *ri, uint64_t value)
312
/* fall through */
313
case 1:
314
if (ri->crm == 9 && (env->uncached_cpsr & CPSR_PAN)) {
315
- mmu_idx = (secure ? ARMMMUIdx_Stage1_SE1_PAN
316
- : ARMMMUIdx_Stage1_E1_PAN);
317
+ mmu_idx = ARMMMUIdx_Stage1_E1_PAN;
318
} else {
319
- mmu_idx = secure ? ARMMMUIdx_Stage1_SE1 : ARMMMUIdx_Stage1_E1;
320
+ mmu_idx = ARMMMUIdx_Stage1_E1;
321
}
322
break;
323
default:
324
@@ -XXX,XX +XXX,XX @@ static void ats_write(CPUARMState *env, const ARMCPRegInfo *ri, uint64_t value)
325
/* stage 1 current state PL0: ATS1CUR, ATS1CUW */
326
switch (el) {
327
case 3:
328
- mmu_idx = ARMMMUIdx_SE10_0;
329
+ mmu_idx = ARMMMUIdx_E10_0;
330
secure = true;
331
break;
332
case 2:
333
@@ -XXX,XX +XXX,XX @@ static void ats_write(CPUARMState *env, const ARMCPRegInfo *ri, uint64_t value)
334
mmu_idx = ARMMMUIdx_Stage1_E0;
335
break;
336
case 1:
337
- mmu_idx = secure ? ARMMMUIdx_Stage1_SE0 : ARMMMUIdx_Stage1_E0;
338
+ mmu_idx = ARMMMUIdx_Stage1_E0;
339
break;
340
default:
341
g_assert_not_reached();
342
@@ -XXX,XX +XXX,XX @@ static void ats_write64(CPUARMState *env, const ARMCPRegInfo *ri,
343
switch (ri->opc1) {
344
case 0: /* AT S1E1R, AT S1E1W, AT S1E1RP, AT S1E1WP */
345
if (ri->crm == 9 && (env->pstate & PSTATE_PAN)) {
346
- mmu_idx = (secure ? ARMMMUIdx_Stage1_SE1_PAN
347
- : ARMMMUIdx_Stage1_E1_PAN);
348
+ mmu_idx = ARMMMUIdx_Stage1_E1_PAN;
349
} else {
350
- mmu_idx = secure ? ARMMMUIdx_Stage1_SE1 : ARMMMUIdx_Stage1_E1;
351
+ mmu_idx = ARMMMUIdx_Stage1_E1;
352
}
353
break;
354
case 4: /* AT S1E2R, AT S1E2W */
355
- mmu_idx = secure ? ARMMMUIdx_SE2 : ARMMMUIdx_E2;
356
+ mmu_idx = ARMMMUIdx_E2;
357
break;
358
case 6: /* AT S1E3R, AT S1E3W */
359
- mmu_idx = ARMMMUIdx_SE3;
360
+ mmu_idx = ARMMMUIdx_E3;
361
secure = true;
362
break;
363
default:
364
@@ -XXX,XX +XXX,XX @@ static void ats_write64(CPUARMState *env, const ARMCPRegInfo *ri,
365
}
366
break;
367
case 2: /* AT S1E0R, AT S1E0W */
368
- mmu_idx = secure ? ARMMMUIdx_Stage1_SE0 : ARMMMUIdx_Stage1_E0;
369
+ mmu_idx = ARMMMUIdx_Stage1_E0;
370
break;
371
case 4: /* AT S12E1R, AT S12E1W */
372
- mmu_idx = secure ? ARMMMUIdx_SE10_1 : ARMMMUIdx_E10_1;
373
+ mmu_idx = ARMMMUIdx_E10_1;
374
break;
375
case 6: /* AT S12E0R, AT S12E0W */
376
- mmu_idx = secure ? ARMMMUIdx_SE10_0 : ARMMMUIdx_E10_0;
377
+ mmu_idx = ARMMMUIdx_E10_0;
378
break;
379
default:
380
g_assert_not_reached();
381
@@ -XXX,XX +XXX,XX @@ static void vmsa_tcr_ttbr_el2_write(CPUARMState *env, const ARMCPRegInfo *ri,
382
uint16_t mask = ARMMMUIdxBit_E20_2 |
383
ARMMMUIdxBit_E20_2_PAN |
384
ARMMMUIdxBit_E20_0;
385
-
386
- if (arm_is_secure_below_el3(env)) {
387
- mask >>= ARM_MMU_IDX_A_NS;
388
- }
389
-
390
tlb_flush_by_mmuidx(env_cpu(env), mask);
391
}
392
raw_write(env, ri, value);
393
@@ -XXX,XX +XXX,XX @@ static void vttbr_write(CPUARMState *env, const ARMCPRegInfo *ri,
394
uint16_t mask = ARMMMUIdxBit_E10_1 |
395
ARMMMUIdxBit_E10_1_PAN |
396
ARMMMUIdxBit_E10_0;
397
-
398
- if (arm_is_secure_below_el3(env)) {
399
- mask >>= ARM_MMU_IDX_A_NS;
400
- }
401
-
402
tlb_flush_by_mmuidx(cs, mask);
403
raw_write(env, ri, value);
404
}
405
@@ -XXX,XX +XXX,XX @@ static int vae1_tlbmask(CPUARMState *env)
406
ARMMMUIdxBit_E10_1_PAN |
407
ARMMMUIdxBit_E10_0;
408
}
409
-
410
- if (arm_is_secure_below_el3(env)) {
411
- mask >>= ARM_MMU_IDX_A_NS;
412
- }
413
-
414
return mask;
415
}
416
417
@@ -XXX,XX +XXX,XX @@ static int vae1_tlbbits(CPUARMState *env, uint64_t addr)
418
mmu_idx = ARMMMUIdx_E10_0;
419
}
420
421
- if (arm_is_secure_below_el3(env)) {
422
- mmu_idx &= ~ARM_MMU_IDX_A_NS;
423
- }
424
-
425
return tlbbits_for_regime(env, mmu_idx, addr);
426
}
427
428
@@ -XXX,XX +XXX,XX @@ static int alle1_tlbmask(CPUARMState *env)
429
* stage 2 translations, whereas most other scopes only invalidate
430
* stage 1 translations.
431
*/
432
- if (arm_is_secure_below_el3(env)) {
433
- return ARMMMUIdxBit_SE10_1 |
434
- ARMMMUIdxBit_SE10_1_PAN |
435
- ARMMMUIdxBit_SE10_0;
436
- } else {
437
- return ARMMMUIdxBit_E10_1 |
438
- ARMMMUIdxBit_E10_1_PAN |
439
- ARMMMUIdxBit_E10_0;
440
- }
441
+ return (ARMMMUIdxBit_E10_1 |
442
+ ARMMMUIdxBit_E10_1_PAN |
443
+ ARMMMUIdxBit_E10_0);
444
}
445
446
static int e2_tlbmask(CPUARMState *env)
447
{
448
- if (arm_is_secure_below_el3(env)) {
449
- return ARMMMUIdxBit_SE20_0 |
450
- ARMMMUIdxBit_SE20_2 |
451
- ARMMMUIdxBit_SE20_2_PAN |
452
- ARMMMUIdxBit_SE2;
453
- } else {
454
- return ARMMMUIdxBit_E20_0 |
455
- ARMMMUIdxBit_E20_2 |
456
- ARMMMUIdxBit_E20_2_PAN |
457
- ARMMMUIdxBit_E2;
458
- }
459
+ return (ARMMMUIdxBit_E20_0 |
460
+ ARMMMUIdxBit_E20_2 |
461
+ ARMMMUIdxBit_E20_2_PAN |
462
+ ARMMMUIdxBit_E2);
463
}
464
465
static void tlbi_aa64_alle1_write(CPUARMState *env, const ARMCPRegInfo *ri,
466
@@ -XXX,XX +XXX,XX @@ static void tlbi_aa64_alle3_write(CPUARMState *env, const ARMCPRegInfo *ri,
467
ARMCPU *cpu = env_archcpu(env);
468
CPUState *cs = CPU(cpu);
469
470
- tlb_flush_by_mmuidx(cs, ARMMMUIdxBit_SE3);
471
+ tlb_flush_by_mmuidx(cs, ARMMMUIdxBit_E3);
472
}
473
474
static void tlbi_aa64_alle1is_write(CPUARMState *env, const ARMCPRegInfo *ri,
475
@@ -XXX,XX +XXX,XX @@ static void tlbi_aa64_alle3is_write(CPUARMState *env, const ARMCPRegInfo *ri,
476
{
477
CPUState *cs = env_cpu(env);
478
479
- tlb_flush_by_mmuidx_all_cpus_synced(cs, ARMMMUIdxBit_SE3);
480
+ tlb_flush_by_mmuidx_all_cpus_synced(cs, ARMMMUIdxBit_E3);
481
}
482
483
static void tlbi_aa64_vae2_write(CPUARMState *env, const ARMCPRegInfo *ri,
484
@@ -XXX,XX +XXX,XX @@ static void tlbi_aa64_vae3_write(CPUARMState *env, const ARMCPRegInfo *ri,
485
CPUState *cs = CPU(cpu);
486
uint64_t pageaddr = sextract64(value << 12, 0, 56);
487
488
- tlb_flush_page_by_mmuidx(cs, pageaddr, ARMMMUIdxBit_SE3);
489
+ tlb_flush_page_by_mmuidx(cs, pageaddr, ARMMMUIdxBit_E3);
490
}
491
492
static void tlbi_aa64_vae1is_write(CPUARMState *env, const ARMCPRegInfo *ri,
493
@@ -XXX,XX +XXX,XX @@ static void tlbi_aa64_vae2is_write(CPUARMState *env, const ARMCPRegInfo *ri,
494
{
495
CPUState *cs = env_cpu(env);
496
uint64_t pageaddr = sextract64(value << 12, 0, 56);
497
- bool secure = arm_is_secure_below_el3(env);
498
- int mask = secure ? ARMMMUIdxBit_SE2 : ARMMMUIdxBit_E2;
499
- int bits = tlbbits_for_regime(env, secure ? ARMMMUIdx_SE2 : ARMMMUIdx_E2,
500
- pageaddr);
501
+ int bits = tlbbits_for_regime(env, ARMMMUIdx_E2, pageaddr);
502
503
- tlb_flush_page_bits_by_mmuidx_all_cpus_synced(cs, pageaddr, mask, bits);
504
+ tlb_flush_page_bits_by_mmuidx_all_cpus_synced(cs, pageaddr,
505
+ ARMMMUIdxBit_E2, bits);
506
}
507
508
static void tlbi_aa64_vae3is_write(CPUARMState *env, const ARMCPRegInfo *ri,
509
@@ -XXX,XX +XXX,XX @@ static void tlbi_aa64_vae3is_write(CPUARMState *env, const ARMCPRegInfo *ri,
510
{
511
CPUState *cs = env_cpu(env);
512
uint64_t pageaddr = sextract64(value << 12, 0, 56);
513
- int bits = tlbbits_for_regime(env, ARMMMUIdx_SE3, pageaddr);
514
+ int bits = tlbbits_for_regime(env, ARMMMUIdx_E3, pageaddr);
515
516
tlb_flush_page_bits_by_mmuidx_all_cpus_synced(cs, pageaddr,
517
- ARMMMUIdxBit_SE3, bits);
518
+ ARMMMUIdxBit_E3, bits);
519
}
520
521
#ifdef TARGET_AARCH64
522
@@ -XXX,XX +XXX,XX @@ static void tlbi_aa64_rvae1is_write(CPUARMState *env,
523
524
static int vae2_tlbmask(CPUARMState *env)
525
{
526
- return (arm_is_secure_below_el3(env)
527
- ? ARMMMUIdxBit_SE2 : ARMMMUIdxBit_E2);
528
+ return ARMMMUIdxBit_E2;
529
}
530
531
static void tlbi_aa64_rvae2_write(CPUARMState *env,
532
@@ -XXX,XX +XXX,XX @@ static void tlbi_aa64_rvae3_write(CPUARMState *env,
533
* flush-last-level-only.
534
*/
535
536
- do_rvae_write(env, value, ARMMMUIdxBit_SE3,
537
- tlb_force_broadcast(env));
538
+ do_rvae_write(env, value, ARMMMUIdxBit_E3, tlb_force_broadcast(env));
539
}
540
541
static void tlbi_aa64_rvae3is_write(CPUARMState *env,
542
@@ -XXX,XX +XXX,XX @@ static void tlbi_aa64_rvae3is_write(CPUARMState *env,
543
* flush-last-level-only or inner/outer specific flushes.
544
*/
545
546
- do_rvae_write(env, value, ARMMMUIdxBit_SE3, true);
547
+ do_rvae_write(env, value, ARMMMUIdxBit_E3, true);
548
}
549
#endif
550
551
@@ -XXX,XX +XXX,XX @@ uint64_t arm_sctlr(CPUARMState *env, int el)
552
/* Only EL0 needs to be adjusted for EL1&0 or EL2&0. */
553
if (el == 0) {
554
ARMMMUIdx mmu_idx = arm_mmu_idx_el(env, 0);
555
- el = (mmu_idx == ARMMMUIdx_E20_0 || mmu_idx == ARMMMUIdx_SE20_0)
556
- ? 2 : 1;
557
+ el = mmu_idx == ARMMMUIdx_E20_0 ? 2 : 1;
558
}
559
return env->cp15.sctlr_el[el];
560
}
561
@@ -XXX,XX +XXX,XX @@ int arm_mmu_idx_to_el(ARMMMUIdx mmu_idx)
562
switch (mmu_idx) {
563
case ARMMMUIdx_E10_0:
564
case ARMMMUIdx_E20_0:
565
- case ARMMMUIdx_SE10_0:
566
- case ARMMMUIdx_SE20_0:
567
return 0;
568
case ARMMMUIdx_E10_1:
569
case ARMMMUIdx_E10_1_PAN:
570
- case ARMMMUIdx_SE10_1:
571
- case ARMMMUIdx_SE10_1_PAN:
572
return 1;
573
case ARMMMUIdx_E2:
574
case ARMMMUIdx_E20_2:
575
case ARMMMUIdx_E20_2_PAN:
576
- case ARMMMUIdx_SE2:
577
- case ARMMMUIdx_SE20_2:
578
- case ARMMMUIdx_SE20_2_PAN:
579
return 2;
580
- case ARMMMUIdx_SE3:
581
+ case ARMMMUIdx_E3:
582
return 3;
583
default:
584
g_assert_not_reached();
585
@@ -XXX,XX +XXX,XX @@ ARMMMUIdx arm_mmu_idx_el(CPUARMState *env, int el)
586
}
587
break;
588
case 3:
589
- return ARMMMUIdx_SE3;
590
+ return ARMMMUIdx_E3;
591
default:
592
g_assert_not_reached();
593
}
594
595
- if (arm_is_secure_below_el3(env)) {
596
- idx &= ~ARM_MMU_IDX_A_NS;
597
- }
598
-
599
return idx;
600
}
601
602
@@ -XXX,XX +XXX,XX @@ static CPUARMTBFlags rebuild_hflags_a64(CPUARMState *env, int el, int fp_el,
603
switch (mmu_idx) {
604
case ARMMMUIdx_E10_1:
605
case ARMMMUIdx_E10_1_PAN:
606
- case ARMMMUIdx_SE10_1:
607
- case ARMMMUIdx_SE10_1_PAN:
608
/* TODO: ARMv8.3-NV */
609
DP_TBFLAG_A64(flags, UNPRIV, 1);
610
break;
611
case ARMMMUIdx_E20_2:
612
case ARMMMUIdx_E20_2_PAN:
613
- case ARMMMUIdx_SE20_2:
614
- case ARMMMUIdx_SE20_2_PAN:
615
/*
616
* Note that EL20_2 is gated by HCR_EL2.E2H == 1, but EL20_0 is
617
* gated by HCR_EL2.<E2H,TGE> == '11', and so is LDTR.
618
diff --git a/target/arm/ptw.c b/target/arm/ptw.c
619
index XXXXXXX..XXXXXXX 100644
620
--- a/target/arm/ptw.c
621
+++ b/target/arm/ptw.c
622
@@ -XXX,XX +XXX,XX @@ unsigned int arm_pamax(ARMCPU *cpu)
623
ARMMMUIdx stage_1_mmu_idx(ARMMMUIdx mmu_idx)
624
{
625
switch (mmu_idx) {
626
- case ARMMMUIdx_SE10_0:
627
- return ARMMMUIdx_Stage1_SE0;
628
- case ARMMMUIdx_SE10_1:
629
- return ARMMMUIdx_Stage1_SE1;
630
- case ARMMMUIdx_SE10_1_PAN:
631
- return ARMMMUIdx_Stage1_SE1_PAN;
632
case ARMMMUIdx_E10_0:
633
return ARMMMUIdx_Stage1_E0;
634
case ARMMMUIdx_E10_1:
635
@@ -XXX,XX +XXX,XX @@ static bool regime_translation_big_endian(CPUARMState *env, ARMMMUIdx mmu_idx)
636
static bool regime_is_user(CPUARMState *env, ARMMMUIdx mmu_idx)
637
{
638
switch (mmu_idx) {
639
- case ARMMMUIdx_SE10_0:
640
case ARMMMUIdx_E20_0:
641
- case ARMMMUIdx_SE20_0:
642
case ARMMMUIdx_Stage1_E0:
643
- case ARMMMUIdx_Stage1_SE0:
644
case ARMMMUIdx_MUser:
645
case ARMMMUIdx_MSUser:
646
case ARMMMUIdx_MUserNegPri:
647
@@ -XXX,XX +XXX,XX @@ bool get_phys_addr_with_secure(CPUARMState *env, target_ulong address,
648
649
s2_mmu_idx = (s2walk_secure
650
? ARMMMUIdx_Stage2_S : ARMMMUIdx_Stage2);
651
- is_el0 = mmu_idx == ARMMMUIdx_E10_0 || mmu_idx == ARMMMUIdx_SE10_0;
652
+ is_el0 = mmu_idx == ARMMMUIdx_E10_0;
653
654
/*
655
* S1 is done, now do S2 translation.
656
@@ -XXX,XX +XXX,XX @@ bool get_phys_addr(CPUARMState *env, target_ulong address,
657
case ARMMMUIdx_Stage1_E1:
658
case ARMMMUIdx_Stage1_E1_PAN:
659
case ARMMMUIdx_E2:
660
+ is_secure = arm_is_secure_below_el3(env);
661
+ break;
662
case ARMMMUIdx_Stage2:
663
case ARMMMUIdx_MPrivNegPri:
664
case ARMMMUIdx_MUserNegPri:
665
@@ -XXX,XX +XXX,XX @@ bool get_phys_addr(CPUARMState *env, target_ulong address,
666
case ARMMMUIdx_MUser:
667
is_secure = false;
668
break;
669
- case ARMMMUIdx_SE3:
670
- case ARMMMUIdx_SE10_0:
671
- case ARMMMUIdx_SE10_1:
672
- case ARMMMUIdx_SE10_1_PAN:
673
- case ARMMMUIdx_SE20_0:
674
- case ARMMMUIdx_SE20_2:
675
- case ARMMMUIdx_SE20_2_PAN:
676
- case ARMMMUIdx_Stage1_SE0:
677
- case ARMMMUIdx_Stage1_SE1:
678
- case ARMMMUIdx_Stage1_SE1_PAN:
679
- case ARMMMUIdx_SE2:
680
+ case ARMMMUIdx_E3:
681
case ARMMMUIdx_Stage2_S:
682
case ARMMMUIdx_MSPrivNegPri:
683
case ARMMMUIdx_MSUserNegPri:
684
diff --git a/target/arm/translate-a64.c b/target/arm/translate-a64.c
685
index XXXXXXX..XXXXXXX 100644
686
--- a/target/arm/translate-a64.c
687
+++ b/target/arm/translate-a64.c
688
@@ -XXX,XX +XXX,XX @@ static int get_a64_user_mem_index(DisasContext *s)
689
case ARMMMUIdx_E20_2_PAN:
690
useridx = ARMMMUIdx_E20_0;
691
break;
692
- case ARMMMUIdx_SE10_1:
693
- case ARMMMUIdx_SE10_1_PAN:
694
- useridx = ARMMMUIdx_SE10_0;
695
- break;
696
- case ARMMMUIdx_SE20_2:
697
- case ARMMMUIdx_SE20_2_PAN:
698
- useridx = ARMMMUIdx_SE20_0;
699
- break;
700
default:
701
g_assert_not_reached();
702
}
703
diff --git a/target/arm/translate.c b/target/arm/translate.c
704
index XXXXXXX..XXXXXXX 100644
705
--- a/target/arm/translate.c
706
+++ b/target/arm/translate.c
707
@@ -XXX,XX +XXX,XX @@ static inline int get_a32_user_mem_index(DisasContext *s)
708
* otherwise, access as if at PL0.
709
*/
710
switch (s->mmu_idx) {
711
+ case ARMMMUIdx_E3:
712
case ARMMMUIdx_E2: /* this one is UNPREDICTABLE */
713
case ARMMMUIdx_E10_0:
714
case ARMMMUIdx_E10_1:
715
case ARMMMUIdx_E10_1_PAN:
716
return arm_to_core_mmu_idx(ARMMMUIdx_E10_0);
717
- case ARMMMUIdx_SE3:
718
- case ARMMMUIdx_SE10_0:
719
- case ARMMMUIdx_SE10_1:
720
- case ARMMMUIdx_SE10_1_PAN:
721
- return arm_to_core_mmu_idx(ARMMMUIdx_SE10_0);
722
case ARMMMUIdx_MUser:
723
case ARMMMUIdx_MPriv:
724
return arm_to_core_mmu_idx(ARMMMUIdx_MUser);
725
--
726
2.25.1
diff view generated by jsdifflib
1
From: Eric Auger <eric.auger@redhat.com>
1
From: Richard Henderson <richard.henderson@linaro.org>
2
2
3
The event queue management is broken today. Event records
3
Use a switch on mmu_idx for the a-profile indexes, instead of
4
are not properly written as EVT_SET_* macro was not updating
4
three different if's vs regime_el and arm_mmu_idx_is_stage1_of_2.
5
the actual event record. Also the event queue interrupt
6
is not correctly triggered.
7
5
8
Fixes: bb981004eaf4 ("hw/arm/smmuv3: Event queue recording helper")
9
Signed-off-by: Eric Auger <eric.auger@redhat.com>
10
Message-id: 20180921070138.10114-3-eric.auger@redhat.com
11
Reviewed-by: Peter Maydell <peter.maydell@linaro.org>
6
Reviewed-by: Peter Maydell <peter.maydell@linaro.org>
7
Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
8
Message-id: 20221001162318.153420-12-richard.henderson@linaro.org
12
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
9
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
13
---
10
---
14
hw/arm/smmuv3-internal.h | 26 +++++++++++++-------------
11
target/arm/ptw.c | 32 +++++++++++++++++++++++++-------
15
hw/arm/smmuv3.c | 2 +-
12
1 file changed, 25 insertions(+), 7 deletions(-)
16
2 files changed, 14 insertions(+), 14 deletions(-)
17
13
18
diff --git a/hw/arm/smmuv3-internal.h b/hw/arm/smmuv3-internal.h
14
diff --git a/target/arm/ptw.c b/target/arm/ptw.c
19
index XXXXXXX..XXXXXXX 100644
15
index XXXXXXX..XXXXXXX 100644
20
--- a/hw/arm/smmuv3-internal.h
16
--- a/target/arm/ptw.c
21
+++ b/hw/arm/smmuv3-internal.h
17
+++ b/target/arm/ptw.c
22
@@ -XXX,XX +XXX,XX @@ typedef struct SMMUEventInfo {
18
@@ -XXX,XX +XXX,XX @@ static bool regime_translation_disabled(CPUARMState *env, ARMMMUIdx mmu_idx,
23
19
24
#define EVT_Q_OVERFLOW (1 << 31)
20
hcr_el2 = arm_hcr_el2_eff(env);
25
21
26
-#define EVT_SET_TYPE(x, v) deposit32((x)->word[0], 0 , 8 , v)
22
- if (mmu_idx == ARMMMUIdx_Stage2 || mmu_idx == ARMMMUIdx_Stage2_S) {
27
-#define EVT_SET_SSV(x, v) deposit32((x)->word[0], 11, 1 , v)
23
+ switch (mmu_idx) {
28
-#define EVT_SET_SSID(x, v) deposit32((x)->word[0], 12, 20, v)
24
+ case ARMMMUIdx_Stage2:
29
-#define EVT_SET_SID(x, v) ((x)->word[1] = v)
25
+ case ARMMMUIdx_Stage2_S:
30
-#define EVT_SET_STAG(x, v) deposit32((x)->word[2], 0 , 16, v)
26
/* HCR.DC means HCR.VM behaves as 1 */
31
-#define EVT_SET_STALL(x, v) deposit32((x)->word[2], 31, 1 , v)
27
return (hcr_el2 & (HCR_DC | HCR_VM)) == 0;
32
-#define EVT_SET_PNU(x, v) deposit32((x)->word[3], 1 , 1 , v)
28
- }
33
-#define EVT_SET_IND(x, v) deposit32((x)->word[3], 2 , 1 , v)
29
34
-#define EVT_SET_RNW(x, v) deposit32((x)->word[3], 3 , 1 , v)
30
- if (hcr_el2 & HCR_TGE) {
35
-#define EVT_SET_S2(x, v) deposit32((x)->word[3], 7 , 1 , v)
31
+ case ARMMMUIdx_E10_0:
36
-#define EVT_SET_CLASS(x, v) deposit32((x)->word[3], 8 , 2 , v)
32
+ case ARMMMUIdx_E10_1:
37
+#define EVT_SET_TYPE(x, v) ((x)->word[0] = deposit32((x)->word[0], 0 , 8 , v))
33
+ case ARMMMUIdx_E10_1_PAN:
38
+#define EVT_SET_SSV(x, v) ((x)->word[0] = deposit32((x)->word[0], 11, 1 , v))
34
/* TGE means that NS EL0/1 act as if SCTLR_EL1.M is zero */
39
+#define EVT_SET_SSID(x, v) ((x)->word[0] = deposit32((x)->word[0], 12, 20, v))
35
- if (!is_secure && regime_el(env, mmu_idx) == 1) {
40
+#define EVT_SET_SID(x, v) ((x)->word[1] = v)
36
+ if (!is_secure && (hcr_el2 & HCR_TGE)) {
41
+#define EVT_SET_STAG(x, v) ((x)->word[2] = deposit32((x)->word[2], 0 , 16, v))
37
return true;
42
+#define EVT_SET_STALL(x, v) ((x)->word[2] = deposit32((x)->word[2], 31, 1 , v))
38
}
43
+#define EVT_SET_PNU(x, v) ((x)->word[3] = deposit32((x)->word[3], 1 , 1 , v))
39
- }
44
+#define EVT_SET_IND(x, v) ((x)->word[3] = deposit32((x)->word[3], 2 , 1 , v))
40
+ break;
45
+#define EVT_SET_RNW(x, v) ((x)->word[3] = deposit32((x)->word[3], 3 , 1 , v))
41
46
+#define EVT_SET_S2(x, v) ((x)->word[3] = deposit32((x)->word[3], 7 , 1 , v))
42
- if ((hcr_el2 & HCR_DC) && arm_mmu_idx_is_stage1_of_2(mmu_idx)) {
47
+#define EVT_SET_CLASS(x, v) ((x)->word[3] = deposit32((x)->word[3], 8 , 2 , v))
43
+ case ARMMMUIdx_Stage1_E0:
48
#define EVT_SET_ADDR(x, addr) \
44
+ case ARMMMUIdx_Stage1_E1:
49
do { \
45
+ case ARMMMUIdx_Stage1_E1_PAN:
50
(x)->word[5] = (uint32_t)(addr >> 32); \
46
/* HCR.DC means SCTLR_EL1.M behaves as 0 */
51
@@ -XXX,XX +XXX,XX @@ typedef struct SMMUEventInfo {
47
- return true;
52
} while (0)
48
+ if (hcr_el2 & HCR_DC) {
53
#define EVT_SET_ADDR2(x, addr) \
49
+ return true;
54
do { \
50
+ }
55
- deposit32((x)->word[7], 3, 29, addr >> 16); \
51
+ break;
56
- deposit32((x)->word[7], 0, 16, addr & 0xffff);\
52
+
57
+ (x)->word[7] = deposit32((x)->word[7], 3, 29, addr >> 16); \
53
+ case ARMMMUIdx_E20_0:
58
+ (x)->word[7] = deposit32((x)->word[7], 0, 16, addr & 0xffff);\
54
+ case ARMMMUIdx_E20_2:
59
} while (0)
55
+ case ARMMMUIdx_E20_2_PAN:
60
56
+ case ARMMMUIdx_E2:
61
void smmuv3_record_event(SMMUv3State *s, SMMUEventInfo *event);
57
+ case ARMMMUIdx_E3:
62
diff --git a/hw/arm/smmuv3.c b/hw/arm/smmuv3.c
58
+ break;
63
index XXXXXXX..XXXXXXX 100644
59
+
64
--- a/hw/arm/smmuv3.c
60
+ default:
65
+++ b/hw/arm/smmuv3.c
61
+ g_assert_not_reached();
66
@@ -XXX,XX +XXX,XX @@ static MemTxResult smmuv3_write_eventq(SMMUv3State *s, Evt *evt)
67
return r;
68
}
62
}
69
63
70
- if (smmuv3_q_empty(q)) {
64
return (regime_sctlr(env, mmu_idx) & SCTLR_M) == 0;
71
+ if (!smmuv3_q_empty(q)) {
72
smmuv3_trigger_irq(s, SMMU_IRQ_EVTQ, 0);
73
}
74
return MEMTX_OK;
75
--
65
--
76
2.19.0
66
2.25.1
77
78
diff view generated by jsdifflib
1
Add 'break' statements missing from a switch in the APB dual-timer
1
From: Richard Henderson <richard.henderson@linaro.org>
2
write function. Spotted by Coverity as CID 1395626 and 1395633.
3
2
4
Reported-by: Paolo Bonzini <pbonzini@redhat.com>
3
The effect of TGE does not only apply to non-secure state,
4
now that Secure EL2 exists.
5
6
Reviewed-by: Peter Maydell <peter.maydell@linaro.org>
7
Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
8
Message-id: 20221001162318.153420-13-richard.henderson@linaro.org
5
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
9
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
6
Reviewed-by: Philippe Mathieu-Daudé <f4bug@amsat.org>
7
Message-id: 20180924123122.14549-1-peter.maydell@linaro.org
8
---
10
---
9
hw/timer/cmsdk-apb-dualtimer.c | 2 ++
11
target/arm/ptw.c | 4 ++--
10
1 file changed, 2 insertions(+)
12
1 file changed, 2 insertions(+), 2 deletions(-)
11
13
12
diff --git a/hw/timer/cmsdk-apb-dualtimer.c b/hw/timer/cmsdk-apb-dualtimer.c
14
diff --git a/target/arm/ptw.c b/target/arm/ptw.c
13
index XXXXXXX..XXXXXXX 100644
15
index XXXXXXX..XXXXXXX 100644
14
--- a/hw/timer/cmsdk-apb-dualtimer.c
16
--- a/target/arm/ptw.c
15
+++ b/hw/timer/cmsdk-apb-dualtimer.c
17
+++ b/target/arm/ptw.c
16
@@ -XXX,XX +XXX,XX @@ static void cmsdk_apb_dualtimer_write(void *opaque, hwaddr offset,
18
@@ -XXX,XX +XXX,XX @@ static bool regime_translation_disabled(CPUARMState *env, ARMMMUIdx mmu_idx,
17
case A_TIMERITCR:
19
case ARMMMUIdx_E10_0:
18
s->timeritcr = value & R_TIMERITCR_VALID_MASK;
20
case ARMMMUIdx_E10_1:
19
cmsdk_apb_dualtimer_update(s);
21
case ARMMMUIdx_E10_1_PAN:
20
+ break;
22
- /* TGE means that NS EL0/1 act as if SCTLR_EL1.M is zero */
21
case A_TIMERITOP:
23
- if (!is_secure && (hcr_el2 & HCR_TGE)) {
22
s->timeritop = value & R_TIMERITOP_VALID_MASK;
24
+ /* TGE means that EL0/1 act as if SCTLR_EL1.M is zero */
23
cmsdk_apb_dualtimer_update(s);
25
+ if (hcr_el2 & HCR_TGE) {
24
+ break;
26
return true;
25
default:
27
}
26
bad_offset:
28
break;
27
qemu_log_mask(LOG_GUEST_ERROR,
28
--
29
--
29
2.19.0
30
2.25.1
30
31
diff view generated by jsdifflib
1
From: Joel Stanley <joel@jms.id.au>
1
From: Richard Henderson <richard.henderson@linaro.org>
2
2
3
This adds the base for a machine model of the BBC micro:bit:
3
For page walking, we may require HCR for a security state
4
that is not "current".
4
5
5
https://en.wikipedia.org/wiki/Micro_Bit
6
7
This is a system with a nRF51 SoC containing the main processor, with
8
various peripherals on board.
9
10
Reviewed-by: Stefan Hajnoczi <stefanha@redhat.com>
11
Signed-off-by: Joel Stanley <joel@jms.id.au>
12
Message-id: 20180831220920.27113-4-joel@jms.id.au
13
Reviewed-by: Peter Maydell <peter.maydell@linaro.org>
6
Reviewed-by: Peter Maydell <peter.maydell@linaro.org>
7
Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
8
Message-id: 20221001162318.153420-14-richard.henderson@linaro.org
14
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
9
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
15
---
10
---
16
hw/arm/Makefile.objs | 2 +-
11
target/arm/cpu.h | 20 +++++++++++++-------
17
hw/arm/microbit.c | 67 ++++++++++++++++++++++++++++++++++++++++++++
12
target/arm/helper.c | 11 ++++++++---
18
2 files changed, 68 insertions(+), 1 deletion(-)
13
2 files changed, 21 insertions(+), 10 deletions(-)
19
create mode 100644 hw/arm/microbit.c
20
14
21
diff --git a/hw/arm/Makefile.objs b/hw/arm/Makefile.objs
15
diff --git a/target/arm/cpu.h b/target/arm/cpu.h
22
index XXXXXXX..XXXXXXX 100644
16
index XXXXXXX..XXXXXXX 100644
23
--- a/hw/arm/Makefile.objs
17
--- a/target/arm/cpu.h
24
+++ b/hw/arm/Makefile.objs
18
+++ b/target/arm/cpu.h
25
@@ -XXX,XX +XXX,XX @@ obj-$(CONFIG_IOTKIT) += iotkit.o
19
@@ -XXX,XX +XXX,XX @@ static inline bool arm_is_secure(CPUARMState *env)
26
obj-$(CONFIG_FSL_IMX7) += fsl-imx7.o mcimx7d-sabre.o
20
* Return true if the current security state has AArch64 EL2 or AArch32 Hyp.
27
obj-$(CONFIG_ARM_SMMUV3) += smmu-common.o smmuv3.o
21
* This corresponds to the pseudocode EL2Enabled()
28
obj-$(CONFIG_FSL_IMX6UL) += fsl-imx6ul.o mcimx6ul-evk.o
22
*/
29
-obj-$(CONFIG_NRF51_SOC) += nrf51_soc.o
23
+static inline bool arm_is_el2_enabled_secstate(CPUARMState *env, bool secure)
30
+obj-$(CONFIG_NRF51_SOC) += nrf51_soc.o microbit.o
31
diff --git a/hw/arm/microbit.c b/hw/arm/microbit.c
32
new file mode 100644
33
index XXXXXXX..XXXXXXX
34
--- /dev/null
35
+++ b/hw/arm/microbit.c
36
@@ -XXX,XX +XXX,XX @@
37
+/*
38
+ * BBC micro:bit machine
39
+ * http://tech.microbit.org/hardware/
40
+ *
41
+ * Copyright 2018 Joel Stanley <joel@jms.id.au>
42
+ *
43
+ * This code is licensed under the GPL version 2 or later. See
44
+ * the COPYING file in the top-level directory.
45
+ */
46
+
47
+#include "qemu/osdep.h"
48
+#include "qapi/error.h"
49
+#include "hw/boards.h"
50
+#include "hw/arm/arm.h"
51
+#include "exec/address-spaces.h"
52
+
53
+#include "hw/arm/nrf51_soc.h"
54
+
55
+typedef struct {
56
+ MachineState parent;
57
+
58
+ NRF51State nrf51;
59
+} MicrobitMachineState;
60
+
61
+#define TYPE_MICROBIT_MACHINE MACHINE_TYPE_NAME("microbit")
62
+
63
+#define MICROBIT_MACHINE(obj) \
64
+ OBJECT_CHECK(MicrobitMachineState, obj, TYPE_MICROBIT_MACHINE)
65
+
66
+static void microbit_init(MachineState *machine)
67
+{
24
+{
68
+ MicrobitMachineState *s = MICROBIT_MACHINE(machine);
25
+ return arm_feature(env, ARM_FEATURE_EL2)
69
+ MemoryRegion *system_memory = get_system_memory();
26
+ && (!secure || (env->cp15.scr_el3 & SCR_EEL2));
70
+ Object *soc = OBJECT(&s->nrf51);
71
+
72
+ sysbus_init_child_obj(OBJECT(machine), "nrf51", soc, sizeof(s->nrf51),
73
+ TYPE_NRF51_SOC);
74
+ object_property_set_link(soc, OBJECT(system_memory), "memory",
75
+ &error_fatal);
76
+ object_property_set_bool(soc, true, "realized", &error_fatal);
77
+
78
+ armv7m_load_kernel(ARM_CPU(first_cpu), machine->kernel_filename,
79
+ NRF51_SOC(soc)->flash_size);
80
+}
27
+}
81
+
28
+
82
+static void microbit_machine_class_init(ObjectClass *oc, void *data)
29
static inline bool arm_is_el2_enabled(CPUARMState *env)
30
{
31
- if (arm_feature(env, ARM_FEATURE_EL2)) {
32
- if (arm_is_secure_below_el3(env)) {
33
- return (env->cp15.scr_el3 & SCR_EEL2) != 0;
34
- }
35
- return true;
36
- }
37
- return false;
38
+ return arm_is_el2_enabled_secstate(env, arm_is_secure_below_el3(env));
39
}
40
41
#else
42
@@ -XXX,XX +XXX,XX @@ static inline bool arm_is_secure(CPUARMState *env)
43
return false;
44
}
45
46
+static inline bool arm_is_el2_enabled_secstate(CPUARMState *env, bool secure)
83
+{
47
+{
84
+ MachineClass *mc = MACHINE_CLASS(oc);
48
+ return false;
85
+
86
+ mc->desc = "BBC micro:bit";
87
+ mc->init = microbit_init;
88
+ mc->max_cpus = 1;
89
+}
49
+}
90
+
50
+
91
+static const TypeInfo microbit_info = {
51
static inline bool arm_is_el2_enabled(CPUARMState *env)
92
+ .name = TYPE_MICROBIT_MACHINE,
52
{
93
+ .parent = TYPE_MACHINE,
53
return false;
94
+ .instance_size = sizeof(MicrobitMachineState),
54
@@ -XXX,XX +XXX,XX @@ static inline bool arm_is_el2_enabled(CPUARMState *env)
95
+ .class_init = microbit_machine_class_init,
55
* "for all purposes other than a direct read or write access of HCR_EL2."
96
+};
56
* Not included here is HCR_RW.
97
+
57
*/
98
+static void microbit_machine_init(void)
58
+uint64_t arm_hcr_el2_eff_secstate(CPUARMState *env, bool secure);
59
uint64_t arm_hcr_el2_eff(CPUARMState *env);
60
uint64_t arm_hcrx_el2_eff(CPUARMState *env);
61
62
diff --git a/target/arm/helper.c b/target/arm/helper.c
63
index XXXXXXX..XXXXXXX 100644
64
--- a/target/arm/helper.c
65
+++ b/target/arm/helper.c
66
@@ -XXX,XX +XXX,XX @@ static void hcr_writelow(CPUARMState *env, const ARMCPRegInfo *ri,
67
}
68
69
/*
70
- * Return the effective value of HCR_EL2.
71
+ * Return the effective value of HCR_EL2, at the given security state.
72
* Bits that are not included here:
73
* RW (read from SCR_EL3.RW as needed)
74
*/
75
-uint64_t arm_hcr_el2_eff(CPUARMState *env)
76
+uint64_t arm_hcr_el2_eff_secstate(CPUARMState *env, bool secure)
77
{
78
uint64_t ret = env->cp15.hcr_el2;
79
80
- if (!arm_is_el2_enabled(env)) {
81
+ if (!arm_is_el2_enabled_secstate(env, secure)) {
82
/*
83
* "This register has no effect if EL2 is not enabled in the
84
* current Security state". This is ARMv8.4-SecEL2 speak for
85
@@ -XXX,XX +XXX,XX @@ uint64_t arm_hcr_el2_eff(CPUARMState *env)
86
return ret;
87
}
88
89
+uint64_t arm_hcr_el2_eff(CPUARMState *env)
99
+{
90
+{
100
+ type_register_static(&microbit_info);
91
+ return arm_hcr_el2_eff_secstate(env, arm_is_secure_below_el3(env));
101
+}
92
+}
102
+
93
+
103
+type_init(microbit_machine_init);
94
/*
95
* Corresponds to ARM pseudocode function ELIsInHost().
96
*/
104
--
97
--
105
2.19.0
98
2.25.1
106
107
diff view generated by jsdifflib
1
From: Cédric Le Goater <clg@kaod.org>
1
From: Richard Henderson <richard.henderson@linaro.org>
2
2
3
aspeed i2c interrupts should be cleared by software only, and the bus
3
Rename the argument to is_secure_ptr, and introduce a
4
interrupt should be lowered when all interrupts have been cleared.
4
local variable is_secure with the value. We only write
5
back to the pointer toward the end of the function.
5
6
6
Signed-off-by: Cédric Le Goater <clg@kaod.org>
7
Message-id: 20180914063506.20815-2-clg@kaod.org
8
Reviewed-by: Peter Maydell <peter.maydell@linaro.org>
7
Reviewed-by: Peter Maydell <peter.maydell@linaro.org>
9
[PMM: drop TODO comment describing an issue which is
8
Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
10
fixed later in the patch series, and clean up commit message]
9
Message-id: 20221001162318.153420-15-richard.henderson@linaro.org
11
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
10
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
12
---
11
---
13
hw/i2c/aspeed_i2c.c | 16 ++++++++++++----
12
target/arm/ptw.c | 22 ++++++++++++----------
14
1 file changed, 12 insertions(+), 4 deletions(-)
13
1 file changed, 12 insertions(+), 10 deletions(-)
15
14
16
diff --git a/hw/i2c/aspeed_i2c.c b/hw/i2c/aspeed_i2c.c
15
diff --git a/target/arm/ptw.c b/target/arm/ptw.c
17
index XXXXXXX..XXXXXXX 100644
16
index XXXXXXX..XXXXXXX 100644
18
--- a/hw/i2c/aspeed_i2c.c
17
--- a/target/arm/ptw.c
19
+++ b/hw/i2c/aspeed_i2c.c
18
+++ b/target/arm/ptw.c
20
@@ -XXX,XX +XXX,XX @@
19
@@ -XXX,XX +XXX,XX @@ static bool ptw_attrs_are_device(CPUARMState *env, ARMCacheAttrs cacheattrs)
21
#define I2CD_AC_TIMING_REG2 0x08 /* Clock and AC Timing Control #1 */
20
22
#define I2CD_INTR_CTRL_REG 0x0c /* I2CD Interrupt Control */
21
/* Translate a S1 pagetable walk through S2 if needed. */
23
#define I2CD_INTR_STS_REG 0x10 /* I2CD Interrupt Status */
22
static hwaddr S1_ptw_translate(CPUARMState *env, ARMMMUIdx mmu_idx,
24
+
23
- hwaddr addr, bool *is_secure,
25
+#define I2CD_INTR_SLAVE_ADDR_MATCH (0x1 << 31) /* 0: addr1 1: addr2 */
24
+ hwaddr addr, bool *is_secure_ptr,
26
+#define I2CD_INTR_SLAVE_ADDR_RX_PENDING (0x1 << 30)
25
ARMMMUFaultInfo *fi)
27
+/* bits[19-16] Reserved */
28
+
29
+/* All bits below are cleared by writing 1 */
30
+#define I2CD_INTR_SLAVE_INACTIVE_TIMEOUT (0x1 << 15)
31
#define I2CD_INTR_SDA_DL_TIMEOUT (0x1 << 14)
32
#define I2CD_INTR_BUS_RECOVER_DONE (0x1 << 13)
33
#define I2CD_INTR_SMBUS_ALERT (0x1 << 12) /* Bus [0-3] only */
34
@@ -XXX,XX +XXX,XX @@
35
#define I2CD_INTR_SMBUS_DEV_ALERT_ADDR (0x1 << 10) /* Removed */
36
#define I2CD_INTR_SMBUS_DEF_ADDR (0x1 << 9) /* Removed */
37
#define I2CD_INTR_GCALL_ADDR (0x1 << 8) /* Removed */
38
-#define I2CD_INTR_SLAVE_MATCH (0x1 << 7) /* use RX_DONE */
39
+#define I2CD_INTR_SLAVE_ADDR_RX_MATCH (0x1 << 7) /* use RX_DONE */
40
#define I2CD_INTR_SCL_TIMEOUT (0x1 << 6)
41
#define I2CD_INTR_ABNORMAL (0x1 << 5)
42
#define I2CD_INTR_NORMAL_STOP (0x1 << 4)
43
@@ -XXX,XX +XXX,XX @@ static void aspeed_i2c_bus_handle_cmd(AspeedI2CBus *bus, uint64_t value)
44
{
26
{
45
bus->cmd &= ~0xFFFF;
27
- ARMMMUIdx s2_mmu_idx = *is_secure ? ARMMMUIdx_Stage2_S : ARMMMUIdx_Stage2;
46
bus->cmd |= value & 0xFFFF;
28
+ bool is_secure = *is_secure_ptr;
47
- bus->intr_status = 0;
29
+ ARMMMUIdx s2_mmu_idx = is_secure ? ARMMMUIdx_Stage2_S : ARMMMUIdx_Stage2;
48
30
49
if (bus->cmd & I2CD_M_START_CMD) {
31
if (arm_mmu_idx_is_stage1_of_2(mmu_idx) &&
50
uint8_t state = aspeed_i2c_get_state(bus) & I2CD_MACTIVE ?
32
- !regime_translation_disabled(env, s2_mmu_idx, *is_secure)) {
51
@@ -XXX,XX +XXX,XX @@ static void aspeed_i2c_bus_write(void *opaque, hwaddr offset,
33
+ !regime_translation_disabled(env, s2_mmu_idx, is_secure)) {
52
break;
34
GetPhysAddrResult s2 = {};
53
case I2CD_INTR_STS_REG:
35
int ret;
54
bus->intr_status &= ~(value & 0x7FFF);
36
55
- bus->controller->intr_status &= ~(1 << bus->id);
37
ret = get_phys_addr_lpae(env, addr, MMU_DATA_LOAD, s2_mmu_idx,
56
- qemu_irq_lower(bus->controller->irq);
38
- *is_secure, false, &s2, fi);
57
+ if (!bus->intr_status) {
39
+ is_secure, false, &s2, fi);
58
+ bus->controller->intr_status &= ~(1 << bus->id);
40
if (ret) {
59
+ qemu_irq_lower(bus->controller->irq);
41
assert(fi->type != ARMFault_None);
60
+ }
42
fi->s2addr = addr;
61
break;
43
fi->stage2 = true;
62
case I2CD_DEV_ADDR_REG:
44
fi->s1ptw = true;
63
qemu_log_mask(LOG_UNIMP, "%s: slave mode not implemented\n",
45
- fi->s1ns = !*is_secure;
46
+ fi->s1ns = !is_secure;
47
return ~0;
48
}
49
if ((arm_hcr_el2_eff(env) & HCR_PTW) &&
50
@@ -XXX,XX +XXX,XX @@ static hwaddr S1_ptw_translate(CPUARMState *env, ARMMMUIdx mmu_idx,
51
fi->s2addr = addr;
52
fi->stage2 = true;
53
fi->s1ptw = true;
54
- fi->s1ns = !*is_secure;
55
+ fi->s1ns = !is_secure;
56
return ~0;
57
}
58
59
if (arm_is_secure_below_el3(env)) {
60
/* Check if page table walk is to secure or non-secure PA space. */
61
- if (*is_secure) {
62
- *is_secure = !(env->cp15.vstcr_el2 & VSTCR_SW);
63
+ if (is_secure) {
64
+ is_secure = !(env->cp15.vstcr_el2 & VSTCR_SW);
65
} else {
66
- *is_secure = !(env->cp15.vtcr_el2 & VTCR_NSW);
67
+ is_secure = !(env->cp15.vtcr_el2 & VTCR_NSW);
68
}
69
+ *is_secure_ptr = is_secure;
70
} else {
71
- assert(!*is_secure);
72
+ assert(!is_secure);
73
}
74
75
addr = s2.phys;
64
--
76
--
65
2.19.0
77
2.25.1
66
67
diff view generated by jsdifflib
1
From: Bartlomiej Zolnierkiewicz <b.zolnierkie@samsung.com>
1
From: Richard Henderson <richard.henderson@linaro.org>
2
2
3
commit 97274d0c05d4 ("hw/char/exynos4210_uart.c: Remove unneeded
3
This value is unused.
4
handling of NULL chardev") broke Exynos4210 support as it removed
5
NULL 'Chardev *chr' handling from exynos4210_uart_create() and
6
currently exynos4210_init() always passes NULL as 'Chardev *chr'
7
argument to exynos4210_uart_create() calls. Fix it by adding
8
missing serial_hd() calls to exynos4210_init().
9
4
10
Signed-off-by: Bartlomiej Zolnierkiewicz <b.zolnierkie@samsung.com>
5
Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
11
Reviewed-by: Thomas Huth <thuth@redhat.com>
6
Reviewed-by: Peter Maydell <peter.maydell@linaro.org>
12
Reviewed-by: Philippe Mathieu-Daudé <f4bug@amsat.org>
7
Message-id: 20221001162318.153420-16-richard.henderson@linaro.org
13
Message-id: 9310418.Wg32kryeWE@amdc3058
14
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
8
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
15
---
9
---
16
hw/arm/exynos4210.c | 8 ++++----
10
target/arm/ptw.c | 5 ++---
17
1 file changed, 4 insertions(+), 4 deletions(-)
11
1 file changed, 2 insertions(+), 3 deletions(-)
18
12
19
diff --git a/hw/arm/exynos4210.c b/hw/arm/exynos4210.c
13
diff --git a/target/arm/ptw.c b/target/arm/ptw.c
20
index XXXXXXX..XXXXXXX 100644
14
index XXXXXXX..XXXXXXX 100644
21
--- a/hw/arm/exynos4210.c
15
--- a/target/arm/ptw.c
22
+++ b/hw/arm/exynos4210.c
16
+++ b/target/arm/ptw.c
23
@@ -XXX,XX +XXX,XX @@ Exynos4210State *exynos4210_init(MemoryRegion *system_mem)
17
@@ -XXX,XX +XXX,XX @@ static uint8_t force_cacheattr_nibble_wb(uint8_t attr)
24
18
* s1 and s2 for the HCR_EL2.FWB == 1 case, returning the
25
/*** UARTs ***/
19
* combined attributes in MAIR_EL1 format.
26
exynos4210_uart_create(EXYNOS4210_UART0_BASE_ADDR,
20
*/
27
- EXYNOS4210_UART0_FIFO_SIZE, 0, NULL,
21
-static uint8_t combined_attrs_fwb(CPUARMState *env,
28
+ EXYNOS4210_UART0_FIFO_SIZE, 0, serial_hd(0),
22
- ARMCacheAttrs s1, ARMCacheAttrs s2)
29
s->irq_table[exynos4210_get_irq(EXYNOS4210_UART_INT_GRP, 0)]);
23
+static uint8_t combined_attrs_fwb(ARMCacheAttrs s1, ARMCacheAttrs s2)
30
24
{
31
exynos4210_uart_create(EXYNOS4210_UART1_BASE_ADDR,
25
switch (s2.attrs) {
32
- EXYNOS4210_UART1_FIFO_SIZE, 1, NULL,
26
case 7:
33
+ EXYNOS4210_UART1_FIFO_SIZE, 1, serial_hd(1),
27
@@ -XXX,XX +XXX,XX @@ static ARMCacheAttrs combine_cacheattrs(CPUARMState *env,
34
s->irq_table[exynos4210_get_irq(EXYNOS4210_UART_INT_GRP, 1)]);
28
35
29
/* Combine memory type and cacheability attributes */
36
exynos4210_uart_create(EXYNOS4210_UART2_BASE_ADDR,
30
if (arm_hcr_el2_eff(env) & HCR_FWB) {
37
- EXYNOS4210_UART2_FIFO_SIZE, 2, NULL,
31
- ret.attrs = combined_attrs_fwb(env, s1, s2);
38
+ EXYNOS4210_UART2_FIFO_SIZE, 2, serial_hd(2),
32
+ ret.attrs = combined_attrs_fwb(s1, s2);
39
s->irq_table[exynos4210_get_irq(EXYNOS4210_UART_INT_GRP, 2)]);
33
} else {
40
34
ret.attrs = combined_attrs_nofwb(env, s1, s2);
41
exynos4210_uart_create(EXYNOS4210_UART3_BASE_ADDR,
35
}
42
- EXYNOS4210_UART3_FIFO_SIZE, 3, NULL,
43
+ EXYNOS4210_UART3_FIFO_SIZE, 3, serial_hd(3),
44
s->irq_table[exynos4210_get_irq(EXYNOS4210_UART_INT_GRP, 3)]);
45
46
/*** SD/MMC host controllers ***/
47
--
36
--
48
2.19.0
37
2.25.1
49
50
diff view generated by jsdifflib
1
From: Guenter Roeck <linux@roeck-us.net>
1
From: Richard Henderson <richard.henderson@linaro.org>
2
2
3
Receive command handling may have to be deferred if a previous receive
3
These subroutines did not need ENV for anything except
4
done interrupt was not yet acknowledged. Move receive command handling
4
retrieving the effective value of HCR anyway.
5
into a separate function to prepare for the necessary changes.
6
5
7
Signed-off-by: Guenter Roeck <linux@roeck-us.net>
6
We have computed the effective value of HCR in the callers,
8
Signed-off-by: Cédric Le Goater <clg@kaod.org>
7
and this will be especially important for interpreting HCR
9
Message-id: 20180914063506.20815-3-clg@kaod.org
8
in a non-current security state.
9
10
Reviewed-by: Peter Maydell <peter.maydell@linaro.org>
10
Reviewed-by: Peter Maydell <peter.maydell@linaro.org>
11
Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
12
Message-id: 20221001162318.153420-17-richard.henderson@linaro.org
11
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
13
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
12
---
14
---
13
hw/i2c/aspeed_i2c.c | 37 +++++++++++++++++++++----------------
15
target/arm/ptw.c | 30 +++++++++++++++++-------------
14
1 file changed, 21 insertions(+), 16 deletions(-)
16
1 file changed, 17 insertions(+), 13 deletions(-)
15
17
16
diff --git a/hw/i2c/aspeed_i2c.c b/hw/i2c/aspeed_i2c.c
18
diff --git a/target/arm/ptw.c b/target/arm/ptw.c
17
index XXXXXXX..XXXXXXX 100644
19
index XXXXXXX..XXXXXXX 100644
18
--- a/hw/i2c/aspeed_i2c.c
20
--- a/target/arm/ptw.c
19
+++ b/hw/i2c/aspeed_i2c.c
21
+++ b/target/arm/ptw.c
20
@@ -XXX,XX +XXX,XX @@ static uint8_t aspeed_i2c_get_state(AspeedI2CBus *bus)
22
@@ -XXX,XX +XXX,XX @@ static bool regime_translation_disabled(CPUARMState *env, ARMMMUIdx mmu_idx,
21
return (bus->cmd >> I2CD_TX_STATE_SHIFT) & I2CD_TX_STATE_MASK;
23
return (regime_sctlr(env, mmu_idx) & SCTLR_M) == 0;
22
}
24
}
23
25
24
+static void aspeed_i2c_handle_rx_cmd(AspeedI2CBus *bus)
26
-static bool ptw_attrs_are_device(CPUARMState *env, ARMCacheAttrs cacheattrs)
25
+{
27
+static bool ptw_attrs_are_device(uint64_t hcr, ARMCacheAttrs cacheattrs)
26
+ int ret;
28
{
29
/*
30
* For an S1 page table walk, the stage 1 attributes are always
31
@@ -XXX,XX +XXX,XX @@ static bool ptw_attrs_are_device(CPUARMState *env, ARMCacheAttrs cacheattrs)
32
* when cacheattrs.attrs bit [2] is 0.
33
*/
34
assert(cacheattrs.is_s2_format);
35
- if (arm_hcr_el2_eff(env) & HCR_FWB) {
36
+ if (hcr & HCR_FWB) {
37
return (cacheattrs.attrs & 0x4) == 0;
38
} else {
39
return (cacheattrs.attrs & 0xc) == 0;
40
@@ -XXX,XX +XXX,XX @@ static hwaddr S1_ptw_translate(CPUARMState *env, ARMMMUIdx mmu_idx,
41
if (arm_mmu_idx_is_stage1_of_2(mmu_idx) &&
42
!regime_translation_disabled(env, s2_mmu_idx, is_secure)) {
43
GetPhysAddrResult s2 = {};
44
+ uint64_t hcr;
45
int ret;
46
47
ret = get_phys_addr_lpae(env, addr, MMU_DATA_LOAD, s2_mmu_idx,
48
@@ -XXX,XX +XXX,XX @@ static hwaddr S1_ptw_translate(CPUARMState *env, ARMMMUIdx mmu_idx,
49
fi->s1ns = !is_secure;
50
return ~0;
51
}
52
- if ((arm_hcr_el2_eff(env) & HCR_PTW) &&
53
- ptw_attrs_are_device(env, s2.cacheattrs)) {
27
+
54
+
28
+ aspeed_i2c_set_state(bus, I2CD_MRXD);
55
+ hcr = arm_hcr_el2_eff(env);
29
+ ret = i2c_recv(bus->bus);
56
+ if ((hcr & HCR_PTW) && ptw_attrs_are_device(hcr, s2.cacheattrs)) {
30
+ if (ret < 0) {
57
/*
31
+ qemu_log_mask(LOG_GUEST_ERROR, "%s: read failed\n", __func__);
58
* PTW set and S1 walk touched S2 Device memory:
32
+ ret = 0xff;
59
* generate Permission fault.
33
+ } else {
60
@@ -XXX,XX +XXX,XX @@ static bool get_phys_addr_pmsav8(CPUARMState *env, uint32_t address,
34
+ bus->intr_status |= I2CD_INTR_RX_DONE;
61
* ref: shared/translation/attrs/S2AttrDecode()
35
+ }
62
* .../S2ConvertAttrsHints()
36
+ bus->buf = (ret & I2CD_BYTE_BUF_RX_MASK) << I2CD_BYTE_BUF_RX_SHIFT;
63
*/
37
+ if (bus->cmd & I2CD_M_S_RX_CMD_LAST) {
64
-static uint8_t convert_stage2_attrs(CPUARMState *env, uint8_t s2attrs)
38
+ i2c_nack(bus->bus);
65
+static uint8_t convert_stage2_attrs(uint64_t hcr, uint8_t s2attrs)
39
+ }
66
{
40
+ bus->cmd &= ~(I2CD_M_RX_CMD | I2CD_M_S_RX_CMD_LAST);
67
uint8_t hiattr = extract32(s2attrs, 2, 2);
41
+ aspeed_i2c_set_state(bus, I2CD_MACTIVE);
68
uint8_t loattr = extract32(s2attrs, 0, 2);
42
+}
69
uint8_t hihint = 0, lohint = 0;
43
+
70
44
/*
71
if (hiattr != 0) { /* normal memory */
45
* The state machine needs some refinement. It is only used to track
72
- if (arm_hcr_el2_eff(env) & HCR_CD) { /* cache disabled */
46
* invalid STOP commands for the moment.
73
+ if (hcr & HCR_CD) { /* cache disabled */
47
@@ -XXX,XX +XXX,XX @@ static void aspeed_i2c_bus_handle_cmd(AspeedI2CBus *bus, uint64_t value)
74
hiattr = loattr = 1; /* non-cacheable */
75
} else {
76
if (hiattr != 1) { /* Write-through or write-back */
77
@@ -XXX,XX +XXX,XX @@ static uint8_t combine_cacheattr_nibble(uint8_t s1, uint8_t s2)
78
* s1 and s2 for the HCR_EL2.FWB == 0 case, returning the
79
* combined attributes in MAIR_EL1 format.
80
*/
81
-static uint8_t combined_attrs_nofwb(CPUARMState *env,
82
+static uint8_t combined_attrs_nofwb(uint64_t hcr,
83
ARMCacheAttrs s1, ARMCacheAttrs s2)
84
{
85
uint8_t s1lo, s2lo, s1hi, s2hi, s2_mair_attrs, ret_attrs;
86
87
- s2_mair_attrs = convert_stage2_attrs(env, s2.attrs);
88
+ s2_mair_attrs = convert_stage2_attrs(hcr, s2.attrs);
89
90
s1lo = extract32(s1.attrs, 0, 4);
91
s2lo = extract32(s2_mair_attrs, 0, 4);
92
@@ -XXX,XX +XXX,XX @@ static uint8_t combined_attrs_fwb(ARMCacheAttrs s1, ARMCacheAttrs s2)
93
* @s1: Attributes from stage 1 walk
94
* @s2: Attributes from stage 2 walk
95
*/
96
-static ARMCacheAttrs combine_cacheattrs(CPUARMState *env,
97
+static ARMCacheAttrs combine_cacheattrs(uint64_t hcr,
98
ARMCacheAttrs s1, ARMCacheAttrs s2)
99
{
100
ARMCacheAttrs ret;
101
@@ -XXX,XX +XXX,XX @@ static ARMCacheAttrs combine_cacheattrs(CPUARMState *env,
48
}
102
}
49
103
50
if (bus->cmd & (I2CD_M_RX_CMD | I2CD_M_S_RX_CMD_LAST)) {
104
/* Combine memory type and cacheability attributes */
51
- int ret;
105
- if (arm_hcr_el2_eff(env) & HCR_FWB) {
52
-
106
+ if (hcr & HCR_FWB) {
53
- aspeed_i2c_set_state(bus, I2CD_MRXD);
107
ret.attrs = combined_attrs_fwb(s1, s2);
54
- ret = i2c_recv(bus->bus);
108
} else {
55
- if (ret < 0) {
109
- ret.attrs = combined_attrs_nofwb(env, s1, s2);
56
- qemu_log_mask(LOG_GUEST_ERROR, "%s: read failed\n", __func__);
110
+ ret.attrs = combined_attrs_nofwb(hcr, s1, s2);
57
- ret = 0xff;
58
- } else {
59
- bus->intr_status |= I2CD_INTR_RX_DONE;
60
- }
61
- bus->buf = (ret & I2CD_BYTE_BUF_RX_MASK) << I2CD_BYTE_BUF_RX_SHIFT;
62
- if (bus->cmd & I2CD_M_S_RX_CMD_LAST) {
63
- i2c_nack(bus->bus);
64
- }
65
- bus->cmd &= ~(I2CD_M_RX_CMD | I2CD_M_S_RX_CMD_LAST);
66
- aspeed_i2c_set_state(bus, I2CD_MACTIVE);
67
+ aspeed_i2c_handle_rx_cmd(bus);
68
}
111
}
69
112
70
if (bus->cmd & I2CD_M_STOP_CMD) {
113
/*
114
@@ -XXX,XX +XXX,XX @@ bool get_phys_addr_with_secure(CPUARMState *env, target_ulong address,
115
ARMCacheAttrs cacheattrs1;
116
ARMMMUIdx s2_mmu_idx;
117
bool is_el0;
118
+ uint64_t hcr;
119
120
ret = get_phys_addr_with_secure(env, address, access_type,
121
s1_mmu_idx, is_secure, result, fi);
122
@@ -XXX,XX +XXX,XX @@ bool get_phys_addr_with_secure(CPUARMState *env, target_ulong address,
123
}
124
125
/* Combine the S1 and S2 cache attributes. */
126
- if (arm_hcr_el2_eff(env) & HCR_DC) {
127
+ hcr = arm_hcr_el2_eff(env);
128
+ if (hcr & HCR_DC) {
129
/*
130
* HCR.DC forces the first stage attributes to
131
* Normal Non-Shareable,
132
@@ -XXX,XX +XXX,XX @@ bool get_phys_addr_with_secure(CPUARMState *env, target_ulong address,
133
}
134
cacheattrs1.shareability = 0;
135
}
136
- result->cacheattrs = combine_cacheattrs(env, cacheattrs1,
137
+ result->cacheattrs = combine_cacheattrs(hcr, cacheattrs1,
138
result->cacheattrs);
139
140
/*
71
--
141
--
72
2.19.0
142
2.25.1
73
74
diff view generated by jsdifflib
1
From: Cédric Le Goater <clg@kaod.org>
1
From: Richard Henderson <richard.henderson@linaro.org>
2
2
3
Signed-off-by: Cédric Le Goater <clg@kaod.org>
3
Use arm_hcr_el2_eff_secstate instead of arm_hcr_el2_eff, so
4
Reviewed-by: Philippe Mathieu-Daudé <f4bug@amsat.org>
4
that we use is_secure instead of the current security state.
5
Message-id: 20180921161939.822-6-clg@kaod.org
5
These AT* operations have been broken since arm_hcr_el2_eff
6
gained a check for "el2 enabled" for Secure EL2.
7
6
Reviewed-by: Peter Maydell <peter.maydell@linaro.org>
8
Reviewed-by: Peter Maydell <peter.maydell@linaro.org>
9
Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
10
Message-id: 20221001162318.153420-18-richard.henderson@linaro.org
7
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
11
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
8
---
12
---
9
hw/ssi/aspeed_smc.c | 8 ++++----
13
target/arm/ptw.c | 8 ++++----
10
1 file changed, 4 insertions(+), 4 deletions(-)
14
1 file changed, 4 insertions(+), 4 deletions(-)
11
15
12
diff --git a/hw/ssi/aspeed_smc.c b/hw/ssi/aspeed_smc.c
16
diff --git a/target/arm/ptw.c b/target/arm/ptw.c
13
index XXXXXXX..XXXXXXX 100644
17
index XXXXXXX..XXXXXXX 100644
14
--- a/hw/ssi/aspeed_smc.c
18
--- a/target/arm/ptw.c
15
+++ b/hw/ssi/aspeed_smc.c
19
+++ b/target/arm/ptw.c
16
@@ -XXX,XX +XXX,XX @@ static uint64_t aspeed_smc_flash_default_read(void *opaque, hwaddr addr,
20
@@ -XXX,XX +XXX,XX @@ static bool regime_translation_disabled(CPUARMState *env, ARMMMUIdx mmu_idx,
17
static void aspeed_smc_flash_default_write(void *opaque, hwaddr addr,
18
uint64_t data, unsigned size)
19
{
20
- qemu_log_mask(LOG_GUEST_ERROR, "%s: To 0x%" HWADDR_PRIx " of size %u: 0x%"
21
- PRIx64 "\n", __func__, addr, size, data);
22
+ qemu_log_mask(LOG_GUEST_ERROR, "%s: To 0x%" HWADDR_PRIx " of size %u: 0x%"
23
+ PRIx64 "\n", __func__, addr, size, data);
24
}
25
26
static const MemoryRegionOps aspeed_smc_flash_default_ops = {
27
@@ -XXX,XX +XXX,XX @@ static void aspeed_smc_flash_setup(AspeedSMCFlash *fl, uint32_t addr)
28
*/
29
if (aspeed_smc_flash_mode(fl) == CTRL_FREADMODE) {
30
for (i = 0; i < aspeed_smc_flash_dummies(fl); i++) {
31
- ssi_transfer(fl->controller->spi, 0xFF);
32
+ ssi_transfer(fl->controller->spi, 0xFF);
33
}
21
}
34
}
22
}
35
}
23
36
@@ -XXX,XX +XXX,XX @@ static uint64_t aspeed_smc_flash_read(void *opaque, hwaddr addr, unsigned size)
24
- hcr_el2 = arm_hcr_el2_eff(env);
37
}
25
+ hcr_el2 = arm_hcr_el2_eff_secstate(env, is_secure);
38
26
39
static void aspeed_smc_flash_write(void *opaque, hwaddr addr, uint64_t data,
27
switch (mmu_idx) {
40
- unsigned size)
28
case ARMMMUIdx_Stage2:
41
+ unsigned size)
29
@@ -XXX,XX +XXX,XX @@ static hwaddr S1_ptw_translate(CPUARMState *env, ARMMMUIdx mmu_idx,
42
{
30
return ~0;
43
AspeedSMCFlash *fl = opaque;
31
}
44
AspeedSMCState *s = fl->controller;
32
33
- hcr = arm_hcr_el2_eff(env);
34
+ hcr = arm_hcr_el2_eff_secstate(env, is_secure);
35
if ((hcr & HCR_PTW) && ptw_attrs_are_device(hcr, s2.cacheattrs)) {
36
/*
37
* PTW set and S1 walk touched S2 Device memory:
38
@@ -XXX,XX +XXX,XX @@ bool get_phys_addr_with_secure(CPUARMState *env, target_ulong address,
39
}
40
41
/* Combine the S1 and S2 cache attributes. */
42
- hcr = arm_hcr_el2_eff(env);
43
+ hcr = arm_hcr_el2_eff_secstate(env, is_secure);
44
if (hcr & HCR_DC) {
45
/*
46
* HCR.DC forces the first stage attributes to
47
@@ -XXX,XX +XXX,XX @@ bool get_phys_addr_with_secure(CPUARMState *env, target_ulong address,
48
result->page_size = TARGET_PAGE_SIZE;
49
50
/* Fill in cacheattr a-la AArch64.TranslateAddressS1Off. */
51
- hcr = arm_hcr_el2_eff(env);
52
+ hcr = arm_hcr_el2_eff_secstate(env, is_secure);
53
result->cacheattrs.shareability = 0;
54
result->cacheattrs.is_s2_format = false;
55
if (hcr & HCR_DC) {
45
--
56
--
46
2.19.0
57
2.25.1
47
48
diff view generated by jsdifflib
1
From: Joel Stanley <joel@jms.id.au>
1
From: Richard Henderson <richard.henderson@linaro.org>
2
2
3
The nRF51 is a Cortex-M0 microcontroller with an on-board radio module,
4
plus other common ARM SoC peripherals.
5
6
http://infocenter.nordicsemi.com/pdf/nRF51_RM_v3.0.pdf
7
8
This defines a basic model of the CPU and memory, with no peripherals
9
implemented at this stage.
10
11
Signed-off-by: Joel Stanley <joel@jms.id.au>
12
Message-id: 20180831220920.27113-3-joel@jms.id.au
13
Reviewed-by: Peter Maydell <peter.maydell@linaro.org>
3
Reviewed-by: Peter Maydell <peter.maydell@linaro.org>
14
[PMM: wrapped a few long lines]
4
Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
5
Message-id: 20221001162318.153420-19-richard.henderson@linaro.org
15
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
6
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
16
---
7
---
17
hw/arm/Makefile.objs | 1 +
8
target/arm/ptw.c | 138 +++++++++++++++++++++++++----------------------
18
include/hw/arm/nrf51_soc.h | 41 ++++++++++
9
1 file changed, 74 insertions(+), 64 deletions(-)
19
hw/arm/nrf51_soc.c | 133 ++++++++++++++++++++++++++++++++
20
default-configs/arm-softmmu.mak | 1 +
21
4 files changed, 176 insertions(+)
22
create mode 100644 include/hw/arm/nrf51_soc.h
23
create mode 100644 hw/arm/nrf51_soc.c
24
10
25
diff --git a/hw/arm/Makefile.objs b/hw/arm/Makefile.objs
11
diff --git a/target/arm/ptw.c b/target/arm/ptw.c
26
index XXXXXXX..XXXXXXX 100644
12
index XXXXXXX..XXXXXXX 100644
27
--- a/hw/arm/Makefile.objs
13
--- a/target/arm/ptw.c
28
+++ b/hw/arm/Makefile.objs
14
+++ b/target/arm/ptw.c
29
@@ -XXX,XX +XXX,XX @@ obj-$(CONFIG_IOTKIT) += iotkit.o
15
@@ -XXX,XX +XXX,XX @@ static ARMCacheAttrs combine_cacheattrs(uint64_t hcr,
30
obj-$(CONFIG_FSL_IMX7) += fsl-imx7.o mcimx7d-sabre.o
16
return ret;
31
obj-$(CONFIG_ARM_SMMUV3) += smmu-common.o smmuv3.o
17
}
32
obj-$(CONFIG_FSL_IMX6UL) += fsl-imx6ul.o mcimx6ul-evk.o
18
33
+obj-$(CONFIG_NRF51_SOC) += nrf51_soc.o
34
diff --git a/include/hw/arm/nrf51_soc.h b/include/hw/arm/nrf51_soc.h
35
new file mode 100644
36
index XXXXXXX..XXXXXXX
37
--- /dev/null
38
+++ b/include/hw/arm/nrf51_soc.h
39
@@ -XXX,XX +XXX,XX @@
40
+/*
19
+/*
41
+ * Nordic Semiconductor nRF51 SoC
20
+ * MMU disabled. S1 addresses within aa64 translation regimes are
42
+ *
21
+ * still checked for bounds -- see AArch64.S1DisabledOutput().
43
+ * Copyright 2018 Joel Stanley <joel@jms.id.au>
44
+ *
45
+ * This code is licensed under the GPL version 2 or later. See
46
+ * the COPYING file in the top-level directory.
47
+ */
22
+ */
23
+static bool get_phys_addr_disabled(CPUARMState *env, target_ulong address,
24
+ MMUAccessType access_type,
25
+ ARMMMUIdx mmu_idx, bool is_secure,
26
+ GetPhysAddrResult *result,
27
+ ARMMMUFaultInfo *fi)
28
+{
29
+ uint64_t hcr;
30
+ uint8_t memattr;
48
+
31
+
49
+#ifndef NRF51_SOC_H
32
+ if (mmu_idx != ARMMMUIdx_Stage2 && mmu_idx != ARMMMUIdx_Stage2_S) {
50
+#define NRF51_SOC_H
33
+ int r_el = regime_el(env, mmu_idx);
34
+ if (arm_el_is_aa64(env, r_el)) {
35
+ int pamax = arm_pamax(env_archcpu(env));
36
+ uint64_t tcr = env->cp15.tcr_el[r_el];
37
+ int addrtop, tbi;
51
+
38
+
52
+#include "hw/sysbus.h"
39
+ tbi = aa64_va_parameter_tbi(tcr, mmu_idx);
53
+#include "hw/arm/armv7m.h"
40
+ if (access_type == MMU_INST_FETCH) {
41
+ tbi &= ~aa64_va_parameter_tbid(tcr, mmu_idx);
42
+ }
43
+ tbi = (tbi >> extract64(address, 55, 1)) & 1;
44
+ addrtop = (tbi ? 55 : 63);
54
+
45
+
55
+#define TYPE_NRF51_SOC "nrf51-soc"
46
+ if (extract64(address, pamax, addrtop - pamax + 1) != 0) {
56
+#define NRF51_SOC(obj) \
47
+ fi->type = ARMFault_AddressSize;
57
+ OBJECT_CHECK(NRF51State, (obj), TYPE_NRF51_SOC)
48
+ fi->level = 0;
49
+ fi->stage2 = false;
50
+ return 1;
51
+ }
58
+
52
+
59
+typedef struct NRF51State {
53
+ /*
60
+ /*< private >*/
54
+ * When TBI is disabled, we've just validated that all of the
61
+ SysBusDevice parent_obj;
55
+ * bits above PAMax are zero, so logically we only need to
62
+
56
+ * clear the top byte for TBI. But it's clearer to follow
63
+ /*< public >*/
57
+ * the pseudocode set of addrdesc.paddress.
64
+ ARMv7MState cpu;
58
+ */
65
+
59
+ address = extract64(address, 0, 52);
66
+ MemoryRegion iomem;
60
+ }
67
+ MemoryRegion sram;
68
+ MemoryRegion flash;
69
+
70
+ uint32_t sram_size;
71
+ uint32_t flash_size;
72
+
73
+ MemoryRegion *board_memory;
74
+
75
+ MemoryRegion container;
76
+
77
+} NRF51State;
78
+
79
+#endif
80
+
81
diff --git a/hw/arm/nrf51_soc.c b/hw/arm/nrf51_soc.c
82
new file mode 100644
83
index XXXXXXX..XXXXXXX
84
--- /dev/null
85
+++ b/hw/arm/nrf51_soc.c
86
@@ -XXX,XX +XXX,XX @@
87
+/*
88
+ * Nordic Semiconductor nRF51 SoC
89
+ * http://infocenter.nordicsemi.com/pdf/nRF51_RM_v3.0.1.pdf
90
+ *
91
+ * Copyright 2018 Joel Stanley <joel@jms.id.au>
92
+ *
93
+ * This code is licensed under the GPL version 2 or later. See
94
+ * the COPYING file in the top-level directory.
95
+ */
96
+
97
+#include "qemu/osdep.h"
98
+#include "qapi/error.h"
99
+#include "qemu-common.h"
100
+#include "hw/arm/arm.h"
101
+#include "hw/sysbus.h"
102
+#include "hw/boards.h"
103
+#include "hw/devices.h"
104
+#include "hw/misc/unimp.h"
105
+#include "exec/address-spaces.h"
106
+#include "sysemu/sysemu.h"
107
+#include "qemu/log.h"
108
+#include "cpu.h"
109
+
110
+#include "hw/arm/nrf51_soc.h"
111
+
112
+#define IOMEM_BASE 0x40000000
113
+#define IOMEM_SIZE 0x20000000
114
+
115
+#define FICR_BASE 0x10000000
116
+#define FICR_SIZE 0x000000fc
117
+
118
+#define FLASH_BASE 0x00000000
119
+#define SRAM_BASE 0x20000000
120
+
121
+#define PRIVATE_BASE 0xF0000000
122
+#define PRIVATE_SIZE 0x10000000
123
+
124
+/*
125
+ * The size and base is for the NRF51822 part. If other parts
126
+ * are supported in the future, add a sub-class of NRF51SoC for
127
+ * the specific variants
128
+ */
129
+#define NRF51822_FLASH_SIZE (256 * 1024)
130
+#define NRF51822_SRAM_SIZE (16 * 1024)
131
+
132
+static void nrf51_soc_realize(DeviceState *dev_soc, Error **errp)
133
+{
134
+ NRF51State *s = NRF51_SOC(dev_soc);
135
+ Error *err = NULL;
136
+
137
+ if (!s->board_memory) {
138
+ error_setg(errp, "memory property was not set");
139
+ return;
140
+ }
61
+ }
141
+
62
+
142
+ object_property_set_link(OBJECT(&s->cpu), OBJECT(&s->container), "memory",
63
+ result->phys = address;
143
+ &err);
64
+ result->prot = PAGE_READ | PAGE_WRITE | PAGE_EXEC;
144
+ if (err) {
65
+ result->page_size = TARGET_PAGE_SIZE;
145
+ error_propagate(errp, err);
66
+
146
+ return;
67
+ /* Fill in cacheattr a-la AArch64.TranslateAddressS1Off. */
68
+ hcr = arm_hcr_el2_eff_secstate(env, is_secure);
69
+ result->cacheattrs.shareability = 0;
70
+ result->cacheattrs.is_s2_format = false;
71
+ if (hcr & HCR_DC) {
72
+ if (hcr & HCR_DCT) {
73
+ memattr = 0xf0; /* Tagged, Normal, WB, RWA */
74
+ } else {
75
+ memattr = 0xff; /* Normal, WB, RWA */
76
+ }
77
+ } else if (access_type == MMU_INST_FETCH) {
78
+ if (regime_sctlr(env, mmu_idx) & SCTLR_I) {
79
+ memattr = 0xee; /* Normal, WT, RA, NT */
80
+ } else {
81
+ memattr = 0x44; /* Normal, NC, No */
82
+ }
83
+ result->cacheattrs.shareability = 2; /* outer sharable */
84
+ } else {
85
+ memattr = 0x00; /* Device, nGnRnE */
147
+ }
86
+ }
148
+ object_property_set_bool(OBJECT(&s->cpu), true, "realized", &err);
87
+ result->cacheattrs.attrs = memattr;
149
+ if (err) {
88
+ return 0;
150
+ error_propagate(errp, err);
151
+ return;
152
+ }
153
+
154
+ memory_region_add_subregion_overlap(&s->container, 0, s->board_memory, -1);
155
+
156
+ memory_region_init_rom(&s->flash, OBJECT(s), "nrf51.flash", s->flash_size,
157
+ &err);
158
+ if (err) {
159
+ error_propagate(errp, err);
160
+ return;
161
+ }
162
+ memory_region_add_subregion(&s->container, FLASH_BASE, &s->flash);
163
+
164
+ memory_region_init_ram(&s->sram, NULL, "nrf51.sram", s->sram_size, &err);
165
+ if (err) {
166
+ error_propagate(errp, err);
167
+ return;
168
+ }
169
+ memory_region_add_subregion(&s->container, SRAM_BASE, &s->sram);
170
+
171
+ create_unimplemented_device("nrf51_soc.io", IOMEM_BASE, IOMEM_SIZE);
172
+ create_unimplemented_device("nrf51_soc.ficr", FICR_BASE, FICR_SIZE);
173
+ create_unimplemented_device("nrf51_soc.private",
174
+ PRIVATE_BASE, PRIVATE_SIZE);
175
+}
89
+}
176
+
90
+
177
+static void nrf51_soc_init(Object *obj)
91
bool get_phys_addr_with_secure(CPUARMState *env, target_ulong address,
178
+{
92
MMUAccessType access_type, ARMMMUIdx mmu_idx,
179
+ NRF51State *s = NRF51_SOC(obj);
93
bool is_secure, GetPhysAddrResult *result,
180
+
94
@@ -XXX,XX +XXX,XX @@ bool get_phys_addr_with_secure(CPUARMState *env, target_ulong address,
181
+ memory_region_init(&s->container, obj, "nrf51-container", UINT64_MAX);
95
/* Definitely a real MMU, not an MPU */
182
+
96
183
+ sysbus_init_child_obj(OBJECT(s), "armv6m", OBJECT(&s->cpu), sizeof(s->cpu),
97
if (regime_translation_disabled(env, mmu_idx, is_secure)) {
184
+ TYPE_ARMV7M);
98
- uint64_t hcr;
185
+ qdev_prop_set_string(DEVICE(&s->cpu), "cpu-type",
99
- uint8_t memattr;
186
+ ARM_CPU_TYPE_NAME("cortex-m0"));
100
-
187
+ qdev_prop_set_uint32(DEVICE(&s->cpu), "num-irq", 32);
101
- /*
188
+}
102
- * MMU disabled. S1 addresses within aa64 translation regimes are
189
+
103
- * still checked for bounds -- see AArch64.TranslateAddressS1Off.
190
+static Property nrf51_soc_properties[] = {
104
- */
191
+ DEFINE_PROP_LINK("memory", NRF51State, board_memory, TYPE_MEMORY_REGION,
105
- if (mmu_idx != ARMMMUIdx_Stage2 && mmu_idx != ARMMMUIdx_Stage2_S) {
192
+ MemoryRegion *),
106
- int r_el = regime_el(env, mmu_idx);
193
+ DEFINE_PROP_UINT32("sram-size", NRF51State, sram_size, NRF51822_SRAM_SIZE),
107
- if (arm_el_is_aa64(env, r_el)) {
194
+ DEFINE_PROP_UINT32("flash-size", NRF51State, flash_size,
108
- int pamax = arm_pamax(env_archcpu(env));
195
+ NRF51822_FLASH_SIZE),
109
- uint64_t tcr = env->cp15.tcr_el[r_el];
196
+ DEFINE_PROP_END_OF_LIST(),
110
- int addrtop, tbi;
197
+};
111
-
198
+
112
- tbi = aa64_va_parameter_tbi(tcr, mmu_idx);
199
+static void nrf51_soc_class_init(ObjectClass *klass, void *data)
113
- if (access_type == MMU_INST_FETCH) {
200
+{
114
- tbi &= ~aa64_va_parameter_tbid(tcr, mmu_idx);
201
+ DeviceClass *dc = DEVICE_CLASS(klass);
115
- }
202
+
116
- tbi = (tbi >> extract64(address, 55, 1)) & 1;
203
+ dc->realize = nrf51_soc_realize;
117
- addrtop = (tbi ? 55 : 63);
204
+ dc->props = nrf51_soc_properties;
118
-
205
+}
119
- if (extract64(address, pamax, addrtop - pamax + 1) != 0) {
206
+
120
- fi->type = ARMFault_AddressSize;
207
+static const TypeInfo nrf51_soc_info = {
121
- fi->level = 0;
208
+ .name = TYPE_NRF51_SOC,
122
- fi->stage2 = false;
209
+ .parent = TYPE_SYS_BUS_DEVICE,
123
- return 1;
210
+ .instance_size = sizeof(NRF51State),
124
- }
211
+ .instance_init = nrf51_soc_init,
125
-
212
+ .class_init = nrf51_soc_class_init,
126
- /*
213
+};
127
- * When TBI is disabled, we've just validated that all of the
214
+
128
- * bits above PAMax are zero, so logically we only need to
215
+static void nrf51_soc_types(void)
129
- * clear the top byte for TBI. But it's clearer to follow
216
+{
130
- * the pseudocode set of addrdesc.paddress.
217
+ type_register_static(&nrf51_soc_info);
131
- */
218
+}
132
- address = extract64(address, 0, 52);
219
+type_init(nrf51_soc_types)
133
- }
220
diff --git a/default-configs/arm-softmmu.mak b/default-configs/arm-softmmu.mak
134
- }
221
index XXXXXXX..XXXXXXX 100644
135
- result->phys = address;
222
--- a/default-configs/arm-softmmu.mak
136
- result->prot = PAGE_READ | PAGE_WRITE | PAGE_EXEC;
223
+++ b/default-configs/arm-softmmu.mak
137
- result->page_size = TARGET_PAGE_SIZE;
224
@@ -XXX,XX +XXX,XX @@ CONFIG_STM32F2XX_SYSCFG=y
138
-
225
CONFIG_STM32F2XX_ADC=y
139
- /* Fill in cacheattr a-la AArch64.TranslateAddressS1Off. */
226
CONFIG_STM32F2XX_SPI=y
140
- hcr = arm_hcr_el2_eff_secstate(env, is_secure);
227
CONFIG_STM32F205_SOC=y
141
- result->cacheattrs.shareability = 0;
228
+CONFIG_NRF51_SOC=y
142
- result->cacheattrs.is_s2_format = false;
229
143
- if (hcr & HCR_DC) {
230
CONFIG_CMSDK_APB_TIMER=y
144
- if (hcr & HCR_DCT) {
231
CONFIG_CMSDK_APB_DUALTIMER=y
145
- memattr = 0xf0; /* Tagged, Normal, WB, RWA */
146
- } else {
147
- memattr = 0xff; /* Normal, WB, RWA */
148
- }
149
- } else if (access_type == MMU_INST_FETCH) {
150
- if (regime_sctlr(env, mmu_idx) & SCTLR_I) {
151
- memattr = 0xee; /* Normal, WT, RA, NT */
152
- } else {
153
- memattr = 0x44; /* Normal, NC, No */
154
- }
155
- result->cacheattrs.shareability = 2; /* outer sharable */
156
- } else {
157
- memattr = 0x00; /* Device, nGnRnE */
158
- }
159
- result->cacheattrs.attrs = memattr;
160
- return 0;
161
+ return get_phys_addr_disabled(env, address, access_type, mmu_idx,
162
+ is_secure, result, fi);
163
}
164
-
165
if (regime_using_lpae_format(env, mmu_idx)) {
166
return get_phys_addr_lpae(env, address, access_type, mmu_idx,
167
is_secure, false, result, fi);
232
--
168
--
233
2.19.0
169
2.25.1
234
235
diff view generated by jsdifflib
1
From: Shannon Zhao <shannon.zhaosl@gmail.com>
1
From: Richard Henderson <richard.henderson@linaro.org>
2
2
3
Like commit 16b4226(hw/acpi-build: Add a check for memory-less NUMA node
3
Do not apply memattr or shareability for Stage2 translations.
4
), it also needs to check memory length for NUMA nodes on ARM.
4
Make sure to apply HCR_{DC,DCT} only to Regime_EL10, per the
5
pseudocode in AArch64.S1DisabledOutput.
5
6
6
Signed-off-by: Shannon Zhao <shannon.zhaosl@gmail.com>
7
Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
7
Reviewed-by: Andrew Jones <drjones@redhat.com>
8
Reviewed-by: Peter Maydell <peter.maydell@linaro.org>
8
Message-id: 20180911112643.19296-1-shenglong.zsl@alibaba-inc.com
9
Message-id: 20221001162318.153420-20-richard.henderson@linaro.org
9
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
10
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
10
---
11
---
11
hw/arm/virt-acpi-build.c | 10 ++++++----
12
target/arm/ptw.c | 48 +++++++++++++++++++++++++-----------------------
12
1 file changed, 6 insertions(+), 4 deletions(-)
13
1 file changed, 25 insertions(+), 23 deletions(-)
13
14
14
diff --git a/hw/arm/virt-acpi-build.c b/hw/arm/virt-acpi-build.c
15
diff --git a/target/arm/ptw.c b/target/arm/ptw.c
15
index XXXXXXX..XXXXXXX 100644
16
index XXXXXXX..XXXXXXX 100644
16
--- a/hw/arm/virt-acpi-build.c
17
--- a/target/arm/ptw.c
17
+++ b/hw/arm/virt-acpi-build.c
18
+++ b/target/arm/ptw.c
18
@@ -XXX,XX +XXX,XX @@ build_srat(GArray *table_data, BIOSLinker *linker, VirtMachineState *vms)
19
@@ -XXX,XX +XXX,XX @@ static bool get_phys_addr_disabled(CPUARMState *env, target_ulong address,
19
20
GetPhysAddrResult *result,
20
mem_base = vms->memmap[VIRT_MEM].base;
21
ARMMMUFaultInfo *fi)
21
for (i = 0; i < nb_numa_nodes; ++i) {
22
{
22
- numamem = acpi_data_push(table_data, sizeof(*numamem));
23
- uint64_t hcr;
23
- build_srat_memory(numamem, mem_base, numa_info[i].node_mem, i,
24
- uint8_t memattr;
24
- MEM_AFFINITY_ENABLED);
25
+ uint8_t memattr = 0x00; /* Device nGnRnE */
25
- mem_base += numa_info[i].node_mem;
26
+ uint8_t shareability = 0; /* non-sharable */
26
+ if (numa_info[i].node_mem > 0) {
27
27
+ numamem = acpi_data_push(table_data, sizeof(*numamem));
28
if (mmu_idx != ARMMMUIdx_Stage2 && mmu_idx != ARMMMUIdx_Stage2_S) {
28
+ build_srat_memory(numamem, mem_base, numa_info[i].node_mem, i,
29
int r_el = regime_el(env, mmu_idx);
29
+ MEM_AFFINITY_ENABLED);
30
+
30
+ mem_base += numa_info[i].node_mem;
31
if (arm_el_is_aa64(env, r_el)) {
32
int pamax = arm_pamax(env_archcpu(env));
33
uint64_t tcr = env->cp15.tcr_el[r_el];
34
@@ -XXX,XX +XXX,XX @@ static bool get_phys_addr_disabled(CPUARMState *env, target_ulong address,
35
*/
36
address = extract64(address, 0, 52);
37
}
38
+
39
+ /* Fill in cacheattr a-la AArch64.TranslateAddressS1Off. */
40
+ if (r_el == 1) {
41
+ uint64_t hcr = arm_hcr_el2_eff_secstate(env, is_secure);
42
+ if (hcr & HCR_DC) {
43
+ if (hcr & HCR_DCT) {
44
+ memattr = 0xf0; /* Tagged, Normal, WB, RWA */
45
+ } else {
46
+ memattr = 0xff; /* Normal, WB, RWA */
47
+ }
48
+ }
31
+ }
49
+ }
50
+ if (memattr == 0 && access_type == MMU_INST_FETCH) {
51
+ if (regime_sctlr(env, mmu_idx) & SCTLR_I) {
52
+ memattr = 0xee; /* Normal, WT, RA, NT */
53
+ } else {
54
+ memattr = 0x44; /* Normal, NC, No */
55
+ }
56
+ shareability = 2; /* outer sharable */
57
+ }
58
+ result->cacheattrs.is_s2_format = false;
32
}
59
}
33
60
34
build_header(linker, table_data, (void *)(table_data->data + srat_start),
61
result->phys = address;
62
result->prot = PAGE_READ | PAGE_WRITE | PAGE_EXEC;
63
result->page_size = TARGET_PAGE_SIZE;
64
-
65
- /* Fill in cacheattr a-la AArch64.TranslateAddressS1Off. */
66
- hcr = arm_hcr_el2_eff_secstate(env, is_secure);
67
- result->cacheattrs.shareability = 0;
68
- result->cacheattrs.is_s2_format = false;
69
- if (hcr & HCR_DC) {
70
- if (hcr & HCR_DCT) {
71
- memattr = 0xf0; /* Tagged, Normal, WB, RWA */
72
- } else {
73
- memattr = 0xff; /* Normal, WB, RWA */
74
- }
75
- } else if (access_type == MMU_INST_FETCH) {
76
- if (regime_sctlr(env, mmu_idx) & SCTLR_I) {
77
- memattr = 0xee; /* Normal, WT, RA, NT */
78
- } else {
79
- memattr = 0x44; /* Normal, NC, No */
80
- }
81
- result->cacheattrs.shareability = 2; /* outer sharable */
82
- } else {
83
- memattr = 0x00; /* Device, nGnRnE */
84
- }
85
+ result->cacheattrs.shareability = shareability;
86
result->cacheattrs.attrs = memattr;
87
return 0;
88
}
35
--
89
--
36
2.19.0
90
2.25.1
37
38
diff view generated by jsdifflib
1
From: Richard Henderson <richard.henderson@linaro.org>
1
From: Richard Henderson <richard.henderson@linaro.org>
2
2
3
Not only are the sve-related tb_flags fields unused when SVE is
3
Adjust GetPhysAddrResult to fill in CPUTLBEntryFull,
4
disabled, but not all of the cpu registers are initialized properly
4
so that it may be passed directly to tlb_set_page_full.
5
for computing same. This can corrupt other fields by ORing in -1,
6
which might result in QEMU crashing.
7
5
8
This bug was not present in 3.0, but this patch is cc'd to
6
The change is large, but mostly mechanical. The major
9
stable because adf92eab90e3f5f34c285 where the bug was
7
non-mechanical change is page_size -> lg_page_size.
10
introduced was marked for stable.
8
Most of the time this is obvious, and is related to
9
TARGET_PAGE_BITS.
11
10
12
Fixes: adf92eab90e3f5f34c285
13
Cc: qemu-stable@nongnu.org (3.0.1)
14
Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
11
Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
15
Reviewed-by: Peter Maydell <peter.maydell@linaro.org>
12
Reviewed-by: Peter Maydell <peter.maydell@linaro.org>
13
Message-id: 20221001162318.153420-21-richard.henderson@linaro.org
16
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
14
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
17
---
15
---
18
target/arm/helper.c | 45 ++++++++++++++++++++++++---------------------
16
target/arm/internals.h | 5 +-
19
1 file changed, 24 insertions(+), 21 deletions(-)
17
target/arm/helper.c | 12 +--
18
target/arm/m_helper.c | 20 ++---
19
target/arm/ptw.c | 179 ++++++++++++++++++++--------------------
20
target/arm/tlb_helper.c | 9 +-
21
5 files changed, 111 insertions(+), 114 deletions(-)
20
22
23
diff --git a/target/arm/internals.h b/target/arm/internals.h
24
index XXXXXXX..XXXXXXX 100644
25
--- a/target/arm/internals.h
26
+++ b/target/arm/internals.h
27
@@ -XXX,XX +XXX,XX @@ typedef struct ARMCacheAttrs {
28
29
/* Fields that are valid upon success. */
30
typedef struct GetPhysAddrResult {
31
- hwaddr phys;
32
- target_ulong page_size;
33
- int prot;
34
- MemTxAttrs attrs;
35
+ CPUTLBEntryFull f;
36
ARMCacheAttrs cacheattrs;
37
} GetPhysAddrResult;
38
21
diff --git a/target/arm/helper.c b/target/arm/helper.c
39
diff --git a/target/arm/helper.c b/target/arm/helper.c
22
index XXXXXXX..XXXXXXX 100644
40
index XXXXXXX..XXXXXXX 100644
23
--- a/target/arm/helper.c
41
--- a/target/arm/helper.c
24
+++ b/target/arm/helper.c
42
+++ b/target/arm/helper.c
25
@@ -XXX,XX +XXX,XX @@ void cpu_get_tb_cpu_state(CPUARMState *env, target_ulong *pc,
43
@@ -XXX,XX +XXX,XX @@ static uint64_t do_ats_write(CPUARMState *env, uint64_t value,
26
uint32_t flags;
44
/* Create a 64-bit PAR */
27
45
par64 = (1 << 11); /* LPAE bit always set */
28
if (is_a64(env)) {
46
if (!ret) {
29
- int sve_el = sve_exception_el(env);
47
- par64 |= res.phys & ~0xfffULL;
30
- uint32_t zcr_len;
48
- if (!res.attrs.secure) {
31
-
49
+ par64 |= res.f.phys_addr & ~0xfffULL;
32
*pc = env->pc;
50
+ if (!res.f.attrs.secure) {
33
flags = ARM_TBFLAG_AARCH64_STATE_MASK;
51
par64 |= (1 << 9); /* NS */
34
/* Get control bits for tagged addresses */
52
}
35
flags |= (arm_regime_tbi0(env, mmu_idx) << ARM_TBFLAG_TBI0_SHIFT);
53
par64 |= (uint64_t)res.cacheattrs.attrs << 56; /* ATTR */
36
flags |= (arm_regime_tbi1(env, mmu_idx) << ARM_TBFLAG_TBI1_SHIFT);
54
@@ -XXX,XX +XXX,XX @@ static uint64_t do_ats_write(CPUARMState *env, uint64_t value,
37
- flags |= sve_el << ARM_TBFLAG_SVEEXC_EL_SHIFT;
55
*/
38
56
if (!ret) {
39
- /* If SVE is disabled, but FP is enabled,
57
/* We do not set any attribute bits in the PAR */
40
- then the effective len is 0. */
58
- if (res.page_size == (1 << 24)
41
- if (sve_el != 0 && fp_el == 0) {
59
+ if (res.f.lg_page_size == 24
42
- zcr_len = 0;
60
&& arm_feature(env, ARM_FEATURE_V7)) {
43
- } else {
61
- par64 = (res.phys & 0xff000000) | (1 << 1);
44
- int current_el = arm_current_el(env);
62
+ par64 = (res.f.phys_addr & 0xff000000) | (1 << 1);
45
- ARMCPU *cpu = arm_env_get_cpu(env);
63
} else {
46
+ if (arm_feature(env, ARM_FEATURE_SVE)) {
64
- par64 = res.phys & 0xfffff000;
47
+ int sve_el = sve_exception_el(env);
65
+ par64 = res.f.phys_addr & 0xfffff000;
48
+ uint32_t zcr_len;
66
}
49
67
- if (!res.attrs.secure) {
50
- zcr_len = cpu->sve_max_vq - 1;
68
+ if (!res.f.attrs.secure) {
51
- if (current_el <= 1) {
69
par64 |= (1 << 9); /* NS */
52
- zcr_len = MIN(zcr_len, 0xf & (uint32_t)env->vfp.zcr_el[1]);
70
}
53
- }
71
} else {
54
- if (current_el < 2 && arm_feature(env, ARM_FEATURE_EL2)) {
72
diff --git a/target/arm/m_helper.c b/target/arm/m_helper.c
55
- zcr_len = MIN(zcr_len, 0xf & (uint32_t)env->vfp.zcr_el[2]);
73
index XXXXXXX..XXXXXXX 100644
56
- }
74
--- a/target/arm/m_helper.c
57
- if (current_el < 3 && arm_feature(env, ARM_FEATURE_EL3)) {
75
+++ b/target/arm/m_helper.c
58
- zcr_len = MIN(zcr_len, 0xf & (uint32_t)env->vfp.zcr_el[3]);
76
@@ -XXX,XX +XXX,XX @@ static bool v7m_stack_write(ARMCPU *cpu, uint32_t addr, uint32_t value,
59
+ /* If SVE is disabled, but FP is enabled,
77
}
60
+ * then the effective len is 0.
78
goto pend_fault;
61
+ */
79
}
62
+ if (sve_el != 0 && fp_el == 0) {
80
- address_space_stl_le(arm_addressspace(cs, res.attrs), res.phys, value,
63
+ zcr_len = 0;
81
- res.attrs, &txres);
64
+ } else {
82
+ address_space_stl_le(arm_addressspace(cs, res.f.attrs), res.f.phys_addr,
65
+ int current_el = arm_current_el(env);
83
+ value, res.f.attrs, &txres);
66
+ ARMCPU *cpu = arm_env_get_cpu(env);
84
if (txres != MEMTX_OK) {
67
+
85
/* BusFault trying to write the data */
68
+ zcr_len = cpu->sve_max_vq - 1;
86
if (mode == STACK_LAZYFP) {
69
+ if (current_el <= 1) {
87
@@ -XXX,XX +XXX,XX @@ static bool v7m_stack_read(ARMCPU *cpu, uint32_t *dest, uint32_t addr,
70
+ zcr_len = MIN(zcr_len, 0xf & (uint32_t)env->vfp.zcr_el[1]);
88
goto pend_fault;
71
+ }
89
}
72
+ if (current_el < 2 && arm_feature(env, ARM_FEATURE_EL2)) {
90
73
+ zcr_len = MIN(zcr_len, 0xf & (uint32_t)env->vfp.zcr_el[2]);
91
- value = address_space_ldl(arm_addressspace(cs, res.attrs), res.phys,
74
+ }
92
- res.attrs, &txres);
75
+ if (current_el < 3 && arm_feature(env, ARM_FEATURE_EL3)) {
93
+ value = address_space_ldl(arm_addressspace(cs, res.f.attrs),
76
+ zcr_len = MIN(zcr_len, 0xf & (uint32_t)env->vfp.zcr_el[3]);
94
+ res.f.phys_addr, res.f.attrs, &txres);
77
+ }
95
if (txres != MEMTX_OK) {
78
}
96
/* BusFault trying to read the data */
79
+ flags |= sve_el << ARM_TBFLAG_SVEEXC_EL_SHIFT;
97
qemu_log_mask(CPU_LOG_INT, "...BusFault with BFSR.UNSTKERR\n");
80
+ flags |= zcr_len << ARM_TBFLAG_ZCR_LEN_SHIFT;
98
@@ -XXX,XX +XXX,XX @@ static bool v7m_read_half_insn(ARMCPU *cpu, ARMMMUIdx mmu_idx, bool secure,
81
}
99
qemu_log_mask(CPU_LOG_INT, "...really MemManage with CFSR.IACCVIOL\n");
82
- flags |= zcr_len << ARM_TBFLAG_ZCR_LEN_SHIFT;
100
return false;
101
}
102
- *insn = address_space_lduw_le(arm_addressspace(cs, res.attrs), res.phys,
103
- res.attrs, &txres);
104
+ *insn = address_space_lduw_le(arm_addressspace(cs, res.f.attrs),
105
+ res.f.phys_addr, res.f.attrs, &txres);
106
if (txres != MEMTX_OK) {
107
env->v7m.cfsr[M_REG_NS] |= R_V7M_CFSR_IBUSERR_MASK;
108
armv7m_nvic_set_pending(env->nvic, ARMV7M_EXCP_BUS, false);
109
@@ -XXX,XX +XXX,XX @@ static bool v7m_read_sg_stack_word(ARMCPU *cpu, ARMMMUIdx mmu_idx,
110
}
111
return false;
112
}
113
- value = address_space_ldl(arm_addressspace(cs, res.attrs), res.phys,
114
- res.attrs, &txres);
115
+ value = address_space_ldl(arm_addressspace(cs, res.f.attrs),
116
+ res.f.phys_addr, res.f.attrs, &txres);
117
if (txres != MEMTX_OK) {
118
/* BusFault trying to read the data */
119
qemu_log_mask(CPU_LOG_INT,
120
@@ -XXX,XX +XXX,XX @@ uint32_t HELPER(v7m_tt)(CPUARMState *env, uint32_t addr, uint32_t op)
121
} else {
122
mrvalid = true;
123
}
124
- r = res.prot & PAGE_READ;
125
- rw = res.prot & PAGE_WRITE;
126
+ r = res.f.prot & PAGE_READ;
127
+ rw = res.f.prot & PAGE_WRITE;
83
} else {
128
} else {
84
*pc = env->regs[15];
129
r = false;
85
flags = (env->thumb << ARM_TBFLAG_THUMB_SHIFT)
130
rw = false;
131
diff --git a/target/arm/ptw.c b/target/arm/ptw.c
132
index XXXXXXX..XXXXXXX 100644
133
--- a/target/arm/ptw.c
134
+++ b/target/arm/ptw.c
135
@@ -XXX,XX +XXX,XX @@ static hwaddr S1_ptw_translate(CPUARMState *env, ARMMMUIdx mmu_idx,
136
assert(!is_secure);
137
}
138
139
- addr = s2.phys;
140
+ addr = s2.f.phys_addr;
141
}
142
return addr;
143
}
144
@@ -XXX,XX +XXX,XX @@ static bool get_phys_addr_v5(CPUARMState *env, uint32_t address,
145
/* 1Mb section. */
146
phys_addr = (desc & 0xfff00000) | (address & 0x000fffff);
147
ap = (desc >> 10) & 3;
148
- result->page_size = 1024 * 1024;
149
+ result->f.lg_page_size = 20; /* 1MB */
150
} else {
151
/* Lookup l2 entry. */
152
if (type == 1) {
153
@@ -XXX,XX +XXX,XX @@ static bool get_phys_addr_v5(CPUARMState *env, uint32_t address,
154
case 1: /* 64k page. */
155
phys_addr = (desc & 0xffff0000) | (address & 0xffff);
156
ap = (desc >> (4 + ((address >> 13) & 6))) & 3;
157
- result->page_size = 0x10000;
158
+ result->f.lg_page_size = 16;
159
break;
160
case 2: /* 4k page. */
161
phys_addr = (desc & 0xfffff000) | (address & 0xfff);
162
ap = (desc >> (4 + ((address >> 9) & 6))) & 3;
163
- result->page_size = 0x1000;
164
+ result->f.lg_page_size = 12;
165
break;
166
case 3: /* 1k page, or ARMv6/XScale "extended small (4k) page" */
167
if (type == 1) {
168
@@ -XXX,XX +XXX,XX @@ static bool get_phys_addr_v5(CPUARMState *env, uint32_t address,
169
if (arm_feature(env, ARM_FEATURE_XSCALE)
170
|| arm_feature(env, ARM_FEATURE_V6)) {
171
phys_addr = (desc & 0xfffff000) | (address & 0xfff);
172
- result->page_size = 0x1000;
173
+ result->f.lg_page_size = 12;
174
} else {
175
/*
176
* UNPREDICTABLE in ARMv5; we choose to take a
177
@@ -XXX,XX +XXX,XX @@ static bool get_phys_addr_v5(CPUARMState *env, uint32_t address,
178
}
179
} else {
180
phys_addr = (desc & 0xfffffc00) | (address & 0x3ff);
181
- result->page_size = 0x400;
182
+ result->f.lg_page_size = 10;
183
}
184
ap = (desc >> 4) & 3;
185
break;
186
@@ -XXX,XX +XXX,XX @@ static bool get_phys_addr_v5(CPUARMState *env, uint32_t address,
187
g_assert_not_reached();
188
}
189
}
190
- result->prot = ap_to_rw_prot(env, mmu_idx, ap, domain_prot);
191
- result->prot |= result->prot ? PAGE_EXEC : 0;
192
- if (!(result->prot & (1 << access_type))) {
193
+ result->f.prot = ap_to_rw_prot(env, mmu_idx, ap, domain_prot);
194
+ result->f.prot |= result->f.prot ? PAGE_EXEC : 0;
195
+ if (!(result->f.prot & (1 << access_type))) {
196
/* Access permission fault. */
197
fi->type = ARMFault_Permission;
198
goto do_fault;
199
}
200
- result->phys = phys_addr;
201
+ result->f.phys_addr = phys_addr;
202
return false;
203
do_fault:
204
fi->domain = domain;
205
@@ -XXX,XX +XXX,XX @@ static bool get_phys_addr_v6(CPUARMState *env, uint32_t address,
206
phys_addr = (desc & 0xff000000) | (address & 0x00ffffff);
207
phys_addr |= (uint64_t)extract32(desc, 20, 4) << 32;
208
phys_addr |= (uint64_t)extract32(desc, 5, 4) << 36;
209
- result->page_size = 0x1000000;
210
+ result->f.lg_page_size = 24; /* 16MB */
211
} else {
212
/* Section. */
213
phys_addr = (desc & 0xfff00000) | (address & 0x000fffff);
214
- result->page_size = 0x100000;
215
+ result->f.lg_page_size = 20; /* 1MB */
216
}
217
ap = ((desc >> 10) & 3) | ((desc >> 13) & 4);
218
xn = desc & (1 << 4);
219
@@ -XXX,XX +XXX,XX @@ static bool get_phys_addr_v6(CPUARMState *env, uint32_t address,
220
case 1: /* 64k page. */
221
phys_addr = (desc & 0xffff0000) | (address & 0xffff);
222
xn = desc & (1 << 15);
223
- result->page_size = 0x10000;
224
+ result->f.lg_page_size = 16;
225
break;
226
case 2: case 3: /* 4k page. */
227
phys_addr = (desc & 0xfffff000) | (address & 0xfff);
228
xn = desc & 1;
229
- result->page_size = 0x1000;
230
+ result->f.lg_page_size = 12;
231
break;
232
default:
233
/* Never happens, but compiler isn't smart enough to tell. */
234
@@ -XXX,XX +XXX,XX @@ static bool get_phys_addr_v6(CPUARMState *env, uint32_t address,
235
}
236
}
237
if (domain_prot == 3) {
238
- result->prot = PAGE_READ | PAGE_WRITE | PAGE_EXEC;
239
+ result->f.prot = PAGE_READ | PAGE_WRITE | PAGE_EXEC;
240
} else {
241
if (pxn && !regime_is_user(env, mmu_idx)) {
242
xn = 1;
243
@@ -XXX,XX +XXX,XX @@ static bool get_phys_addr_v6(CPUARMState *env, uint32_t address,
244
fi->type = ARMFault_AccessFlag;
245
goto do_fault;
246
}
247
- result->prot = simple_ap_to_rw_prot(env, mmu_idx, ap >> 1);
248
+ result->f.prot = simple_ap_to_rw_prot(env, mmu_idx, ap >> 1);
249
} else {
250
- result->prot = ap_to_rw_prot(env, mmu_idx, ap, domain_prot);
251
+ result->f.prot = ap_to_rw_prot(env, mmu_idx, ap, domain_prot);
252
}
253
- if (result->prot && !xn) {
254
- result->prot |= PAGE_EXEC;
255
+ if (result->f.prot && !xn) {
256
+ result->f.prot |= PAGE_EXEC;
257
}
258
- if (!(result->prot & (1 << access_type))) {
259
+ if (!(result->f.prot & (1 << access_type))) {
260
/* Access permission fault. */
261
fi->type = ARMFault_Permission;
262
goto do_fault;
263
@@ -XXX,XX +XXX,XX @@ static bool get_phys_addr_v6(CPUARMState *env, uint32_t address,
264
* the CPU doesn't support TZ or this is a non-secure translation
265
* regime, because the attribute will already be non-secure.
266
*/
267
- result->attrs.secure = false;
268
+ result->f.attrs.secure = false;
269
}
270
- result->phys = phys_addr;
271
+ result->f.phys_addr = phys_addr;
272
return false;
273
do_fault:
274
fi->domain = domain;
275
@@ -XXX,XX +XXX,XX @@ static bool get_phys_addr_lpae(CPUARMState *env, uint64_t address,
276
if (mmu_idx == ARMMMUIdx_Stage2 || mmu_idx == ARMMMUIdx_Stage2_S) {
277
ns = mmu_idx == ARMMMUIdx_Stage2;
278
xn = extract32(attrs, 11, 2);
279
- result->prot = get_S2prot(env, ap, xn, s1_is_el0);
280
+ result->f.prot = get_S2prot(env, ap, xn, s1_is_el0);
281
} else {
282
ns = extract32(attrs, 3, 1);
283
xn = extract32(attrs, 12, 1);
284
pxn = extract32(attrs, 11, 1);
285
- result->prot = get_S1prot(env, mmu_idx, aarch64, ap, ns, xn, pxn);
286
+ result->f.prot = get_S1prot(env, mmu_idx, aarch64, ap, ns, xn, pxn);
287
}
288
289
fault_type = ARMFault_Permission;
290
- if (!(result->prot & (1 << access_type))) {
291
+ if (!(result->f.prot & (1 << access_type))) {
292
goto do_fault;
293
}
294
295
@@ -XXX,XX +XXX,XX @@ static bool get_phys_addr_lpae(CPUARMState *env, uint64_t address,
296
* the CPU doesn't support TZ or this is a non-secure translation
297
* regime, because the attribute will already be non-secure.
298
*/
299
- result->attrs.secure = false;
300
+ result->f.attrs.secure = false;
301
}
302
/* When in aarch64 mode, and BTI is enabled, remember GP in the IOTLB. */
303
if (aarch64 && guarded && cpu_isar_feature(aa64_bti, cpu)) {
304
- arm_tlb_bti_gp(&result->attrs) = true;
305
+ arm_tlb_bti_gp(&result->f.attrs) = true;
306
}
307
308
if (mmu_idx == ARMMMUIdx_Stage2 || mmu_idx == ARMMMUIdx_Stage2_S) {
309
@@ -XXX,XX +XXX,XX @@ static bool get_phys_addr_lpae(CPUARMState *env, uint64_t address,
310
result->cacheattrs.shareability = extract32(attrs, 6, 2);
311
}
312
313
- result->phys = descaddr;
314
- result->page_size = page_size;
315
+ result->f.phys_addr = descaddr;
316
+ result->f.lg_page_size = ctz64(page_size);
317
return false;
318
319
do_fault:
320
@@ -XXX,XX +XXX,XX @@ static bool get_phys_addr_pmsav5(CPUARMState *env, uint32_t address,
321
322
if (regime_translation_disabled(env, mmu_idx, is_secure)) {
323
/* MPU disabled. */
324
- result->phys = address;
325
- result->prot = PAGE_READ | PAGE_WRITE | PAGE_EXEC;
326
+ result->f.phys_addr = address;
327
+ result->f.prot = PAGE_READ | PAGE_WRITE | PAGE_EXEC;
328
return false;
329
}
330
331
- result->phys = address;
332
+ result->f.phys_addr = address;
333
for (n = 7; n >= 0; n--) {
334
base = env->cp15.c6_region[n];
335
if ((base & 1) == 0) {
336
@@ -XXX,XX +XXX,XX @@ static bool get_phys_addr_pmsav5(CPUARMState *env, uint32_t address,
337
fi->level = 1;
338
return true;
339
}
340
- result->prot = PAGE_READ | PAGE_WRITE;
341
+ result->f.prot = PAGE_READ | PAGE_WRITE;
342
break;
343
case 2:
344
- result->prot = PAGE_READ;
345
+ result->f.prot = PAGE_READ;
346
if (!is_user) {
347
- result->prot |= PAGE_WRITE;
348
+ result->f.prot |= PAGE_WRITE;
349
}
350
break;
351
case 3:
352
- result->prot = PAGE_READ | PAGE_WRITE;
353
+ result->f.prot = PAGE_READ | PAGE_WRITE;
354
break;
355
case 5:
356
if (is_user) {
357
@@ -XXX,XX +XXX,XX @@ static bool get_phys_addr_pmsav5(CPUARMState *env, uint32_t address,
358
fi->level = 1;
359
return true;
360
}
361
- result->prot = PAGE_READ;
362
+ result->f.prot = PAGE_READ;
363
break;
364
case 6:
365
- result->prot = PAGE_READ;
366
+ result->f.prot = PAGE_READ;
367
break;
368
default:
369
/* Bad permission. */
370
@@ -XXX,XX +XXX,XX @@ static bool get_phys_addr_pmsav5(CPUARMState *env, uint32_t address,
371
fi->level = 1;
372
return true;
373
}
374
- result->prot |= PAGE_EXEC;
375
+ result->f.prot |= PAGE_EXEC;
376
return false;
377
}
378
379
static void get_phys_addr_pmsav7_default(CPUARMState *env, ARMMMUIdx mmu_idx,
380
- int32_t address, int *prot)
381
+ int32_t address, uint8_t *prot)
382
{
383
if (!arm_feature(env, ARM_FEATURE_M)) {
384
*prot = PAGE_READ | PAGE_WRITE;
385
@@ -XXX,XX +XXX,XX @@ static bool get_phys_addr_pmsav7(CPUARMState *env, uint32_t address,
386
int n;
387
bool is_user = regime_is_user(env, mmu_idx);
388
389
- result->phys = address;
390
- result->page_size = TARGET_PAGE_SIZE;
391
- result->prot = 0;
392
+ result->f.phys_addr = address;
393
+ result->f.lg_page_size = TARGET_PAGE_BITS;
394
+ result->f.prot = 0;
395
396
if (regime_translation_disabled(env, mmu_idx, secure) ||
397
m_is_ppb_region(env, address)) {
398
@@ -XXX,XX +XXX,XX @@ static bool get_phys_addr_pmsav7(CPUARMState *env, uint32_t address,
399
* which always does a direct read using address_space_ldl(), rather
400
* than going via this function, so we don't need to check that here.
401
*/
402
- get_phys_addr_pmsav7_default(env, mmu_idx, address, &result->prot);
403
+ get_phys_addr_pmsav7_default(env, mmu_idx, address, &result->f.prot);
404
} else { /* MPU enabled */
405
for (n = (int)cpu->pmsav7_dregion - 1; n >= 0; n--) {
406
/* region search */
407
@@ -XXX,XX +XXX,XX @@ static bool get_phys_addr_pmsav7(CPUARMState *env, uint32_t address,
408
if (ranges_overlap(base, rmask,
409
address & TARGET_PAGE_MASK,
410
TARGET_PAGE_SIZE)) {
411
- result->page_size = 1;
412
+ result->f.lg_page_size = 0;
413
}
414
continue;
415
}
416
@@ -XXX,XX +XXX,XX @@ static bool get_phys_addr_pmsav7(CPUARMState *env, uint32_t address,
417
continue;
418
}
419
if (rsize < TARGET_PAGE_BITS) {
420
- result->page_size = 1 << rsize;
421
+ result->f.lg_page_size = rsize;
422
}
423
break;
424
}
425
@@ -XXX,XX +XXX,XX @@ static bool get_phys_addr_pmsav7(CPUARMState *env, uint32_t address,
426
fi->type = ARMFault_Background;
427
return true;
428
}
429
- get_phys_addr_pmsav7_default(env, mmu_idx, address, &result->prot);
430
+ get_phys_addr_pmsav7_default(env, mmu_idx, address,
431
+ &result->f.prot);
432
} else { /* a MPU hit! */
433
uint32_t ap = extract32(env->pmsav7.dracr[n], 8, 3);
434
uint32_t xn = extract32(env->pmsav7.dracr[n], 12, 1);
435
@@ -XXX,XX +XXX,XX @@ static bool get_phys_addr_pmsav7(CPUARMState *env, uint32_t address,
436
case 5:
437
break; /* no access */
438
case 3:
439
- result->prot |= PAGE_WRITE;
440
+ result->f.prot |= PAGE_WRITE;
441
/* fall through */
442
case 2:
443
case 6:
444
- result->prot |= PAGE_READ | PAGE_EXEC;
445
+ result->f.prot |= PAGE_READ | PAGE_EXEC;
446
break;
447
case 7:
448
/* for v7M, same as 6; for R profile a reserved value */
449
if (arm_feature(env, ARM_FEATURE_M)) {
450
- result->prot |= PAGE_READ | PAGE_EXEC;
451
+ result->f.prot |= PAGE_READ | PAGE_EXEC;
452
break;
453
}
454
/* fall through */
455
@@ -XXX,XX +XXX,XX @@ static bool get_phys_addr_pmsav7(CPUARMState *env, uint32_t address,
456
case 1:
457
case 2:
458
case 3:
459
- result->prot |= PAGE_WRITE;
460
+ result->f.prot |= PAGE_WRITE;
461
/* fall through */
462
case 5:
463
case 6:
464
- result->prot |= PAGE_READ | PAGE_EXEC;
465
+ result->f.prot |= PAGE_READ | PAGE_EXEC;
466
break;
467
case 7:
468
/* for v7M, same as 6; for R profile a reserved value */
469
if (arm_feature(env, ARM_FEATURE_M)) {
470
- result->prot |= PAGE_READ | PAGE_EXEC;
471
+ result->f.prot |= PAGE_READ | PAGE_EXEC;
472
break;
473
}
474
/* fall through */
475
@@ -XXX,XX +XXX,XX @@ static bool get_phys_addr_pmsav7(CPUARMState *env, uint32_t address,
476
477
/* execute never */
478
if (xn) {
479
- result->prot &= ~PAGE_EXEC;
480
+ result->f.prot &= ~PAGE_EXEC;
481
}
482
}
483
}
484
485
fi->type = ARMFault_Permission;
486
fi->level = 1;
487
- return !(result->prot & (1 << access_type));
488
+ return !(result->f.prot & (1 << access_type));
489
}
490
491
bool pmsav8_mpu_lookup(CPUARMState *env, uint32_t address,
492
@@ -XXX,XX +XXX,XX @@ bool pmsav8_mpu_lookup(CPUARMState *env, uint32_t address,
493
uint32_t addr_page_base = address & TARGET_PAGE_MASK;
494
uint32_t addr_page_limit = addr_page_base + (TARGET_PAGE_SIZE - 1);
495
496
- result->page_size = TARGET_PAGE_SIZE;
497
- result->phys = address;
498
- result->prot = 0;
499
+ result->f.lg_page_size = TARGET_PAGE_BITS;
500
+ result->f.phys_addr = address;
501
+ result->f.prot = 0;
502
if (mregion) {
503
*mregion = -1;
504
}
505
@@ -XXX,XX +XXX,XX @@ bool pmsav8_mpu_lookup(CPUARMState *env, uint32_t address,
506
ranges_overlap(base, limit - base + 1,
507
addr_page_base,
508
TARGET_PAGE_SIZE)) {
509
- result->page_size = 1;
510
+ result->f.lg_page_size = 0;
511
}
512
continue;
513
}
514
515
if (base > addr_page_base || limit < addr_page_limit) {
516
- result->page_size = 1;
517
+ result->f.lg_page_size = 0;
518
}
519
520
if (matchregion != -1) {
521
@@ -XXX,XX +XXX,XX @@ bool pmsav8_mpu_lookup(CPUARMState *env, uint32_t address,
522
523
if (matchregion == -1) {
524
/* hit using the background region */
525
- get_phys_addr_pmsav7_default(env, mmu_idx, address, &result->prot);
526
+ get_phys_addr_pmsav7_default(env, mmu_idx, address, &result->f.prot);
527
} else {
528
uint32_t ap = extract32(env->pmsav8.rbar[secure][matchregion], 1, 2);
529
uint32_t xn = extract32(env->pmsav8.rbar[secure][matchregion], 0, 1);
530
@@ -XXX,XX +XXX,XX @@ bool pmsav8_mpu_lookup(CPUARMState *env, uint32_t address,
531
xn = 1;
532
}
533
534
- result->prot = simple_ap_to_rw_prot(env, mmu_idx, ap);
535
- if (result->prot && !xn && !(pxn && !is_user)) {
536
- result->prot |= PAGE_EXEC;
537
+ result->f.prot = simple_ap_to_rw_prot(env, mmu_idx, ap);
538
+ if (result->f.prot && !xn && !(pxn && !is_user)) {
539
+ result->f.prot |= PAGE_EXEC;
540
}
541
/*
542
* We don't need to look the attribute up in the MAIR0/MAIR1
543
@@ -XXX,XX +XXX,XX @@ bool pmsav8_mpu_lookup(CPUARMState *env, uint32_t address,
544
545
fi->type = ARMFault_Permission;
546
fi->level = 1;
547
- return !(result->prot & (1 << access_type));
548
+ return !(result->f.prot & (1 << access_type));
549
}
550
551
static bool v8m_is_sau_exempt(CPUARMState *env,
552
@@ -XXX,XX +XXX,XX @@ static bool get_phys_addr_pmsav8(CPUARMState *env, uint32_t address,
553
} else {
554
fi->type = ARMFault_QEMU_SFault;
555
}
556
- result->page_size = sattrs.subpage ? 1 : TARGET_PAGE_SIZE;
557
- result->phys = address;
558
- result->prot = 0;
559
+ result->f.lg_page_size = sattrs.subpage ? 0 : TARGET_PAGE_BITS;
560
+ result->f.phys_addr = address;
561
+ result->f.prot = 0;
562
return true;
563
}
564
} else {
565
@@ -XXX,XX +XXX,XX @@ static bool get_phys_addr_pmsav8(CPUARMState *env, uint32_t address,
566
* might downgrade a secure access to nonsecure.
567
*/
568
if (sattrs.ns) {
569
- result->attrs.secure = false;
570
+ result->f.attrs.secure = false;
571
} else if (!secure) {
572
/*
573
* NS access to S memory must fault.
574
@@ -XXX,XX +XXX,XX @@ static bool get_phys_addr_pmsav8(CPUARMState *env, uint32_t address,
575
* for M_FAKE_FSR_SFAULT in arm_v7m_cpu_do_interrupt().
576
*/
577
fi->type = ARMFault_QEMU_SFault;
578
- result->page_size = sattrs.subpage ? 1 : TARGET_PAGE_SIZE;
579
- result->phys = address;
580
- result->prot = 0;
581
+ result->f.lg_page_size = sattrs.subpage ? 0 : TARGET_PAGE_BITS;
582
+ result->f.phys_addr = address;
583
+ result->f.prot = 0;
584
return true;
585
}
586
}
587
@@ -XXX,XX +XXX,XX @@ static bool get_phys_addr_pmsav8(CPUARMState *env, uint32_t address,
588
ret = pmsav8_mpu_lookup(env, address, access_type, mmu_idx, secure,
589
result, fi, NULL);
590
if (sattrs.subpage) {
591
- result->page_size = 1;
592
+ result->f.lg_page_size = 0;
593
}
594
return ret;
595
}
596
@@ -XXX,XX +XXX,XX @@ static bool get_phys_addr_disabled(CPUARMState *env, target_ulong address,
597
result->cacheattrs.is_s2_format = false;
598
}
599
600
- result->phys = address;
601
- result->prot = PAGE_READ | PAGE_WRITE | PAGE_EXEC;
602
- result->page_size = TARGET_PAGE_SIZE;
603
+ result->f.phys_addr = address;
604
+ result->f.prot = PAGE_READ | PAGE_WRITE | PAGE_EXEC;
605
+ result->f.lg_page_size = TARGET_PAGE_BITS;
606
result->cacheattrs.shareability = shareability;
607
result->cacheattrs.attrs = memattr;
608
return 0;
609
@@ -XXX,XX +XXX,XX @@ bool get_phys_addr_with_secure(CPUARMState *env, target_ulong address,
610
return ret;
611
}
612
613
- ipa = result->phys;
614
- ipa_secure = result->attrs.secure;
615
+ ipa = result->f.phys_addr;
616
+ ipa_secure = result->f.attrs.secure;
617
if (is_secure) {
618
/* Select TCR based on the NS bit from the S1 walk. */
619
s2walk_secure = !(ipa_secure
620
@@ -XXX,XX +XXX,XX @@ bool get_phys_addr_with_secure(CPUARMState *env, target_ulong address,
621
* Save the stage1 results so that we may merge
622
* prot and cacheattrs later.
623
*/
624
- s1_prot = result->prot;
625
+ s1_prot = result->f.prot;
626
cacheattrs1 = result->cacheattrs;
627
memset(result, 0, sizeof(*result));
628
629
@@ -XXX,XX +XXX,XX @@ bool get_phys_addr_with_secure(CPUARMState *env, target_ulong address,
630
fi->s2addr = ipa;
631
632
/* Combine the S1 and S2 perms. */
633
- result->prot &= s1_prot;
634
+ result->f.prot &= s1_prot;
635
636
/* If S2 fails, return early. */
637
if (ret) {
638
@@ -XXX,XX +XXX,XX @@ bool get_phys_addr_with_secure(CPUARMState *env, target_ulong address,
639
* Check if IPA translates to secure or non-secure PA space.
640
* Note that VSTCR overrides VTCR and {N}SW overrides {N}SA.
641
*/
642
- result->attrs.secure =
643
+ result->f.attrs.secure =
644
(is_secure
645
&& !(env->cp15.vstcr_el2 & (VSTCR_SA | VSTCR_SW))
646
&& (ipa_secure
647
@@ -XXX,XX +XXX,XX @@ bool get_phys_addr_with_secure(CPUARMState *env, target_ulong address,
648
* cannot upgrade an non-secure translation regime's attributes
649
* to secure.
650
*/
651
- result->attrs.secure = is_secure;
652
- result->attrs.user = regime_is_user(env, mmu_idx);
653
+ result->f.attrs.secure = is_secure;
654
+ result->f.attrs.user = regime_is_user(env, mmu_idx);
655
656
/*
657
* Fast Context Switch Extension. This doesn't exist at all in v8.
658
@@ -XXX,XX +XXX,XX @@ bool get_phys_addr_with_secure(CPUARMState *env, target_ulong address,
659
660
if (arm_feature(env, ARM_FEATURE_PMSA)) {
661
bool ret;
662
- result->page_size = TARGET_PAGE_SIZE;
663
+ result->f.lg_page_size = TARGET_PAGE_BITS;
664
665
if (arm_feature(env, ARM_FEATURE_V8)) {
666
/* PMSAv8 */
667
@@ -XXX,XX +XXX,XX @@ bool get_phys_addr_with_secure(CPUARMState *env, target_ulong address,
668
(access_type == MMU_DATA_STORE ? "writing" : "execute"),
669
(uint32_t)address, mmu_idx,
670
ret ? "Miss" : "Hit",
671
- result->prot & PAGE_READ ? 'r' : '-',
672
- result->prot & PAGE_WRITE ? 'w' : '-',
673
- result->prot & PAGE_EXEC ? 'x' : '-');
674
+ result->f.prot & PAGE_READ ? 'r' : '-',
675
+ result->f.prot & PAGE_WRITE ? 'w' : '-',
676
+ result->f.prot & PAGE_EXEC ? 'x' : '-');
677
678
return ret;
679
}
680
@@ -XXX,XX +XXX,XX @@ hwaddr arm_cpu_get_phys_page_attrs_debug(CPUState *cs, vaddr addr,
681
bool ret;
682
683
ret = get_phys_addr(env, addr, MMU_DATA_LOAD, mmu_idx, &res, &fi);
684
- *attrs = res.attrs;
685
+ *attrs = res.f.attrs;
686
687
if (ret) {
688
return -1;
689
}
690
- return res.phys;
691
+ return res.f.phys_addr;
692
}
693
diff --git a/target/arm/tlb_helper.c b/target/arm/tlb_helper.c
694
index XXXXXXX..XXXXXXX 100644
695
--- a/target/arm/tlb_helper.c
696
+++ b/target/arm/tlb_helper.c
697
@@ -XXX,XX +XXX,XX @@ bool arm_cpu_tlb_fill(CPUState *cs, vaddr address, int size,
698
* target page size are handled specially, so for those we
699
* pass in the exact addresses.
700
*/
701
- if (res.page_size >= TARGET_PAGE_SIZE) {
702
- res.phys &= TARGET_PAGE_MASK;
703
+ if (res.f.lg_page_size >= TARGET_PAGE_BITS) {
704
+ res.f.phys_addr &= TARGET_PAGE_MASK;
705
address &= TARGET_PAGE_MASK;
706
}
707
/* Notice and record tagged memory. */
708
if (cpu_isar_feature(aa64_mte, cpu) && res.cacheattrs.attrs == 0xf0) {
709
- arm_tlb_mte_tagged(&res.attrs) = true;
710
+ arm_tlb_mte_tagged(&res.f.attrs) = true;
711
}
712
713
- tlb_set_page_with_attrs(cs, address, res.phys, res.attrs,
714
- res.prot, mmu_idx, res.page_size);
715
+ tlb_set_page_full(cs, mmu_idx, address, &res.f);
716
return true;
717
} else if (probe) {
718
return false;
86
--
719
--
87
2.19.0
720
2.25.1
88
89
diff view generated by jsdifflib
1
From: Cédric Le Goater <clg@kaod.org>
1
From: Jerome Forissier <jerome.forissier@linaro.org>
2
2
3
In file included from /home/thuth/devel/qemu/hw/timer/aspeed_timer.c:16:
3
According to the Linux kernel booting.rst [1], CPTR_EL3.ESM and
4
/home/thuth/devel/qemu/include/hw/misc/aspeed_scu.h:37:3: error:
4
SCR_EL3.EnTP2 must be initialized to 1 when EL3 is present and FEAT_SME
5
redefinition of typedef 'AspeedSCUState' is a C11 feature
5
is advertised. This has to be taken care of when QEMU boots directly
6
[-Werror,-Wtypedef-redefinition]
6
into the kernel (i.e., "-M virt,secure=on -cpu max -kernel Image").
7
} AspeedSCUState;
8
^
9
/home/thuth/devel/qemu/include/hw/timer/aspeed_timer.h:27:31: note:
10
previous definition is here
11
typedef struct AspeedSCUState AspeedSCUState;
12
7
13
Reported-by: Thomas Huth <thuth@redhat.com>
8
Cc: qemu-stable@nongnu.org
14
Signed-off-by: Cédric Le Goater <clg@kaod.org>
9
Fixes: 78cb9776662a ("target/arm: Enable SME for -cpu max")
15
Reviewed-by: Philippe Mathieu-Daudé <f4bug@amsat.org>
10
Link: [1] https://git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git/tree/Documentation/arm64/booting.rst?h=v6.0#n321
16
Message-id: 20180921161939.822-2-clg@kaod.org
11
Signed-off-by: Jerome Forissier <jerome.forissier@linaro.org>
12
Message-id: 20221003145641.1921467-1-jerome.forissier@linaro.org
17
Reviewed-by: Peter Maydell <peter.maydell@linaro.org>
13
Reviewed-by: Peter Maydell <peter.maydell@linaro.org>
18
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
14
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
19
---
15
---
20
include/hw/timer/aspeed_timer.h | 3 +--
16
hw/arm/boot.c | 4 ++++
21
hw/timer/aspeed_timer.c | 1 -
17
1 file changed, 4 insertions(+)
22
2 files changed, 1 insertion(+), 3 deletions(-)
23
18
24
diff --git a/include/hw/timer/aspeed_timer.h b/include/hw/timer/aspeed_timer.h
19
diff --git a/hw/arm/boot.c b/hw/arm/boot.c
25
index XXXXXXX..XXXXXXX 100644
20
index XXXXXXX..XXXXXXX 100644
26
--- a/include/hw/timer/aspeed_timer.h
21
--- a/hw/arm/boot.c
27
+++ b/include/hw/timer/aspeed_timer.h
22
+++ b/hw/arm/boot.c
28
@@ -XXX,XX +XXX,XX @@
23
@@ -XXX,XX +XXX,XX @@ static void do_cpu_reset(void *opaque)
29
#define ASPEED_TIMER_H
24
if (cpu_isar_feature(aa64_sve, cpu)) {
30
25
env->cp15.cptr_el[3] |= R_CPTR_EL3_EZ_MASK;
31
#include "qemu/timer.h"
26
}
32
-
27
+ if (cpu_isar_feature(aa64_sme, cpu)) {
33
-typedef struct AspeedSCUState AspeedSCUState;
28
+ env->cp15.cptr_el[3] |= R_CPTR_EL3_ESM_MASK;
34
+#include "hw/misc/aspeed_scu.h"
29
+ env->cp15.scr_el3 |= SCR_ENTP2;
35
30
+ }
36
#define ASPEED_TIMER(obj) \
31
/* AArch64 kernels never boot in secure mode */
37
OBJECT_CHECK(AspeedTimerCtrlState, (obj), TYPE_ASPEED_TIMER);
32
assert(!info->secure_boot);
38
diff --git a/hw/timer/aspeed_timer.c b/hw/timer/aspeed_timer.c
33
/* This hook is only supported for AArch32 currently:
39
index XXXXXXX..XXXXXXX 100644
40
--- a/hw/timer/aspeed_timer.c
41
+++ b/hw/timer/aspeed_timer.c
42
@@ -XXX,XX +XXX,XX @@
43
#include "qapi/error.h"
44
#include "hw/sysbus.h"
45
#include "hw/timer/aspeed_timer.h"
46
-#include "hw/misc/aspeed_scu.h"
47
#include "qemu-common.h"
48
#include "qemu/bitops.h"
49
#include "qemu/timer.h"
50
--
34
--
51
2.19.0
35
2.25.1
52
53
diff view generated by jsdifflib
1
Convert the pcnet-pci device away from using the old_mmio
1
Arm CPUs support some subset of the granule (page) sizes 4K, 16K and
2
MemoryRegionOps accessor functions.
2
64K. The guest selects the one it wants using bits in the TCR_ELx
3
3
registers. If it tries to program these registers with a value that
4
This commit is a no-behaviour-change API conversion.
4
is either reserved or which requests a size that the CPU does not
5
(Since PCNET_PNPMMIO_SIZE is 0x20, the old "addr & 0x10"
5
implement, the architecture requires that the CPU behaves as if the
6
check and the new "addr < 0x10" check are exact opposites;
6
field was programmed to some size that has been implemented.
7
the new code is phrased to be parallel with the
7
Currently we don't implement this, and instead let the guest use any
8
pcnet_io_read/write functions.)
8
granule size, even if the CPU ID register fields say it isn't
9
9
present.
10
I have left a TODO comment marker because the similarity
10
11
between the MMIO and IO accessor behaviour is suspicious
11
Make aa64_va_parameters() check against the supported granule size
12
and they could be combined, but this will be left to a
12
and force use of a different one if it is not implemented.
13
different patch.
13
14
(A subsequent commit will make ARMVAParameters use the new enum
15
rather than the current pair of using16k/using64k bools.)
14
16
15
Reviewed-by: Richard Henderson <richard.henderson@linaro.org>
17
Reviewed-by: Richard Henderson <richard.henderson@linaro.org>
16
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
18
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
19
Message-id: 20221003162315.2833797-2-peter.maydell@linaro.org
17
---
20
---
18
hw/net/pcnet-pci.c | 133 ++++++++++++++++++--------------------------
21
target/arm/cpu.h | 33 +++++++++++++
19
hw/net/trace-events | 8 +--
22
target/arm/internals.h | 9 ++++
20
2 files changed, 57 insertions(+), 84 deletions(-)
23
target/arm/helper.c | 102 +++++++++++++++++++++++++++++++++++++----
21
24
3 files changed, 136 insertions(+), 8 deletions(-)
22
diff --git a/hw/net/pcnet-pci.c b/hw/net/pcnet-pci.c
25
26
diff --git a/target/arm/cpu.h b/target/arm/cpu.h
23
index XXXXXXX..XXXXXXX 100644
27
index XXXXXXX..XXXXXXX 100644
24
--- a/hw/net/pcnet-pci.c
28
--- a/target/arm/cpu.h
25
+++ b/hw/net/pcnet-pci.c
29
+++ b/target/arm/cpu.h
26
@@ -XXX,XX +XXX,XX @@ static const MemoryRegionOps pcnet_io_ops = {
30
@@ -XXX,XX +XXX,XX @@ static inline bool isar_feature_aa64_tgran16_2_lpa2(const ARMISARegisters *id)
27
.endianness = DEVICE_LITTLE_ENDIAN,
31
return t >= 3 || (t == 0 && isar_feature_aa64_tgran16_lpa2(id));
28
};
32
}
29
33
30
-static void pcnet_mmio_writeb(void *opaque, hwaddr addr, uint32_t val)
34
+static inline bool isar_feature_aa64_tgran4(const ARMISARegisters *id)
31
+/*
35
+{
32
+ * TODO: should MMIO accesses to the addresses corresponding to the
36
+ return FIELD_SEX64(id->id_aa64mmfr0, ID_AA64MMFR0, TGRAN4) >= 0;
33
+ * APROM also honour the BCR_DWIO() setting? If so, then these functions
37
+}
34
+ * and pcnet_ioport_write/pcnet_ioport_read could be merged.
38
+
35
+ * If not, then should pcnet_ioport_{read,write}{w,l} really check
39
+static inline bool isar_feature_aa64_tgran16(const ARMISARegisters *id)
36
+ * BCR_DWIO() for MMIO writes ?
40
+{
37
+ */
41
+ return FIELD_EX64(id->id_aa64mmfr0, ID_AA64MMFR0, TGRAN16) >= 1;
38
+static void pcnet_mmio_write(void *opaque, hwaddr addr, uint64_t value,
42
+}
39
+ unsigned size)
43
+
44
+static inline bool isar_feature_aa64_tgran64(const ARMISARegisters *id)
45
+{
46
+ return FIELD_SEX64(id->id_aa64mmfr0, ID_AA64MMFR0, TGRAN64) >= 0;
47
+}
48
+
49
+static inline bool isar_feature_aa64_tgran4_2(const ARMISARegisters *id)
50
+{
51
+ unsigned t = FIELD_EX64(id->id_aa64mmfr0, ID_AA64MMFR0, TGRAN4_2);
52
+ return t >= 2 || (t == 0 && isar_feature_aa64_tgran4(id));
53
+}
54
+
55
+static inline bool isar_feature_aa64_tgran16_2(const ARMISARegisters *id)
56
+{
57
+ unsigned t = FIELD_EX64(id->id_aa64mmfr0, ID_AA64MMFR0, TGRAN16_2);
58
+ return t >= 2 || (t == 0 && isar_feature_aa64_tgran16(id));
59
+}
60
+
61
+static inline bool isar_feature_aa64_tgran64_2(const ARMISARegisters *id)
62
+{
63
+ unsigned t = FIELD_EX64(id->id_aa64mmfr0, ID_AA64MMFR0, TGRAN64_2);
64
+ return t >= 2 || (t == 0 && isar_feature_aa64_tgran64(id));
65
+}
66
+
67
static inline bool isar_feature_aa64_ccidx(const ARMISARegisters *id)
40
{
68
{
41
PCNetState *d = opaque;
69
return FIELD_EX64(id->id_aa64mmfr2, ID_AA64MMFR2, CCIDX) != 0;
42
70
diff --git a/target/arm/internals.h b/target/arm/internals.h
43
- trace_pcnet_mmio_writeb(opaque, addr, val);
71
index XXXXXXX..XXXXXXX 100644
44
- if (!(addr & 0x10))
72
--- a/target/arm/internals.h
45
- pcnet_aprom_writeb(d, addr & 0x0f, val);
73
+++ b/target/arm/internals.h
46
-}
74
@@ -XXX,XX +XXX,XX @@ static inline uint32_t aarch64_pstate_valid_mask(const ARMISARegisters *id)
47
+ trace_pcnet_mmio_write(opaque, addr, size, val);
75
return valid;
48
76
}
49
-static uint32_t pcnet_mmio_readb(void *opaque, hwaddr addr)
77
50
-{
78
+/* Granule size (i.e. page size) */
51
- PCNetState *d = opaque;
79
+typedef enum ARMGranuleSize {
52
- uint32_t val = -1;
80
+ /* Same order as TG0 encoding */
53
-
81
+ Gran4K,
54
- if (!(addr & 0x10))
82
+ Gran64K,
55
- val = pcnet_aprom_readb(d, addr & 0x0f);
83
+ Gran16K,
56
- trace_pcnet_mmio_readb(opaque, addr, val);
84
+ GranInvalid,
57
- return val;
85
+} ARMGranuleSize;
58
-}
86
+
59
-
87
/*
60
-static void pcnet_mmio_writew(void *opaque, hwaddr addr, uint32_t val)
88
* Parameters of a given virtual address, as extracted from the
61
-{
89
* translation control register (TCR) for a given regime.
62
- PCNetState *d = opaque;
90
diff --git a/target/arm/helper.c b/target/arm/helper.c
63
-
91
index XXXXXXX..XXXXXXX 100644
64
- trace_pcnet_mmio_writew(opaque, addr, val);
92
--- a/target/arm/helper.c
65
- if (addr & 0x10)
93
+++ b/target/arm/helper.c
66
- pcnet_ioport_writew(d, addr & 0x0f, val);
94
@@ -XXX,XX +XXX,XX @@ static int aa64_va_parameter_tcma(uint64_t tcr, ARMMMUIdx mmu_idx)
67
- else {
68
- addr &= 0x0f;
69
- pcnet_aprom_writeb(d, addr, val & 0xff);
70
- pcnet_aprom_writeb(d, addr+1, (val & 0xff00) >> 8);
71
+ if (addr < 0x10) {
72
+ if (size == 1) {
73
+ pcnet_aprom_writeb(d, addr, data);
74
+ } else if ((addr & 1) == 0 && size == 2) {
75
+ pcnet_aprom_writeb(d, addr, data & 0xff);
76
+ pcnet_aprom_writeb(d, addr + 1, data >> 8);
77
+ } else if ((addr & 3) == 0 && size == 4) {
78
+ pcnet_aprom_writeb(d, addr, data & 0xff);
79
+ pcnet_aprom_writeb(d, addr + 1, (data >> 8) & 0xff);
80
+ pcnet_aprom_writeb(d, addr + 2, (data >> 16) & 0xff);
81
+ pcnet_aprom_writeb(d, addr + 3, data >> 24);
82
+ }
83
+ } else {
84
+ if (size == 2) {
85
+ pcnet_ioport_writew(d, addr, data);
86
+ } else if (size == 4) {
87
+ pcnet_ioport_writel(d, addr, data);
88
+ }
89
}
95
}
90
}
96
}
91
97
92
-static uint32_t pcnet_mmio_readw(void *opaque, hwaddr addr)
98
+static ARMGranuleSize tg0_to_gran_size(int tg)
93
-{
99
+{
94
- PCNetState *d = opaque;
100
+ switch (tg) {
95
- uint32_t val = -1;
101
+ case 0:
96
-
102
+ return Gran4K;
97
- if (addr & 0x10)
103
+ case 1:
98
- val = pcnet_ioport_readw(d, addr & 0x0f);
104
+ return Gran64K;
99
- else {
105
+ case 2:
100
- addr &= 0x0f;
106
+ return Gran16K;
101
- val = pcnet_aprom_readb(d, addr+1);
107
+ default:
102
- val <<= 8;
108
+ return GranInvalid;
103
- val |= pcnet_aprom_readb(d, addr);
109
+ }
104
- }
110
+}
105
- trace_pcnet_mmio_readw(opaque, addr, val);
111
+
106
- return val;
112
+static ARMGranuleSize tg1_to_gran_size(int tg)
107
-}
113
+{
108
-
114
+ switch (tg) {
109
-static void pcnet_mmio_writel(void *opaque, hwaddr addr, uint32_t val)
115
+ case 1:
110
+static uint64_t pcnet_mmio_read(void *opque, hwaddr addr, unsigned size)
116
+ return Gran16K;
117
+ case 2:
118
+ return Gran4K;
119
+ case 3:
120
+ return Gran64K;
121
+ default:
122
+ return GranInvalid;
123
+ }
124
+}
125
+
126
+static inline bool have4k(ARMCPU *cpu, bool stage2)
127
+{
128
+ return stage2 ? cpu_isar_feature(aa64_tgran4_2, cpu)
129
+ : cpu_isar_feature(aa64_tgran4, cpu);
130
+}
131
+
132
+static inline bool have16k(ARMCPU *cpu, bool stage2)
133
+{
134
+ return stage2 ? cpu_isar_feature(aa64_tgran16_2, cpu)
135
+ : cpu_isar_feature(aa64_tgran16, cpu);
136
+}
137
+
138
+static inline bool have64k(ARMCPU *cpu, bool stage2)
139
+{
140
+ return stage2 ? cpu_isar_feature(aa64_tgran64_2, cpu)
141
+ : cpu_isar_feature(aa64_tgran64, cpu);
142
+}
143
+
144
+static ARMGranuleSize sanitize_gran_size(ARMCPU *cpu, ARMGranuleSize gran,
145
+ bool stage2)
146
+{
147
+ switch (gran) {
148
+ case Gran4K:
149
+ if (have4k(cpu, stage2)) {
150
+ return gran;
151
+ }
152
+ break;
153
+ case Gran16K:
154
+ if (have16k(cpu, stage2)) {
155
+ return gran;
156
+ }
157
+ break;
158
+ case Gran64K:
159
+ if (have64k(cpu, stage2)) {
160
+ return gran;
161
+ }
162
+ break;
163
+ case GranInvalid:
164
+ break;
165
+ }
166
+ /*
167
+ * If the guest selects a granule size that isn't implemented,
168
+ * the architecture requires that we behave as if it selected one
169
+ * that is (with an IMPDEF choice of which one to pick). We choose
170
+ * to implement the smallest supported granule size.
171
+ */
172
+ if (have4k(cpu, stage2)) {
173
+ return Gran4K;
174
+ }
175
+ if (have16k(cpu, stage2)) {
176
+ return Gran16K;
177
+ }
178
+ assert(have64k(cpu, stage2));
179
+ return Gran64K;
180
+}
181
+
182
ARMVAParameters aa64_va_parameters(CPUARMState *env, uint64_t va,
183
ARMMMUIdx mmu_idx, bool data)
111
{
184
{
112
PCNetState *d = opaque;
185
uint64_t tcr = regime_tcr(env, mmu_idx);
113
186
bool epd, hpd, using16k, using64k, tsz_oob, ds;
114
- trace_pcnet_mmio_writel(opaque, addr, val);
187
int select, tsz, tbi, max_tsz, min_tsz, ps, sh;
115
- if (addr & 0x10)
188
+ ARMGranuleSize gran;
116
- pcnet_ioport_writel(d, addr & 0x0f, val);
189
ARMCPU *cpu = env_archcpu(env);
117
- else {
190
+ bool stage2 = mmu_idx == ARMMMUIdx_Stage2 || mmu_idx == ARMMMUIdx_Stage2_S;
118
- addr &= 0x0f;
191
119
- pcnet_aprom_writeb(d, addr, val & 0xff);
192
if (!regime_has_2_ranges(mmu_idx)) {
120
- pcnet_aprom_writeb(d, addr+1, (val & 0xff00) >> 8);
193
select = 0;
121
- pcnet_aprom_writeb(d, addr+2, (val & 0xff0000) >> 16);
194
tsz = extract32(tcr, 0, 6);
122
- pcnet_aprom_writeb(d, addr+3, (val & 0xff000000) >> 24);
195
- using64k = extract32(tcr, 14, 1);
123
- }
196
- using16k = extract32(tcr, 15, 1);
124
-}
197
- if (mmu_idx == ARMMMUIdx_Stage2 || mmu_idx == ARMMMUIdx_Stage2_S) {
125
+ trace_pcnet_ioport_read(opaque, addr, size);
198
+ gran = tg0_to_gran_size(extract32(tcr, 14, 2));
126
199
+ if (stage2) {
127
-static uint32_t pcnet_mmio_readl(void *opaque, hwaddr addr)
200
/* VTCR_EL2 */
128
-{
201
hpd = false;
129
- PCNetState *d = opaque;
202
} else {
130
- uint32_t val;
203
@@ -XXX,XX +XXX,XX @@ ARMVAParameters aa64_va_parameters(CPUARMState *env, uint64_t va,
131
-
204
select = extract64(va, 55, 1);
132
- if (addr & 0x10)
205
if (!select) {
133
- val = pcnet_ioport_readl(d, addr & 0x0f);
206
tsz = extract32(tcr, 0, 6);
134
- else {
207
+ gran = tg0_to_gran_size(extract32(tcr, 14, 2));
135
- addr &= 0x0f;
208
epd = extract32(tcr, 7, 1);
136
- val = pcnet_aprom_readb(d, addr+3);
209
sh = extract32(tcr, 12, 2);
137
- val <<= 8;
210
- using64k = extract32(tcr, 14, 1);
138
- val |= pcnet_aprom_readb(d, addr+2);
211
- using16k = extract32(tcr, 15, 1);
139
- val <<= 8;
212
hpd = extract64(tcr, 41, 1);
140
- val |= pcnet_aprom_readb(d, addr+1);
213
} else {
141
- val <<= 8;
214
- int tg = extract32(tcr, 30, 2);
142
- val |= pcnet_aprom_readb(d, addr);
215
- using16k = tg == 1;
143
+ if (addr < 0x10) {
216
- using64k = tg == 3;
144
+ if (size == 1) {
217
tsz = extract32(tcr, 16, 6);
145
+ return pcnet_aprom_readb(d, addr);
218
+ gran = tg1_to_gran_size(extract32(tcr, 30, 2));
146
+ } else if ((addr & 1) == 0 && size == 2) {
219
epd = extract32(tcr, 23, 1);
147
+ return pcnet_aprom_readb(d, addr) |
220
sh = extract32(tcr, 28, 2);
148
+ (pcnet_aprom_readb(d, addr + 1) << 8);
221
hpd = extract64(tcr, 42, 1);
149
+ } else if ((addr & 3) == 0 && size == 4) {
222
@@ -XXX,XX +XXX,XX @@ ARMVAParameters aa64_va_parameters(CPUARMState *env, uint64_t va,
150
+ return pcnet_aprom_readb(d, addr) |
223
ds = extract64(tcr, 59, 1);
151
+ (pcnet_aprom_readb(d, addr + 1) << 8) |
152
+ (pcnet_aprom_readb(d, addr + 2) << 16) |
153
+ (pcnet_aprom_readb(d, addr + 3) << 24);
154
+ }
155
+ } else {
156
+ if (size == 2) {
157
+ return pcnet_ioport_readw(d, addr);
158
+ } else if (size == 4) {
159
+ return pcnet_ioport_readl(d, addr);
160
+ }
161
}
224
}
162
- trace_pcnet_mmio_readl(opaque, addr, val);
225
163
- return val;
226
+ gran = sanitize_gran_size(cpu, gran, stage2);
164
+ return ((uint64_t)1 << (size * 8)) - 1;
227
+ using64k = gran == Gran64K;
165
}
228
+ using16k = gran == Gran16K;
166
229
+
167
static const VMStateDescription vmstate_pci_pcnet = {
230
if (cpu_isar_feature(aa64_st, cpu)) {
168
@@ -XXX,XX +XXX,XX @@ static const VMStateDescription vmstate_pci_pcnet = {
231
max_tsz = 48 - using64k;
169
/* PCI interface */
232
} else {
170
171
static const MemoryRegionOps pcnet_mmio_ops = {
172
- .old_mmio = {
173
- .read = { pcnet_mmio_readb, pcnet_mmio_readw, pcnet_mmio_readl },
174
- .write = { pcnet_mmio_writeb, pcnet_mmio_writew, pcnet_mmio_writel },
175
- },
176
+ .read = pcnet_mmio_read,
177
+ .write = pcnet_mmio_write,
178
+ .valid.min_access_size = 1,
179
+ .valid.max_access_size = 4,
180
+ .impl.min_access_size = 1,
181
+ .impl.max_access_size = 4,
182
.endianness = DEVICE_LITTLE_ENDIAN,
183
};
184
185
diff --git a/hw/net/trace-events b/hw/net/trace-events
186
index XXXXXXX..XXXXXXX 100644
187
--- a/hw/net/trace-events
188
+++ b/hw/net/trace-events
189
@@ -XXX,XX +XXX,XX @@ pcnet_aprom_writeb(void *opaque, uint32_t addr, uint32_t val) "opaque=%p addr=0x
190
pcnet_aprom_readb(void *opaque, uint32_t addr, uint32_t val) "opaque=%p addr=0x%08x val=0x%02x"
191
pcnet_ioport_read(void *opaque, uint64_t addr, unsigned size) "opaque=%p addr=0x%"PRIx64" size=%d"
192
pcnet_ioport_write(void *opaque, uint64_t addr, uint64_t data, unsigned size) "opaque=%p addr=0x%"PRIx64" data=0x%"PRIx64" size=%d"
193
-pcnet_mmio_writeb(void *opaque, uint64_t addr, uint32_t val) "opaque=%p addr=0x%"PRIx64" val=0x%x"
194
-pcnet_mmio_writew(void *opaque, uint64_t addr, uint32_t val) "opaque=%p addr=0x%"PRIx64" val=0x%x"
195
-pcnet_mmio_writel(void *opaque, uint64_t addr, uint32_t val) "opaque=%p addr=0x%"PRIx64" val=0x%x"
196
-pcnet_mmio_readb(void *opaque, uint64_t addr, uint32_t val) "opaque=%p addr=0x%"PRIx64" val=0x%x"
197
-pcnet_mmio_readw(void *opaque, uint64_t addr, uint32_t val) "opaque=%p addr=0x%"PRIx64" val=0x%x"
198
-pcnet_mmio_readl(void *opaque, uint64_t addr, uint32_t val) "opaque=%p addr=0x%"PRIx64" val=0x%x"
199
+pcnet_mmio_write(void *opaque, uint64_t addr, uint32_t val, unsigned size) "opaque=%p addr=0x%"PRIx64" val=0x%x size=%d"
200
+pcnet_mmio_read(void *opaque, uint64_t addr, unsigned size) "opaque=%p addr=0x%"PRIx64" size=%d"
201
202
# hw/net/net_rx_pkt.c
203
net_rx_pkt_parsed(bool ip4, bool ip6, bool udp, bool tcp, size_t l3o, size_t l4o, size_t l5o) "RX packet parsed: ip4: %d, ip6: %d, udp: %d, tcp: %d, l3 offset: %zu, l4 offset: %zu, l5 offset: %zu"
204
--
233
--
205
2.19.0
234
2.25.1
206
207
diff view generated by jsdifflib
1
The ARMv8 architecture defines that an AArch32 CPU starts
1
Now we have an enum for the granule size, use it in the
2
in SVC mode, unless EL2 is the highest available EL, in
2
ARMVAParameters struct instead of the using16k/using64k bools.
3
which case it starts in Hyp mode. (In ARMv7 a CPU with EL2
4
but not EL3 was not a valid configuration, but we don't
5
specifically reject this if the user asks for one.)
6
3
7
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
4
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
8
Reviewed-by: Philippe Mathieu-Daudé <philmd@redhat.com>
5
Reviewed-by: Richard Henderson <richard.henderson@linaro.org>
9
Message-id: 20180823135047.16525-1-peter.maydell@linaro.org
6
Message-id: 20221003162315.2833797-3-peter.maydell@linaro.org
10
---
7
---
11
target/arm/cpu.c | 14 ++++++++++++--
8
target/arm/internals.h | 23 +++++++++++++++++++++--
12
1 file changed, 12 insertions(+), 2 deletions(-)
9
target/arm/helper.c | 39 ++++++++++++++++++++++++++++-----------
10
target/arm/ptw.c | 8 +-------
11
3 files changed, 50 insertions(+), 20 deletions(-)
13
12
14
diff --git a/target/arm/cpu.c b/target/arm/cpu.c
13
diff --git a/target/arm/internals.h b/target/arm/internals.h
15
index XXXXXXX..XXXXXXX 100644
14
index XXXXXXX..XXXXXXX 100644
16
--- a/target/arm/cpu.c
15
--- a/target/arm/internals.h
17
+++ b/target/arm/cpu.c
16
+++ b/target/arm/internals.h
18
@@ -XXX,XX +XXX,XX @@ static void arm_cpu_reset(CPUState *s)
17
@@ -XXX,XX +XXX,XX @@ typedef enum ARMGranuleSize {
19
env->cp15.c15_cpar = 1;
18
GranInvalid,
19
} ARMGranuleSize;
20
21
+/**
22
+ * arm_granule_bits: Return address size of the granule in bits
23
+ *
24
+ * Return the address size of the granule in bits. This corresponds
25
+ * to the pseudocode TGxGranuleBits().
26
+ */
27
+static inline int arm_granule_bits(ARMGranuleSize gran)
28
+{
29
+ switch (gran) {
30
+ case Gran64K:
31
+ return 16;
32
+ case Gran16K:
33
+ return 14;
34
+ case Gran4K:
35
+ return 12;
36
+ default:
37
+ g_assert_not_reached();
38
+ }
39
+}
40
+
41
/*
42
* Parameters of a given virtual address, as extracted from the
43
* translation control register (TCR) for a given regime.
44
@@ -XXX,XX +XXX,XX @@ typedef struct ARMVAParameters {
45
bool tbi : 1;
46
bool epd : 1;
47
bool hpd : 1;
48
- bool using16k : 1;
49
- bool using64k : 1;
50
bool tsz_oob : 1; /* tsz has been clamped to legal range */
51
bool ds : 1;
52
+ ARMGranuleSize gran : 2;
53
} ARMVAParameters;
54
55
ARMVAParameters aa64_va_parameters(CPUARMState *env, uint64_t va,
56
diff --git a/target/arm/helper.c b/target/arm/helper.c
57
index XXXXXXX..XXXXXXX 100644
58
--- a/target/arm/helper.c
59
+++ b/target/arm/helper.c
60
@@ -XXX,XX +XXX,XX @@ typedef struct {
61
uint64_t length;
62
} TLBIRange;
63
64
+static ARMGranuleSize tlbi_range_tg_to_gran_size(int tg)
65
+{
66
+ /*
67
+ * Note that the TLBI range TG field encoding differs from both
68
+ * TG0 and TG1 encodings.
69
+ */
70
+ switch (tg) {
71
+ case 1:
72
+ return Gran4K;
73
+ case 2:
74
+ return Gran16K;
75
+ case 3:
76
+ return Gran64K;
77
+ default:
78
+ return GranInvalid;
79
+ }
80
+}
81
+
82
static TLBIRange tlbi_aa64_get_range(CPUARMState *env, ARMMMUIdx mmuidx,
83
uint64_t value)
84
{
85
@@ -XXX,XX +XXX,XX @@ static TLBIRange tlbi_aa64_get_range(CPUARMState *env, ARMMMUIdx mmuidx,
86
uint64_t select = sextract64(value, 36, 1);
87
ARMVAParameters param = aa64_va_parameters(env, select, mmuidx, true);
88
TLBIRange ret = { };
89
+ ARMGranuleSize gran;
90
91
page_size_granule = extract64(value, 46, 2);
92
+ gran = tlbi_range_tg_to_gran_size(page_size_granule);
93
94
/* The granule encoded in value must match the granule in use. */
95
- if (page_size_granule != (param.using64k ? 3 : param.using16k ? 2 : 1)) {
96
+ if (gran != param.gran) {
97
qemu_log_mask(LOG_GUEST_ERROR, "Invalid tlbi page size granule %d\n",
98
page_size_granule);
99
return ret;
20
}
100
}
21
#else
101
22
- /* SVC mode with interrupts disabled. */
102
- page_shift = (page_size_granule - 1) * 2 + 12;
23
- env->uncached_cpsr = ARM_CPU_MODE_SVC;
103
+ page_shift = arm_granule_bits(gran);
24
+
104
num = extract64(value, 39, 5);
25
+ /*
105
scale = extract64(value, 44, 2);
26
+ * If the highest available EL is EL2, AArch32 will start in Hyp
106
exponent = (5 * scale) + 1;
27
+ * mode; otherwise it starts in SVC. Note that if we start in
107
@@ -XXX,XX +XXX,XX @@ ARMVAParameters aa64_va_parameters(CPUARMState *env, uint64_t va,
28
+ * AArch64 then these values in the uncached_cpsr will be ignored.
108
ARMMMUIdx mmu_idx, bool data)
29
+ */
109
{
30
+ if (arm_feature(env, ARM_FEATURE_EL2) &&
110
uint64_t tcr = regime_tcr(env, mmu_idx);
31
+ !arm_feature(env, ARM_FEATURE_EL3)) {
111
- bool epd, hpd, using16k, using64k, tsz_oob, ds;
32
+ env->uncached_cpsr = ARM_CPU_MODE_HYP;
112
+ bool epd, hpd, tsz_oob, ds;
33
+ } else {
113
int select, tsz, tbi, max_tsz, min_tsz, ps, sh;
34
+ env->uncached_cpsr = ARM_CPU_MODE_SVC;
114
ARMGranuleSize gran;
35
+ }
115
ARMCPU *cpu = env_archcpu(env);
36
env->daif = PSTATE_D | PSTATE_A | PSTATE_I | PSTATE_F;
116
@@ -XXX,XX +XXX,XX @@ ARMVAParameters aa64_va_parameters(CPUARMState *env, uint64_t va,
37
117
}
38
if (arm_feature(env, ARM_FEATURE_M)) {
118
119
gran = sanitize_gran_size(cpu, gran, stage2);
120
- using64k = gran == Gran64K;
121
- using16k = gran == Gran16K;
122
123
if (cpu_isar_feature(aa64_st, cpu)) {
124
- max_tsz = 48 - using64k;
125
+ max_tsz = 48 - (gran == Gran64K);
126
} else {
127
max_tsz = 39;
128
}
129
@@ -XXX,XX +XXX,XX @@ ARMVAParameters aa64_va_parameters(CPUARMState *env, uint64_t va,
130
* adjust the effective value of DS, as documented.
131
*/
132
min_tsz = 16;
133
- if (using64k) {
134
+ if (gran == Gran64K) {
135
if (cpu_isar_feature(aa64_lva, cpu)) {
136
min_tsz = 12;
137
}
138
@@ -XXX,XX +XXX,XX @@ ARMVAParameters aa64_va_parameters(CPUARMState *env, uint64_t va,
139
switch (mmu_idx) {
140
case ARMMMUIdx_Stage2:
141
case ARMMMUIdx_Stage2_S:
142
- if (using16k) {
143
+ if (gran == Gran16K) {
144
ds = cpu_isar_feature(aa64_tgran16_2_lpa2, cpu);
145
} else {
146
ds = cpu_isar_feature(aa64_tgran4_2_lpa2, cpu);
147
}
148
break;
149
default:
150
- if (using16k) {
151
+ if (gran == Gran16K) {
152
ds = cpu_isar_feature(aa64_tgran16_lpa2, cpu);
153
} else {
154
ds = cpu_isar_feature(aa64_tgran4_lpa2, cpu);
155
@@ -XXX,XX +XXX,XX @@ ARMVAParameters aa64_va_parameters(CPUARMState *env, uint64_t va,
156
.tbi = tbi,
157
.epd = epd,
158
.hpd = hpd,
159
- .using16k = using16k,
160
- .using64k = using64k,
161
.tsz_oob = tsz_oob,
162
.ds = ds,
163
+ .gran = gran,
164
};
165
}
166
167
diff --git a/target/arm/ptw.c b/target/arm/ptw.c
168
index XXXXXXX..XXXXXXX 100644
169
--- a/target/arm/ptw.c
170
+++ b/target/arm/ptw.c
171
@@ -XXX,XX +XXX,XX @@ static bool get_phys_addr_lpae(CPUARMState *env, uint64_t address,
172
}
173
}
174
175
- if (param.using64k) {
176
- stride = 13;
177
- } else if (param.using16k) {
178
- stride = 11;
179
- } else {
180
- stride = 9;
181
- }
182
+ stride = arm_granule_bits(param.gran) - 3;
183
184
/*
185
* Note that QEMU ignores shareability and cacheability attributes,
39
--
186
--
40
2.19.0
187
2.25.1
41
42
diff view generated by jsdifflib
1
The only difference between our implementation of the pcnet ioport
1
FEAT_GTG is a change tho the ID register ID_AA64MMFR0_EL1 so that it
2
accessors and the mmio accessors is that the former check BCR_DWIO to
2
can report a different set of supported granule (page) sizes for
3
see what access widths are permitted for addresses in the aprom range
3
stage 1 and stage 2 translation tables. As of commit c20281b2a5048
4
(0x0..0xf). In fact our failure to do this in the mmio accessors
4
we already report the granule sizes that way for '-cpu max', and now
5
is a bug (one which was fixed for the ioport accessors in
5
we also correctly make attempts to use unimplemented granule sizes
6
commit 7ba79741970 in 2011).
6
fail, so we can report the support of the feature in the
7
7
documentation.
8
The data sheet for the Am79C970A does not describe the DWIO
9
bit as only applying for I/O space mapped I/O resources and
10
not memory mapped I/O resources, and our MMIO accessors already
11
honour DWIO for accesses in the 0x10..0x1f range (since the
12
pcnet_ioport_{read,write}{w,l} functions check it).
13
14
The data sheet for the later but compatible Am79C976 is clearer:
15
it states specifically "DWIO mode applies to both I/O- and
16
memory-mapped acceses." This seems to be reasonable evidence
17
in favour of interpretating the Am79C970A spec as being the same.
18
19
(NB: Linux's pcnet driver only supports I/O accesses, so the
20
MMIO access part of this device is probably untested anyway.)
21
8
22
Reviewed-by: Richard Henderson <richard.henderson@linaro.org>
9
Reviewed-by: Richard Henderson <richard.henderson@linaro.org>
23
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
10
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
11
Message-id: 20221003162315.2833797-4-peter.maydell@linaro.org
24
---
12
---
25
hw/net/pcnet-pci.c | 67 ++-------------------------------------------
13
docs/system/arm/emulation.rst | 1 +
26
hw/net/trace-events | 2 --
14
1 file changed, 1 insertion(+)
27
2 files changed, 2 insertions(+), 67 deletions(-)
28
15
29
diff --git a/hw/net/pcnet-pci.c b/hw/net/pcnet-pci.c
16
diff --git a/docs/system/arm/emulation.rst b/docs/system/arm/emulation.rst
30
index XXXXXXX..XXXXXXX 100644
17
index XXXXXXX..XXXXXXX 100644
31
--- a/hw/net/pcnet-pci.c
18
--- a/docs/system/arm/emulation.rst
32
+++ b/hw/net/pcnet-pci.c
19
+++ b/docs/system/arm/emulation.rst
33
@@ -XXX,XX +XXX,XX @@ static const MemoryRegionOps pcnet_io_ops = {
20
@@ -XXX,XX +XXX,XX @@ the following architecture extensions:
34
.endianness = DEVICE_LITTLE_ENDIAN,
21
- FEAT_FRINTTS (Floating-point to integer instructions)
35
};
22
- FEAT_FlagM (Flag manipulation instructions v2)
36
23
- FEAT_FlagM2 (Enhancements to flag manipulation instructions)
37
-/*
24
+- FEAT_GTG (Guest translation granule size)
38
- * TODO: should MMIO accesses to the addresses corresponding to the
25
- FEAT_HCX (Support for the HCRX_EL2 register)
39
- * APROM also honour the BCR_DWIO() setting? If so, then these functions
26
- FEAT_HPDS (Hierarchical permission disables)
40
- * and pcnet_ioport_write/pcnet_ioport_read could be merged.
27
- FEAT_I8MM (AArch64 Int8 matrix multiplication instructions)
41
- * If not, then should pcnet_ioport_{read,write}{w,l} really check
42
- * BCR_DWIO() for MMIO writes ?
43
- */
44
-static void pcnet_mmio_write(void *opaque, hwaddr addr, uint64_t value,
45
- unsigned size)
46
-{
47
- PCNetState *d = opaque;
48
-
49
- trace_pcnet_mmio_write(opaque, addr, size, val);
50
-
51
- if (addr < 0x10) {
52
- if (size == 1) {
53
- pcnet_aprom_writeb(d, addr, data);
54
- } else if ((addr & 1) == 0 && size == 2) {
55
- pcnet_aprom_writeb(d, addr, data & 0xff);
56
- pcnet_aprom_writeb(d, addr + 1, data >> 8);
57
- } else if ((addr & 3) == 0 && size == 4) {
58
- pcnet_aprom_writeb(d, addr, data & 0xff);
59
- pcnet_aprom_writeb(d, addr + 1, (data >> 8) & 0xff);
60
- pcnet_aprom_writeb(d, addr + 2, (data >> 16) & 0xff);
61
- pcnet_aprom_writeb(d, addr + 3, data >> 24);
62
- }
63
- } else {
64
- if (size == 2) {
65
- pcnet_ioport_writew(d, addr, data);
66
- } else if (size == 4) {
67
- pcnet_ioport_writel(d, addr, data);
68
- }
69
- }
70
-}
71
-
72
-static uint64_t pcnet_mmio_read(void *opque, hwaddr addr, unsigned size)
73
-{
74
- PCNetState *d = opaque;
75
-
76
- trace_pcnet_ioport_read(opaque, addr, size);
77
-
78
- if (addr < 0x10) {
79
- if (size == 1) {
80
- return pcnet_aprom_readb(d, addr);
81
- } else if ((addr & 1) == 0 && size == 2) {
82
- return pcnet_aprom_readb(d, addr) |
83
- (pcnet_aprom_readb(d, addr + 1) << 8);
84
- } else if ((addr & 3) == 0 && size == 4) {
85
- return pcnet_aprom_readb(d, addr) |
86
- (pcnet_aprom_readb(d, addr + 1) << 8) |
87
- (pcnet_aprom_readb(d, addr + 2) << 16) |
88
- (pcnet_aprom_readb(d, addr + 3) << 24);
89
- }
90
- } else {
91
- if (size == 2) {
92
- return pcnet_ioport_readw(d, addr);
93
- } else if (size == 4) {
94
- return pcnet_ioport_readl(d, addr);
95
- }
96
- }
97
- return ((uint64_t)1 << (size * 8)) - 1;
98
-}
99
-
100
static const VMStateDescription vmstate_pci_pcnet = {
101
.name = "pcnet",
102
.version_id = 3,
103
@@ -XXX,XX +XXX,XX @@ static const VMStateDescription vmstate_pci_pcnet = {
104
/* PCI interface */
105
106
static const MemoryRegionOps pcnet_mmio_ops = {
107
- .read = pcnet_mmio_read,
108
- .write = pcnet_mmio_write,
109
+ .read = pcnet_ioport_read,
110
+ .write = pcnet_ioport_write,
111
.valid.min_access_size = 1,
112
.valid.max_access_size = 4,
113
.impl.min_access_size = 1,
114
diff --git a/hw/net/trace-events b/hw/net/trace-events
115
index XXXXXXX..XXXXXXX 100644
116
--- a/hw/net/trace-events
117
+++ b/hw/net/trace-events
118
@@ -XXX,XX +XXX,XX @@ pcnet_aprom_writeb(void *opaque, uint32_t addr, uint32_t val) "opaque=%p addr=0x
119
pcnet_aprom_readb(void *opaque, uint32_t addr, uint32_t val) "opaque=%p addr=0x%08x val=0x%02x"
120
pcnet_ioport_read(void *opaque, uint64_t addr, unsigned size) "opaque=%p addr=0x%"PRIx64" size=%d"
121
pcnet_ioport_write(void *opaque, uint64_t addr, uint64_t data, unsigned size) "opaque=%p addr=0x%"PRIx64" data=0x%"PRIx64" size=%d"
122
-pcnet_mmio_write(void *opaque, uint64_t addr, uint32_t val, unsigned size) "opaque=%p addr=0x%"PRIx64" val=0x%x size=%d"
123
-pcnet_mmio_read(void *opaque, uint64_t addr, unsigned size) "opaque=%p addr=0x%"PRIx64" size=%d"
124
125
# hw/net/net_rx_pkt.c
126
net_rx_pkt_parsed(bool ip4, bool ip6, bool udp, bool tcp, size_t l3o, size_t l4o, size_t l5o) "RX packet parsed: ip4: %d, ip6: %d, udp: %d, tcp: %d, l3 offset: %zu, l4 offset: %zu, l5 offset: %zu"
127
--
28
--
128
2.19.0
29
2.25.1
129
130
diff view generated by jsdifflib