1
Arm changes for before softfreeze: mostly my PL061/GPIO patches,
1
Hi; here's the latest round of arm patches. I have included also
2
but also a new M-profile board and various other things.
2
my patchset for the RTC devices to avoid keeping time_t and
3
time_t diffs in 32-bit variables.
3
4
4
thanks
5
thanks
5
-- PMM
6
-- PMM
6
7
7
The following changes since commit 05de778b5b8ab0b402996769117b88c7ea5c7c61:
8
The following changes since commit 156618d9ea67f2f2e31d9dedd97f2dcccbe6808c:
8
9
9
Merge remote-tracking branch 'remotes/mst/tags/for_upstream' into staging (2021-07-09 14:30:01 +0100)
10
Merge tag 'block-pull-request' of https://gitlab.com/stefanha/qemu into staging (2023-08-30 09:20:27 -0400)
10
11
11
are available in the Git repository at:
12
are available in the Git repository at:
12
13
13
https://git.linaro.org/people/pmaydell/qemu-arm.git tags/pull-target-arm-20210709
14
https://git.linaro.org/people/pmaydell/qemu-arm.git tags/pull-target-arm-20230831
14
15
15
for you to fetch changes up to 05449abb1d4c5f0c69ceb3d8d03cbc75de39b646:
16
for you to fetch changes up to e73b8bb8a3e9a162f70e9ffbf922d4fafc96bbfb:
16
17
17
hw/intc: Improve formatting of MEMTX_ERROR guest error message (2021-07-09 16:09:12 +0100)
18
hw/arm: Set number of MPU regions correctly for an505, an521, an524 (2023-08-31 11:07:02 +0100)
18
19
19
----------------------------------------------------------------
20
----------------------------------------------------------------
20
target-arm queue:
21
target-arm queue:
21
* New machine type: stm32vldiscovery
22
* Some of the preliminary patches for Cortex-A710 support
22
* hw/intc/arm_gicv3_cpuif: Fix virtual irq number check in icv_[dir|eoir]_write
23
* i.MX7 and i.MX6UL refactoring
23
* hw/gpio/pl061: Honour Luminary PL061 PUR and PDR registers
24
* Implement SRC device for i.MX7
24
* virt: Fix implementation of GPIO-based powerdown/shutdown mechanism
25
* Catch illegal-exception-return from EL3 with bad NSE/NS
25
* Correct the encoding of MDCCSR_EL0 and DBGDSCRint
26
* Use 64-bit offsets for holding time_t differences in RTC devices
26
* hw/intc: Improve formatting of MEMTX_ERROR guest error message
27
* Model correct number of MPU regions for an505, an521, an524 boards
27
28
28
----------------------------------------------------------------
29
----------------------------------------------------------------
29
Alexandre Iooss (4):
30
Alex Bennée (1):
30
stm32f100: Add the stm32f100 SoC
31
target/arm: properly document FEAT_CRC32
31
stm32vldiscovery: Add the STM32VLDISCOVERY Machine
32
docs/system: arm: Add stm32 boards description
33
tests/boot-serial-test: Add STM32VLDISCOVERY board testcase
34
32
35
Peter Maydell (10):
33
Jean-Christophe Dubois (6):
36
hw/gpio/pl061: Convert DPRINTF to tracepoints
34
Remove i.MX7 IOMUX GPR device from i.MX6UL
37
hw/gpio/pl061: Clean up read/write offset handling logic
35
Refactor i.MX6UL processor code
38
hw/gpio/pl061: Add tracepoints for register read and write
36
Add i.MX6UL missing devices.
39
hw/gpio/pl061: Document the interface of this device
37
Refactor i.MX7 processor code
40
hw/gpio/pl061: Honour Luminary PL061 PUR and PDR registers
38
Add i.MX7 missing TZ devices and memory regions
41
hw/gpio/pl061: Make pullup/pulldown of outputs configurable
39
Add i.MX7 SRC device implementation
42
hw/arm/virt: Make PL061 GPIO lines pulled low, not high
43
hw/gpio/pl061: Convert to 3-phase reset and assert GPIO lines correctly on reset
44
hw/gpio/pl061: Document a shortcoming in our implementation
45
hw/arm/stellaris: Expand comment about handling of OLED chipselect
46
40
47
Rebecca Cran (1):
41
Peter Maydell (8):
48
hw/intc: Improve formatting of MEMTX_ERROR guest error message
42
target/arm: Catch illegal-exception-return from EL3 with bad NSE/NS
43
hw/rtc/m48t59: Use 64-bit arithmetic in set_alarm()
44
hw/rtc/twl92230: Use int64_t for sec_offset and alm_sec
45
hw/rtc/aspeed_rtc: Use 64-bit offset for holding time_t difference
46
rtc: Use time_t for passing and returning time offsets
47
target/arm: Do all "ARM_FEATURE_X implies Y" checks in post_init
48
hw/arm/armv7m: Add mpu-ns-regions and mpu-s-regions properties
49
hw/arm: Set number of MPU regions correctly for an505, an521, an524
49
50
50
Ricardo Koller (1):
51
Richard Henderson (9):
51
hw/intc/arm_gicv3_cpuif: Fix virtual irq number check in icv_[dir|eoir]_write
52
target/arm: Reduce dcz_blocksize to uint8_t
53
target/arm: Allow cpu to configure GM blocksize
54
target/arm: Support more GM blocksizes
55
target/arm: When tag memory is not present, set MTE=1
56
target/arm: Introduce make_ccsidr64
57
target/arm: Apply access checks to neoverse-n1 special registers
58
target/arm: Apply access checks to neoverse-v1 special registers
59
target/arm: Suppress FEAT_TRBE (Trace Buffer Extension)
60
target/arm: Implement FEAT_HPDS2 as a no-op
52
61
53
hnick@vmware.com (1):
62
docs/system/arm/emulation.rst | 2 +
54
target/arm: Correct the encoding of MDCCSR_EL0 and DBGDSCRint
63
include/hw/arm/armsse.h | 5 +
64
include/hw/arm/armv7m.h | 8 +
65
include/hw/arm/fsl-imx6ul.h | 158 ++++++++++++++++---
66
include/hw/arm/fsl-imx7.h | 338 ++++++++++++++++++++++++++++++-----------
67
include/hw/misc/imx7_src.h | 66 ++++++++
68
include/hw/rtc/aspeed_rtc.h | 2 +-
69
include/sysemu/rtc.h | 4 +-
70
target/arm/cpregs.h | 2 +
71
target/arm/cpu.h | 5 +-
72
target/arm/internals.h | 6 -
73
target/arm/tcg/translate.h | 2 +
74
hw/arm/armsse.c | 16 ++
75
hw/arm/armv7m.c | 21 +++
76
hw/arm/fsl-imx6ul.c | 174 +++++++++++++--------
77
hw/arm/fsl-imx7.c | 201 +++++++++++++++++++-----
78
hw/arm/mps2-tz.c | 29 ++++
79
hw/misc/imx7_src.c | 276 +++++++++++++++++++++++++++++++++
80
hw/rtc/aspeed_rtc.c | 5 +-
81
hw/rtc/m48t59.c | 2 +-
82
hw/rtc/twl92230.c | 4 +-
83
softmmu/rtc.c | 4 +-
84
target/arm/cpu.c | 207 ++++++++++++++-----------
85
target/arm/helper.c | 15 +-
86
target/arm/tcg/cpu32.c | 2 +-
87
target/arm/tcg/cpu64.c | 102 +++++++++----
88
target/arm/tcg/helper-a64.c | 9 ++
89
target/arm/tcg/mte_helper.c | 90 ++++++++---
90
target/arm/tcg/translate-a64.c | 5 +-
91
hw/misc/meson.build | 1 +
92
hw/misc/trace-events | 4 +
93
31 files changed, 1393 insertions(+), 372 deletions(-)
94
create mode 100644 include/hw/misc/imx7_src.h
95
create mode 100644 hw/misc/imx7_src.c
55
96
56
docs/system/arm/stm32.rst | 66 +++++++
57
docs/system/target-arm.rst | 1 +
58
default-configs/devices/arm-softmmu.mak | 1 +
59
include/hw/arm/stm32f100_soc.h | 57 ++++++
60
hw/arm/stellaris.c | 56 +++++-
61
hw/arm/stm32f100_soc.c | 182 +++++++++++++++++
62
hw/arm/stm32vldiscovery.c | 66 +++++++
63
hw/arm/virt.c | 3 +
64
hw/gpio/pl061.c | 341 +++++++++++++++++++++++++-------
65
hw/intc/arm_gicv3_cpuif.c | 4 +-
66
hw/intc/arm_gicv3_redist.c | 4 +-
67
target/arm/helper.c | 16 +-
68
tests/qtest/boot-serial-test.c | 37 ++++
69
MAINTAINERS | 13 ++
70
hw/arm/Kconfig | 10 +
71
hw/arm/meson.build | 2 +
72
hw/gpio/trace-events | 9 +
73
17 files changed, 790 insertions(+), 78 deletions(-)
74
create mode 100644 docs/system/arm/stm32.rst
75
create mode 100644 include/hw/arm/stm32f100_soc.h
76
create mode 100644 hw/arm/stm32f100_soc.c
77
create mode 100644 hw/arm/stm32vldiscovery.c
78
diff view generated by jsdifflib
1
The stellaris board doesn't emulate the handling of the OLED
1
From: Richard Henderson <richard.henderson@linaro.org>
2
chipselect line correctly. Expand the comment describing this,
3
including a sketch of the theoretical correct way to do it.
4
2
3
This value is only 4 bits wide.
4
5
Reviewed-by: Peter Maydell <peter.maydell@linaro.org>
6
Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
7
Reviewed-by: Philippe Mathieu-Daudé <philmd@linaro.org>
8
Message-id: 20230811214031.171020-2-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
---
10
---
7
hw/arm/stellaris.c | 56 +++++++++++++++++++++++++++++++++++++++++++++-
11
target/arm/cpu.h | 3 ++-
8
1 file changed, 55 insertions(+), 1 deletion(-)
12
1 file changed, 2 insertions(+), 1 deletion(-)
9
13
10
diff --git a/hw/arm/stellaris.c b/hw/arm/stellaris.c
14
diff --git a/target/arm/cpu.h b/target/arm/cpu.h
11
index XXXXXXX..XXXXXXX 100644
15
index XXXXXXX..XXXXXXX 100644
12
--- a/hw/arm/stellaris.c
16
--- a/target/arm/cpu.h
13
+++ b/hw/arm/stellaris.c
17
+++ b/target/arm/cpu.h
14
@@ -XXX,XX +XXX,XX @@ static void stellaris_init(MachineState *ms, stellaris_board_info *board)
18
@@ -XXX,XX +XXX,XX @@ struct ArchCPU {
15
DeviceState *sddev;
19
bool prop_lpa2;
16
DeviceState *ssddev;
20
17
21
/* DCZ blocksize, in log_2(words), ie low 4 bits of DCZID_EL0 */
18
- /* Some boards have both an OLED controller and SD card connected to
22
- uint32_t dcz_blocksize;
19
+ /*
23
+ uint8_t dcz_blocksize;
20
+ * Some boards have both an OLED controller and SD card connected to
24
+
21
* the same SSI port, with the SD card chip select connected to a
25
uint64_t rvbar_prop; /* Property/input signals. */
22
* GPIO pin. Technically the OLED chip select is connected to the
26
23
* SSI Fss pin. We do not bother emulating that as both devices
27
/* Configurable aspects of GIC cpu interface (which is part of the CPU) */
24
* should never be selected simultaneously, and our OLED controller
25
* ignores stray 0xff commands that occur when deselecting the SD
26
* card.
27
+ *
28
+ * The h/w wiring is:
29
+ * - GPIO pin D0 is wired to the active-low SD card chip select
30
+ * - GPIO pin A3 is wired to the active-low OLED chip select
31
+ * - The SoC wiring of the PL061 "auxiliary function" for A3 is
32
+ * SSI0Fss ("frame signal"), which is an output from the SoC's
33
+ * SSI controller. The SSI controller takes SSI0Fss low when it
34
+ * transmits a frame, so it can work as a chip-select signal.
35
+ * - GPIO A4 is aux-function SSI0Rx, and wired to the SD card Tx
36
+ * (the OLED never sends data to the CPU, so no wiring needed)
37
+ * - GPIO A5 is aux-function SSI0Tx, and wired to the SD card Rx
38
+ * and the OLED display-data-in
39
+ * - GPIO A2 is aux-function SSI0Clk, wired to SD card and OLED
40
+ * serial-clock input
41
+ * So a guest that wants to use the OLED can configure the PL061
42
+ * to make pins A2, A3, A5 aux-function, so they are connected
43
+ * directly to the SSI controller. When the SSI controller sends
44
+ * data it asserts SSI0Fss which selects the OLED.
45
+ * A guest that wants to use the SD card configures A2, A4 and A5
46
+ * as aux-function, but leaves A3 as a software-controlled GPIO
47
+ * line. It asserts the SD card chip-select by using the PL061
48
+ * to control pin D0, and lets the SSI controller handle Clk, Tx
49
+ * and Rx. (The SSI controller asserts Fss during tx cycles as
50
+ * usual, but because A3 is not set to aux-function this is not
51
+ * forwarded to the OLED, and so the OLED stays unselected.)
52
+ *
53
+ * The QEMU implementation instead is:
54
+ * - GPIO pin D0 is wired to the active-low SD card chip select,
55
+ * and also to the OLED chip-select which is implemented
56
+ * as *active-high*
57
+ * - SSI controller signals go to the devices regardless of
58
+ * whether the guest programs A2, A4, A5 as aux-function or not
59
+ *
60
+ * The problem with this implementation is if the guest doesn't
61
+ * care about the SD card and only uses the OLED. In that case it
62
+ * may choose never to do anything with D0 (leaving it in its
63
+ * default floating state, which reliably leaves the card disabled
64
+ * because an SD card has a pullup on CS within the card itself),
65
+ * and only set up A2, A3, A5. This for us would mean the OLED
66
+ * never gets the chip-select assert it needs. We work around
67
+ * this with a manual raise of D0 here (despite board creation
68
+ * code being the wrong place to raise IRQ lines) to put the OLED
69
+ * into an initially selected state.
70
+ *
71
+ * In theory the right way to model this would be:
72
+ * - Implement aux-function support in the PL061, with an
73
+ * extra set of AFIN and AFOUT GPIO lines (set up so that
74
+ * if a GPIO line is in auxfn mode the main GPIO in and out
75
+ * track the AFIN and AFOUT lines)
76
+ * - Wire the AFOUT for D0 up to either a line from the
77
+ * SSI controller that's pulled low around every transmit,
78
+ * or at least to an always-0 line here on the board
79
+ * - Make the ssd0323 OLED controller chipselect active-low
80
*/
81
bus = qdev_get_child_bus(dev, "ssi");
82
83
--
28
--
84
2.20.1
29
2.34.1
85
30
86
31
diff view generated by jsdifflib
1
The PL061 comes out of reset with all its lines configured as input,
1
From: Richard Henderson <richard.henderson@linaro.org>
2
which means they might need to be pulled to 0 or 1 depending on the
2
3
'pullups' and 'pulldowns' properties. Currently we do not assert
3
Previously we hard-coded the blocksize with GMID_EL1_BS.
4
these lines on reset; they will only be set whenever the guest first
4
But the value we choose for -cpu max does not match the
5
touches a register that triggers a call to pl061_update().
5
value that cortex-a710 uses.
6
6
7
Convert the device to three-phase reset so we have a place where we
7
Mirror the way we handle dcz_blocksize.
8
can safely call qemu_set_irq() to set the floating lines to their
8
9
correct values.
9
Reviewed-by: Peter Maydell <peter.maydell@linaro.org>
10
10
Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
11
Message-id: 20230811214031.171020-3-richard.henderson@linaro.org
11
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
12
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
12
Reviewed-by: Philippe Mathieu-Daudé <f4bug@amsat.org>
13
Reviewed-by: Richard Henderson <richard.henderson@linaro.org>
14
---
13
---
15
hw/gpio/pl061.c | 29 +++++++++++++++++++++++++----
14
target/arm/cpu.h | 2 ++
16
hw/gpio/trace-events | 1 +
15
target/arm/internals.h | 6 -----
17
2 files changed, 26 insertions(+), 4 deletions(-)
16
target/arm/tcg/translate.h | 2 ++
18
17
target/arm/helper.c | 11 +++++---
19
diff --git a/hw/gpio/pl061.c b/hw/gpio/pl061.c
18
target/arm/tcg/cpu64.c | 1 +
20
index XXXXXXX..XXXXXXX 100644
19
target/arm/tcg/mte_helper.c | 46 ++++++++++++++++++++++------------
21
--- a/hw/gpio/pl061.c
20
target/arm/tcg/translate-a64.c | 5 ++--
22
+++ b/hw/gpio/pl061.c
21
7 files changed, 45 insertions(+), 28 deletions(-)
23
@@ -XXX,XX +XXX,XX @@ static void pl061_write(void *opaque, hwaddr offset,
22
24
return;
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 @@ struct ArchCPU {
28
29
/* DCZ blocksize, in log_2(words), ie low 4 bits of DCZID_EL0 */
30
uint8_t dcz_blocksize;
31
+ /* GM blocksize, in log_2(words), ie low 4 bits of GMID_EL0 */
32
+ uint8_t gm_blocksize;
33
34
uint64_t rvbar_prop; /* Property/input signals. */
35
36
diff --git a/target/arm/internals.h b/target/arm/internals.h
37
index XXXXXXX..XXXXXXX 100644
38
--- a/target/arm/internals.h
39
+++ b/target/arm/internals.h
40
@@ -XXX,XX +XXX,XX @@ void arm_log_exception(CPUState *cs);
41
42
#endif /* !CONFIG_USER_ONLY */
43
44
-/*
45
- * The log2 of the words in the tag block, for GMID_EL1.BS.
46
- * The is the maximum, 256 bytes, which manipulates 64-bits of tags.
47
- */
48
-#define GMID_EL1_BS 6
49
-
50
/*
51
* SVE predicates are 1/8 the size of SVE vectors, and cannot use
52
* the same simd_desc() encoding due to restrictions on size.
53
diff --git a/target/arm/tcg/translate.h b/target/arm/tcg/translate.h
54
index XXXXXXX..XXXXXXX 100644
55
--- a/target/arm/tcg/translate.h
56
+++ b/target/arm/tcg/translate.h
57
@@ -XXX,XX +XXX,XX @@ typedef struct DisasContext {
58
int8_t btype;
59
/* A copy of cpu->dcz_blocksize. */
60
uint8_t dcz_blocksize;
61
+ /* A copy of cpu->gm_blocksize. */
62
+ uint8_t gm_blocksize;
63
/* True if this page is guarded. */
64
bool guarded_page;
65
/* Bottom two bits of XScale c15_cpar coprocessor access control reg */
66
diff --git a/target/arm/helper.c b/target/arm/helper.c
67
index XXXXXXX..XXXXXXX 100644
68
--- a/target/arm/helper.c
69
+++ b/target/arm/helper.c
70
@@ -XXX,XX +XXX,XX @@ static const ARMCPRegInfo mte_reginfo[] = {
71
.opc0 = 3, .opc1 = 0, .crn = 1, .crm = 0, .opc2 = 6,
72
.access = PL1_RW, .accessfn = access_mte,
73
.fieldoffset = offsetof(CPUARMState, cp15.gcr_el1) },
74
- { .name = "GMID_EL1", .state = ARM_CP_STATE_AA64,
75
- .opc0 = 3, .opc1 = 1, .crn = 0, .crm = 0, .opc2 = 4,
76
- .access = PL1_R, .accessfn = access_aa64_tid5,
77
- .type = ARM_CP_CONST, .resetvalue = GMID_EL1_BS },
78
{ .name = "TCO", .state = ARM_CP_STATE_AA64,
79
.opc0 = 3, .opc1 = 3, .crn = 4, .crm = 2, .opc2 = 7,
80
.type = ARM_CP_NO_RAW,
81
@@ -XXX,XX +XXX,XX @@ void register_cp_regs_for_features(ARMCPU *cpu)
82
* then define only a RAZ/WI version of PSTATE.TCO.
83
*/
84
if (cpu_isar_feature(aa64_mte, cpu)) {
85
+ ARMCPRegInfo gmid_reginfo = {
86
+ .name = "GMID_EL1", .state = ARM_CP_STATE_AA64,
87
+ .opc0 = 3, .opc1 = 1, .crn = 0, .crm = 0, .opc2 = 4,
88
+ .access = PL1_R, .accessfn = access_aa64_tid5,
89
+ .type = ARM_CP_CONST, .resetvalue = cpu->gm_blocksize,
90
+ };
91
+ define_one_arm_cp_reg(cpu, &gmid_reginfo);
92
define_arm_cp_regs(cpu, mte_reginfo);
93
define_arm_cp_regs(cpu, mte_el0_cacheop_reginfo);
94
} else if (cpu_isar_feature(aa64_mte_insn_reg, cpu)) {
95
diff --git a/target/arm/tcg/cpu64.c b/target/arm/tcg/cpu64.c
96
index XXXXXXX..XXXXXXX 100644
97
--- a/target/arm/tcg/cpu64.c
98
+++ b/target/arm/tcg/cpu64.c
99
@@ -XXX,XX +XXX,XX @@ void aarch64_max_tcg_initfn(Object *obj)
100
cpu->ctr = 0x80038003; /* 32 byte I and D cacheline size, VIPT icache */
101
cpu->dcz_blocksize = 7; /* 512 bytes */
102
#endif
103
+ cpu->gm_blocksize = 6; /* 256 bytes */
104
105
cpu->sve_vq.supported = MAKE_64BIT_MASK(0, ARM_MAX_VQ);
106
cpu->sme_vq.supported = SVE_VQ_POW2_MAP;
107
diff --git a/target/arm/tcg/mte_helper.c b/target/arm/tcg/mte_helper.c
108
index XXXXXXX..XXXXXXX 100644
109
--- a/target/arm/tcg/mte_helper.c
110
+++ b/target/arm/tcg/mte_helper.c
111
@@ -XXX,XX +XXX,XX @@ void HELPER(st2g_stub)(CPUARMState *env, uint64_t ptr)
112
}
25
}
113
}
26
114
27
-static void pl061_reset(DeviceState *dev)
115
-#define LDGM_STGM_SIZE (4 << GMID_EL1_BS)
28
+static void pl061_enter_reset(Object *obj, ResetType type)
116
-
117
uint64_t HELPER(ldgm)(CPUARMState *env, uint64_t ptr)
29
{
118
{
30
- PL061State *s = PL061(dev);
119
int mmu_idx = cpu_mmu_index(env, false);
31
+ PL061State *s = PL061(obj);
120
uintptr_t ra = GETPC();
32
+
121
+ int gm_bs = env_archcpu(env)->gm_blocksize;
33
+ trace_pl061_reset(DEVICE(s)->canonical_path);
122
+ int gm_bs_bytes = 4 << gm_bs;
34
123
void *tag_mem;
35
/* reset values from PL061 TRM, Stellaris LM3S5P31 & LM3S8962 Data Sheet */
124
36
s->data = 0;
125
- ptr = QEMU_ALIGN_DOWN(ptr, LDGM_STGM_SIZE);
37
- s->old_out_data = 0;
126
+ ptr = QEMU_ALIGN_DOWN(ptr, gm_bs_bytes);
38
s->old_in_data = 0;
127
39
s->dir = 0;
128
/* Trap if accessing an invalid page. */
40
s->isense = 0;
129
tag_mem = allocation_tag_mem(env, mmu_idx, ptr, MMU_DATA_LOAD,
41
@@ -XXX,XX +XXX,XX @@ static void pl061_reset(DeviceState *dev)
130
- LDGM_STGM_SIZE, MMU_DATA_LOAD,
42
s->amsel = 0;
131
- LDGM_STGM_SIZE / (2 * TAG_GRANULE), ra);
132
+ gm_bs_bytes, MMU_DATA_LOAD,
133
+ gm_bs_bytes / (2 * TAG_GRANULE), ra);
134
135
/* The tag is squashed to zero if the page does not support tags. */
136
if (!tag_mem) {
137
return 0;
138
}
139
140
- QEMU_BUILD_BUG_ON(GMID_EL1_BS != 6);
141
/*
142
- * We are loading 64-bits worth of tags. The ordering of elements
143
- * within the word corresponds to a 64-bit little-endian operation.
144
+ * The ordering of elements within the word corresponds to
145
+ * a little-endian operation.
146
*/
147
- return ldq_le_p(tag_mem);
148
+ switch (gm_bs) {
149
+ case 6:
150
+ /* 256 bytes -> 16 tags -> 64 result bits */
151
+ return ldq_le_p(tag_mem);
152
+ default:
153
+ /* cpu configured with unsupported gm blocksize. */
154
+ g_assert_not_reached();
155
+ }
43
}
156
}
44
157
45
+static void pl061_hold_reset(Object *obj)
158
void HELPER(stgm)(CPUARMState *env, uint64_t ptr, uint64_t val)
46
+{
159
{
47
+ PL061State *s = PL061(obj);
160
int mmu_idx = cpu_mmu_index(env, false);
48
+ int i, level;
161
uintptr_t ra = GETPC();
49
+ uint8_t floating = pl061_floating(s);
162
+ int gm_bs = env_archcpu(env)->gm_blocksize;
50
+ uint8_t pullups = pl061_pullups(s);
163
+ int gm_bs_bytes = 4 << gm_bs;
51
+
164
void *tag_mem;
52
+ for (i = 0; i < N_GPIOS; i++) {
165
53
+ if (extract32(floating, i, 1)) {
166
- ptr = QEMU_ALIGN_DOWN(ptr, LDGM_STGM_SIZE);
54
+ continue;
167
+ ptr = QEMU_ALIGN_DOWN(ptr, gm_bs_bytes);
55
+ }
168
56
+ level = extract32(pullups, i, 1);
169
/* Trap if accessing an invalid page. */
57
+ trace_pl061_set_output(DEVICE(s)->canonical_path, i, level);
170
tag_mem = allocation_tag_mem(env, mmu_idx, ptr, MMU_DATA_STORE,
58
+ qemu_set_irq(s->out[i], level);
171
- LDGM_STGM_SIZE, MMU_DATA_LOAD,
172
- LDGM_STGM_SIZE / (2 * TAG_GRANULE), ra);
173
+ gm_bs_bytes, MMU_DATA_LOAD,
174
+ gm_bs_bytes / (2 * TAG_GRANULE), ra);
175
176
/*
177
* Tag store only happens if the page support tags,
178
@@ -XXX,XX +XXX,XX @@ void HELPER(stgm)(CPUARMState *env, uint64_t ptr, uint64_t val)
179
return;
180
}
181
182
- QEMU_BUILD_BUG_ON(GMID_EL1_BS != 6);
183
/*
184
- * We are storing 64-bits worth of tags. The ordering of elements
185
- * within the word corresponds to a 64-bit little-endian operation.
186
+ * The ordering of elements within the word corresponds to
187
+ * a little-endian operation.
188
*/
189
- stq_le_p(tag_mem, val);
190
+ switch (gm_bs) {
191
+ case 6:
192
+ stq_le_p(tag_mem, val);
193
+ break;
194
+ default:
195
+ /* cpu configured with unsupported gm blocksize. */
196
+ g_assert_not_reached();
59
+ }
197
+ }
60
+ s->old_out_data = pullups;
61
+}
62
+
63
static void pl061_set_irq(void * opaque, int irq, int level)
64
{
65
PL061State *s = (PL061State *)opaque;
66
@@ -XXX,XX +XXX,XX @@ static Property pl061_props[] = {
67
static void pl061_class_init(ObjectClass *klass, void *data)
68
{
69
DeviceClass *dc = DEVICE_CLASS(klass);
70
+ ResettableClass *rc = RESETTABLE_CLASS(klass);
71
72
dc->vmsd = &vmstate_pl061;
73
- dc->reset = &pl061_reset;
74
dc->realize = pl061_realize;
75
device_class_set_props(dc, pl061_props);
76
+ rc->phases.enter = pl061_enter_reset;
77
+ rc->phases.hold = pl061_hold_reset;
78
}
198
}
79
199
80
static const TypeInfo pl061_info = {
200
void HELPER(stzgm_tags)(CPUARMState *env, uint64_t ptr, uint64_t val)
81
diff --git a/hw/gpio/trace-events b/hw/gpio/trace-events
201
diff --git a/target/arm/tcg/translate-a64.c b/target/arm/tcg/translate-a64.c
82
index XXXXXXX..XXXXXXX 100644
202
index XXXXXXX..XXXXXXX 100644
83
--- a/hw/gpio/trace-events
203
--- a/target/arm/tcg/translate-a64.c
84
+++ b/hw/gpio/trace-events
204
+++ b/target/arm/tcg/translate-a64.c
85
@@ -XXX,XX +XXX,XX @@ pl061_input_change(const char *id, int gpio, int level) "%s input %d changed to
205
@@ -XXX,XX +XXX,XX @@ static bool trans_STGM(DisasContext *s, arg_ldst_tag *a)
86
pl061_update_istate(const char *id, uint32_t istate, uint32_t im, int level) "%s GPIORIS 0x%x GPIOIE 0x%x interrupt level %d"
206
gen_helper_stgm(cpu_env, addr, tcg_rt);
87
pl061_read(const char *id, uint64_t offset, uint64_t r) "%s offset 0x%" PRIx64 " value 0x%" PRIx64
207
} else {
88
pl061_write(const char *id, uint64_t offset, uint64_t value) "%s offset 0x%" PRIx64 " value 0x%" PRIx64
208
MMUAccessType acc = MMU_DATA_STORE;
89
+pl061_reset(const char *id) "%s reset"
209
- int size = 4 << GMID_EL1_BS;
90
210
+ int size = 4 << s->gm_blocksize;
91
# sifive_gpio.c
211
92
sifive_gpio_read(uint64_t offset, uint64_t r) "offset 0x%" PRIx64 " value 0x%" PRIx64
212
clean_addr = clean_data_tbi(s, addr);
213
tcg_gen_andi_i64(clean_addr, clean_addr, -size);
214
@@ -XXX,XX +XXX,XX @@ static bool trans_LDGM(DisasContext *s, arg_ldst_tag *a)
215
gen_helper_ldgm(tcg_rt, cpu_env, addr);
216
} else {
217
MMUAccessType acc = MMU_DATA_LOAD;
218
- int size = 4 << GMID_EL1_BS;
219
+ int size = 4 << s->gm_blocksize;
220
221
clean_addr = clean_data_tbi(s, addr);
222
tcg_gen_andi_i64(clean_addr, clean_addr, -size);
223
@@ -XXX,XX +XXX,XX @@ static void aarch64_tr_init_disas_context(DisasContextBase *dcbase,
224
dc->cp_regs = arm_cpu->cp_regs;
225
dc->features = env->features;
226
dc->dcz_blocksize = arm_cpu->dcz_blocksize;
227
+ dc->gm_blocksize = arm_cpu->gm_blocksize;
228
229
#ifdef CONFIG_USER_ONLY
230
/* In sve_probe_page, we assume TBI is enabled. */
93
--
231
--
94
2.20.1
232
2.34.1
95
96
diff view generated by jsdifflib
New patch
1
From: Richard Henderson <richard.henderson@linaro.org>
1
2
3
Support all of the easy GM block sizes.
4
Use direct memory operations, since the pointers are aligned.
5
6
While BS=2 (16 bytes, 1 tag) is a legal setting, that requires
7
an atomic store of one nibble. This is not difficult, but there
8
is also no point in supporting it until required.
9
10
Note that cortex-a710 sets GM blocksize to match its cacheline
11
size of 64 bytes. I expect many implementations will also
12
match the cacheline, which makes 16 bytes very unlikely.
13
14
Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
15
Reviewed-by: Peter Maydell <peter.maydell@linaro.org>
16
Message-id: 20230811214031.171020-4-richard.henderson@linaro.org
17
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
18
---
19
target/arm/cpu.c | 18 +++++++++---
20
target/arm/tcg/mte_helper.c | 56 +++++++++++++++++++++++++++++++------
21
2 files changed, 62 insertions(+), 12 deletions(-)
22
23
diff --git a/target/arm/cpu.c b/target/arm/cpu.c
24
index XXXXXXX..XXXXXXX 100644
25
--- a/target/arm/cpu.c
26
+++ b/target/arm/cpu.c
27
@@ -XXX,XX +XXX,XX @@ static void arm_cpu_realizefn(DeviceState *dev, Error **errp)
28
ID_PFR1, VIRTUALIZATION, 0);
29
}
30
31
+ if (cpu_isar_feature(aa64_mte, cpu)) {
32
+ /*
33
+ * The architectural range of GM blocksize is 2-6, however qemu
34
+ * doesn't support blocksize of 2 (see HELPER(ldgm)).
35
+ */
36
+ if (tcg_enabled()) {
37
+ assert(cpu->gm_blocksize >= 3 && cpu->gm_blocksize <= 6);
38
+ }
39
+
40
#ifndef CONFIG_USER_ONLY
41
- if (cpu->tag_memory == NULL && cpu_isar_feature(aa64_mte, cpu)) {
42
/*
43
* Disable the MTE feature bits if we do not have tag-memory
44
* provided by the machine.
45
*/
46
- cpu->isar.id_aa64pfr1 =
47
- FIELD_DP64(cpu->isar.id_aa64pfr1, ID_AA64PFR1, MTE, 0);
48
- }
49
+ if (cpu->tag_memory == NULL) {
50
+ cpu->isar.id_aa64pfr1 =
51
+ FIELD_DP64(cpu->isar.id_aa64pfr1, ID_AA64PFR1, MTE, 0);
52
+ }
53
#endif
54
+ }
55
56
if (tcg_enabled()) {
57
/*
58
diff --git a/target/arm/tcg/mte_helper.c b/target/arm/tcg/mte_helper.c
59
index XXXXXXX..XXXXXXX 100644
60
--- a/target/arm/tcg/mte_helper.c
61
+++ b/target/arm/tcg/mte_helper.c
62
@@ -XXX,XX +XXX,XX @@ uint64_t HELPER(ldgm)(CPUARMState *env, uint64_t ptr)
63
int gm_bs = env_archcpu(env)->gm_blocksize;
64
int gm_bs_bytes = 4 << gm_bs;
65
void *tag_mem;
66
+ uint64_t ret;
67
+ int shift;
68
69
ptr = QEMU_ALIGN_DOWN(ptr, gm_bs_bytes);
70
71
@@ -XXX,XX +XXX,XX @@ uint64_t HELPER(ldgm)(CPUARMState *env, uint64_t ptr)
72
73
/*
74
* The ordering of elements within the word corresponds to
75
- * a little-endian operation.
76
+ * a little-endian operation. Computation of shift comes from
77
+ *
78
+ * index = address<LOG2_TAG_GRANULE+3:LOG2_TAG_GRANULE>
79
+ * data<index*4+3:index*4> = tag
80
+ *
81
+ * Because of the alignment of ptr above, BS=6 has shift=0.
82
+ * All memory operations are aligned. Defer support for BS=2,
83
+ * requiring insertion or extraction of a nibble, until we
84
+ * support a cpu that requires it.
85
*/
86
switch (gm_bs) {
87
+ case 3:
88
+ /* 32 bytes -> 2 tags -> 8 result bits */
89
+ ret = *(uint8_t *)tag_mem;
90
+ break;
91
+ case 4:
92
+ /* 64 bytes -> 4 tags -> 16 result bits */
93
+ ret = cpu_to_le16(*(uint16_t *)tag_mem);
94
+ break;
95
+ case 5:
96
+ /* 128 bytes -> 8 tags -> 32 result bits */
97
+ ret = cpu_to_le32(*(uint32_t *)tag_mem);
98
+ break;
99
case 6:
100
/* 256 bytes -> 16 tags -> 64 result bits */
101
- return ldq_le_p(tag_mem);
102
+ return cpu_to_le64(*(uint64_t *)tag_mem);
103
default:
104
- /* cpu configured with unsupported gm blocksize. */
105
+ /*
106
+ * CPU configured with unsupported/invalid gm blocksize.
107
+ * This is detected early in arm_cpu_realizefn.
108
+ */
109
g_assert_not_reached();
110
}
111
+ shift = extract64(ptr, LOG2_TAG_GRANULE, 4) * 4;
112
+ return ret << shift;
113
}
114
115
void HELPER(stgm)(CPUARMState *env, uint64_t ptr, uint64_t val)
116
@@ -XXX,XX +XXX,XX @@ void HELPER(stgm)(CPUARMState *env, uint64_t ptr, uint64_t val)
117
int gm_bs = env_archcpu(env)->gm_blocksize;
118
int gm_bs_bytes = 4 << gm_bs;
119
void *tag_mem;
120
+ int shift;
121
122
ptr = QEMU_ALIGN_DOWN(ptr, gm_bs_bytes);
123
124
@@ -XXX,XX +XXX,XX @@ void HELPER(stgm)(CPUARMState *env, uint64_t ptr, uint64_t val)
125
return;
126
}
127
128
- /*
129
- * The ordering of elements within the word corresponds to
130
- * a little-endian operation.
131
- */
132
+ /* See LDGM for comments on BS and on shift. */
133
+ shift = extract64(ptr, LOG2_TAG_GRANULE, 4) * 4;
134
+ val >>= shift;
135
switch (gm_bs) {
136
+ case 3:
137
+ /* 32 bytes -> 2 tags -> 8 result bits */
138
+ *(uint8_t *)tag_mem = val;
139
+ break;
140
+ case 4:
141
+ /* 64 bytes -> 4 tags -> 16 result bits */
142
+ *(uint16_t *)tag_mem = cpu_to_le16(val);
143
+ break;
144
+ case 5:
145
+ /* 128 bytes -> 8 tags -> 32 result bits */
146
+ *(uint32_t *)tag_mem = cpu_to_le32(val);
147
+ break;
148
case 6:
149
- stq_le_p(tag_mem, val);
150
+ /* 256 bytes -> 16 tags -> 64 result bits */
151
+ *(uint64_t *)tag_mem = cpu_to_le64(val);
152
break;
153
default:
154
/* cpu configured with unsupported gm blocksize. */
155
--
156
2.34.1
diff view generated by jsdifflib
New patch
1
From: Richard Henderson <richard.henderson@linaro.org>
1
2
3
When the cpu support MTE, but the system does not, reduce cpu
4
support to user instructions at EL0 instead of completely
5
disabling MTE. If we encounter a cpu implementation which does
6
something else, we can revisit this setting.
7
8
Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
9
Reviewed-by: Peter Maydell <peter.maydell@linaro.org>
10
Message-id: 20230811214031.171020-5-richard.henderson@linaro.org
11
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
12
---
13
target/arm/cpu.c | 7 ++++---
14
1 file changed, 4 insertions(+), 3 deletions(-)
15
16
diff --git a/target/arm/cpu.c b/target/arm/cpu.c
17
index XXXXXXX..XXXXXXX 100644
18
--- a/target/arm/cpu.c
19
+++ b/target/arm/cpu.c
20
@@ -XXX,XX +XXX,XX @@ static void arm_cpu_realizefn(DeviceState *dev, Error **errp)
21
22
#ifndef CONFIG_USER_ONLY
23
/*
24
- * Disable the MTE feature bits if we do not have tag-memory
25
- * provided by the machine.
26
+ * If we do not have tag-memory provided by the machine,
27
+ * reduce MTE support to instructions enabled at EL0.
28
+ * This matches Cortex-A710 BROADCASTMTE input being LOW.
29
*/
30
if (cpu->tag_memory == NULL) {
31
cpu->isar.id_aa64pfr1 =
32
- FIELD_DP64(cpu->isar.id_aa64pfr1, ID_AA64PFR1, MTE, 0);
33
+ FIELD_DP64(cpu->isar.id_aa64pfr1, ID_AA64PFR1, MTE, 1);
34
}
35
#endif
36
}
37
--
38
2.34.1
diff view generated by jsdifflib
1
From: Alexandre Iooss <erdnaxe@crans.org>
1
From: Richard Henderson <richard.henderson@linaro.org>
2
2
3
This is a Cortex-M3 based machine. Information can be found at:
3
Do not hard-code the constants for Neoverse V1.
4
https://www.st.com/en/evaluation-tools/stm32vldiscovery.html
5
4
6
Signed-off-by: Alexandre Iooss <erdnaxe@crans.org>
5
Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
7
Reviewed-by: Alistair Francis <alistair.francis@wdc.com>
6
Reviewed-by: Peter Maydell <peter.maydell@linaro.org>
8
Message-id: 20210617165647.2575955-3-erdnaxe@crans.org
7
Message-id: 20230811214031.171020-6-richard.henderson@linaro.org
9
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
8
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
10
---
9
---
11
default-configs/devices/arm-softmmu.mak | 1 +
10
target/arm/tcg/cpu64.c | 48 ++++++++++++++++++++++++++++--------------
12
hw/arm/stm32vldiscovery.c | 66 +++++++++++++++++++++++++
11
1 file changed, 32 insertions(+), 16 deletions(-)
13
MAINTAINERS | 6 +++
14
hw/arm/Kconfig | 4 ++
15
hw/arm/meson.build | 1 +
16
5 files changed, 78 insertions(+)
17
create mode 100644 hw/arm/stm32vldiscovery.c
18
12
19
diff --git a/default-configs/devices/arm-softmmu.mak b/default-configs/devices/arm-softmmu.mak
13
diff --git a/target/arm/tcg/cpu64.c b/target/arm/tcg/cpu64.c
20
index XXXXXXX..XXXXXXX 100644
14
index XXXXXXX..XXXXXXX 100644
21
--- a/default-configs/devices/arm-softmmu.mak
15
--- a/target/arm/tcg/cpu64.c
22
+++ b/default-configs/devices/arm-softmmu.mak
16
+++ b/target/arm/tcg/cpu64.c
23
@@ -XXX,XX +XXX,XX @@ CONFIG_CHEETAH=y
24
CONFIG_SX1=y
25
CONFIG_NSERIES=y
26
CONFIG_STELLARIS=y
27
+CONFIG_STM32VLDISCOVERY=y
28
CONFIG_REALVIEW=y
29
CONFIG_VERSATILE=y
30
CONFIG_VEXPRESS=y
31
diff --git a/hw/arm/stm32vldiscovery.c b/hw/arm/stm32vldiscovery.c
32
new file mode 100644
33
index XXXXXXX..XXXXXXX
34
--- /dev/null
35
+++ b/hw/arm/stm32vldiscovery.c
36
@@ -XXX,XX +XXX,XX @@
17
@@ -XXX,XX +XXX,XX @@
37
+/*
18
#include "qemu/module.h"
38
+ * ST STM32VLDISCOVERY machine
19
#include "qapi/visitor.h"
39
+ *
20
#include "hw/qdev-properties.h"
40
+ * Copyright (c) 2021 Alexandre Iooss <erdnaxe@crans.org>
21
+#include "qemu/units.h"
41
+ * Copyright (c) 2014 Alistair Francis <alistair@alistair23.me>
22
#include "internals.h"
42
+ *
23
#include "cpregs.h"
43
+ * Permission is hereby granted, free of charge, to any person obtaining a copy
24
44
+ * of this software and associated documentation files (the "Software"), to deal
25
+static uint64_t make_ccsidr64(unsigned assoc, unsigned linesize,
45
+ * in the Software without restriction, including without limitation the rights
26
+ unsigned cachesize)
46
+ * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
47
+ * copies of the Software, and to permit persons to whom the Software is
48
+ * furnished to do so, subject to the following conditions:
49
+ *
50
+ * The above copyright notice and this permission notice shall be included in
51
+ * all copies or substantial portions of the Software.
52
+ *
53
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
54
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
55
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
56
+ * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
57
+ * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
58
+ * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
59
+ * THE SOFTWARE.
60
+ */
61
+
62
+#include "qemu/osdep.h"
63
+#include "qapi/error.h"
64
+#include "hw/boards.h"
65
+#include "hw/qdev-properties.h"
66
+#include "qemu/error-report.h"
67
+#include "hw/arm/stm32f100_soc.h"
68
+#include "hw/arm/boot.h"
69
+
70
+/* stm32vldiscovery implementation is derived from netduinoplus2 */
71
+
72
+/* Main SYSCLK frequency in Hz (24MHz) */
73
+#define SYSCLK_FRQ 24000000ULL
74
+
75
+static void stm32vldiscovery_init(MachineState *machine)
76
+{
27
+{
77
+ DeviceState *dev;
28
+ unsigned lg_linesize = ctz32(linesize);
29
+ unsigned sets;
78
+
30
+
79
+ /*
31
+ /*
80
+ * TODO: ideally we would model the SoC RCC and let it handle
32
+ * The 64-bit CCSIDR_EL1 format is:
81
+ * system_clock_scale, including its ability to define different
33
+ * [55:32] number of sets - 1
82
+ * possible SYSCLK sources.
34
+ * [23:3] associativity - 1
35
+ * [2:0] log2(linesize) - 4
36
+ * so 0 == 16 bytes, 1 == 32 bytes, 2 == 64 bytes, etc
83
+ */
37
+ */
84
+ system_clock_scale = NANOSECONDS_PER_SECOND / SYSCLK_FRQ;
38
+ assert(assoc != 0);
39
+ assert(is_power_of_2(linesize));
40
+ assert(lg_linesize >= 4 && lg_linesize <= 7 + 4);
85
+
41
+
86
+ dev = qdev_new(TYPE_STM32F100_SOC);
42
+ /* sets * associativity * linesize == cachesize. */
87
+ qdev_prop_set_string(dev, "cpu-type", ARM_CPU_TYPE_NAME("cortex-m3"));
43
+ sets = cachesize / (assoc * linesize);
88
+ sysbus_realize_and_unref(SYS_BUS_DEVICE(dev), &error_fatal);
44
+ assert(cachesize % (assoc * linesize) == 0);
89
+
45
+
90
+ armv7m_load_kernel(ARM_CPU(first_cpu),
46
+ return ((uint64_t)(sets - 1) << 32)
91
+ machine->kernel_filename,
47
+ | ((assoc - 1) << 3)
92
+ FLASH_SIZE);
48
+ | (lg_linesize - 4);
93
+}
49
+}
94
+
50
+
95
+static void stm32vldiscovery_machine_init(MachineClass *mc)
51
static void aarch64_a35_initfn(Object *obj)
96
+{
52
{
97
+ mc->desc = "ST STM32VLDISCOVERY (Cortex-M3)";
53
ARMCPU *cpu = ARM_CPU(obj);
98
+ mc->init = stm32vldiscovery_init;
54
@@ -XXX,XX +XXX,XX @@ static void aarch64_neoverse_v1_initfn(Object *obj)
99
+}
55
* The Neoverse-V1 r1p2 TRM lists 32-bit format CCSIDR_EL1 values,
100
+
56
* but also says it implements CCIDX, which means they should be
101
+DEFINE_MACHINE("stm32vldiscovery", stm32vldiscovery_machine_init)
57
* 64-bit format. So we here use values which are based on the textual
102
+
58
- * information in chapter 2 of the TRM (and on the fact that
103
diff --git a/MAINTAINERS b/MAINTAINERS
59
- * sets * associativity * linesize == cachesize).
104
index XXXXXXX..XXXXXXX 100644
60
- *
105
--- a/MAINTAINERS
61
- * The 64-bit CCSIDR_EL1 format is:
106
+++ b/MAINTAINERS
62
- * [55:32] number of sets - 1
107
@@ -XXX,XX +XXX,XX @@ F: hw/*/stellaris*
63
- * [23:3] associativity - 1
108
F: include/hw/input/gamepad.h
64
- * [2:0] log2(linesize) - 4
109
F: docs/system/arm/stellaris.rst
65
- * so 0 == 16 bytes, 1 == 32 bytes, 2 == 64 bytes, etc
110
66
- *
111
+STM32VLDISCOVERY
67
- * L1: 4-way set associative 64-byte line size, total size 64K,
112
+M: Alexandre Iooss <erdnaxe@crans.org>
68
- * so sets is 256.
113
+L: qemu-arm@nongnu.org
69
+ * information in chapter 2 of the TRM:
114
+S: Maintained
70
*
115
+F: hw/arm/stm32vldiscovery.c
71
+ * L1: 4-way set associative 64-byte line size, total size 64K.
116
+
72
* L2: 8-way set associative, 64 byte line size, either 512K or 1MB.
117
Versatile Express
73
- * We pick 1MB, so this has 2048 sets.
118
M: Peter Maydell <peter.maydell@linaro.org>
74
- *
119
L: qemu-arm@nongnu.org
75
* L3: No L3 (this matches the CLIDR_EL1 value).
120
diff --git a/hw/arm/Kconfig b/hw/arm/Kconfig
76
*/
121
index XXXXXXX..XXXXXXX 100644
77
- cpu->ccsidr[0] = 0x000000ff0000001aull; /* 64KB L1 dcache */
122
--- a/hw/arm/Kconfig
78
- cpu->ccsidr[1] = 0x000000ff0000001aull; /* 64KB L1 icache */
123
+++ b/hw/arm/Kconfig
79
- cpu->ccsidr[2] = 0x000007ff0000003aull; /* 1MB L2 cache */
124
@@ -XXX,XX +XXX,XX @@ config STELLARIS
80
+ cpu->ccsidr[0] = make_ccsidr64(4, 64, 64 * KiB); /* L1 dcache */
125
select STELLARIS_ENET # ethernet
81
+ cpu->ccsidr[1] = cpu->ccsidr[0]; /* L1 icache */
126
select UNIMP
82
+ cpu->ccsidr[2] = make_ccsidr64(8, 64, 1 * MiB); /* L2 cache */
127
83
128
+config STM32VLDISCOVERY
84
/* From 3.2.115 SCTLR_EL3 */
129
+ bool
85
cpu->reset_sctlr = 0x30c50838;
130
+ select STM32F100_SOC
131
+
132
config STRONGARM
133
bool
134
select PXA2XX
135
diff --git a/hw/arm/meson.build b/hw/arm/meson.build
136
index XXXXXXX..XXXXXXX 100644
137
--- a/hw/arm/meson.build
138
+++ b/hw/arm/meson.build
139
@@ -XXX,XX +XXX,XX @@ arm_ss.add(when: 'CONFIG_Z2', if_true: files('z2.c'))
140
arm_ss.add(when: 'CONFIG_REALVIEW', if_true: files('realview.c'))
141
arm_ss.add(when: 'CONFIG_SBSA_REF', if_true: files('sbsa-ref.c'))
142
arm_ss.add(when: 'CONFIG_STELLARIS', if_true: files('stellaris.c'))
143
+arm_ss.add(when: 'CONFIG_STM32VLDISCOVERY', if_true: files('stm32vldiscovery.c'))
144
arm_ss.add(when: 'CONFIG_COLLIE', if_true: files('collie.c'))
145
arm_ss.add(when: 'CONFIG_VERSATILE', if_true: files('versatilepb.c'))
146
arm_ss.add(when: 'CONFIG_VEXPRESS', if_true: files('vexpress.c'))
147
--
86
--
148
2.20.1
87
2.34.1
149
150
diff view generated by jsdifflib
1
From: "hnick@vmware.com" <hnick@vmware.com>
1
From: Richard Henderson <richard.henderson@linaro.org>
2
2
3
Signed-off-by: Nick Hudson <hnick@vmware.com>
3
Access to many of the special registers is enabled or disabled
4
by ACTLR_EL[23], which we implement as constant 0, which means
5
that all writes outside EL3 should trap.
6
7
Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
4
Reviewed-by: Peter Maydell <peter.maydell@linaro.org>
8
Reviewed-by: Peter Maydell <peter.maydell@linaro.org>
9
Message-id: 20230811214031.171020-7-richard.henderson@linaro.org
5
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
10
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
6
---
11
---
7
target/arm/helper.c | 16 +++++++++++++---
12
target/arm/cpregs.h | 2 ++
8
1 file changed, 13 insertions(+), 3 deletions(-)
13
target/arm/helper.c | 4 ++--
14
target/arm/tcg/cpu64.c | 46 +++++++++++++++++++++++++++++++++---------
15
3 files changed, 41 insertions(+), 11 deletions(-)
9
16
17
diff --git a/target/arm/cpregs.h b/target/arm/cpregs.h
18
index XXXXXXX..XXXXXXX 100644
19
--- a/target/arm/cpregs.h
20
+++ b/target/arm/cpregs.h
21
@@ -XXX,XX +XXX,XX @@ static inline void define_cortex_a72_a57_a53_cp_reginfo(ARMCPU *cpu) { }
22
void define_cortex_a72_a57_a53_cp_reginfo(ARMCPU *cpu);
23
#endif
24
25
+CPAccessResult access_tvm_trvm(CPUARMState *, const ARMCPRegInfo *, bool);
26
+
27
#endif /* TARGET_ARM_CPREGS_H */
10
diff --git a/target/arm/helper.c b/target/arm/helper.c
28
diff --git a/target/arm/helper.c b/target/arm/helper.c
11
index XXXXXXX..XXXXXXX 100644
29
index XXXXXXX..XXXXXXX 100644
12
--- a/target/arm/helper.c
30
--- a/target/arm/helper.c
13
+++ b/target/arm/helper.c
31
+++ b/target/arm/helper.c
14
@@ -XXX,XX +XXX,XX @@ static const ARMCPRegInfo debug_cp_reginfo[] = {
32
@@ -XXX,XX +XXX,XX @@ static CPAccessResult access_tpm(CPUARMState *env, const ARMCPRegInfo *ri,
15
.access = PL1_RW, .accessfn = access_tda,
33
}
16
.fieldoffset = offsetof(CPUARMState, cp15.mdscr_el1),
34
17
.resetvalue = 0 },
35
/* Check for traps from EL1 due to HCR_EL2.TVM and HCR_EL2.TRVM. */
18
- /* MDCCSR_EL0, aka DBGDSCRint. This is a read-only mirror of MDSCR_EL1.
36
-static CPAccessResult access_tvm_trvm(CPUARMState *env, const ARMCPRegInfo *ri,
19
+ /*
37
- bool isread)
20
+ * MDCCSR_EL0[30:29] map to EDSCR[30:29]. Simply RAZ as the external
38
+CPAccessResult access_tvm_trvm(CPUARMState *env, const ARMCPRegInfo *ri,
21
+ * Debug Communication Channel is not implemented.
39
+ bool isread)
22
+ */
40
{
23
+ { .name = "MDCCSR_EL0", .state = ARM_CP_STATE_AA64,
41
if (arm_current_el(env) == 1) {
24
+ .opc0 = 2, .opc1 = 3, .crn = 0, .crm = 1, .opc2 = 0,
42
uint64_t trap = isread ? HCR_TRVM : HCR_TVM;
25
+ .access = PL0_R, .accessfn = access_tda,
43
diff --git a/target/arm/tcg/cpu64.c b/target/arm/tcg/cpu64.c
26
+ .type = ARM_CP_CONST, .resetvalue = 0 },
44
index XXXXXXX..XXXXXXX 100644
27
+ /*
45
--- a/target/arm/tcg/cpu64.c
28
+ * DBGDSCRint[15,12,5:2] map to MDSCR_EL1[15,12,5:2]. Map all bits as
46
+++ b/target/arm/tcg/cpu64.c
29
+ * it is unlikely a guest will care.
47
@@ -XXX,XX +XXX,XX @@ static void aarch64_a64fx_initfn(Object *obj)
30
* We don't implement the configurable EL0 access.
48
/* TODO: Add A64FX specific HPC extension registers */
31
*/
49
}
32
- { .name = "MDCCSR_EL0", .state = ARM_CP_STATE_BOTH,
50
33
- .cp = 14, .opc0 = 2, .opc1 = 0, .crn = 0, .crm = 1, .opc2 = 0,
51
+static CPAccessResult access_actlr_w(CPUARMState *env, const ARMCPRegInfo *r,
34
+ { .name = "DBGDSCRint", .state = ARM_CP_STATE_AA32,
52
+ bool read)
35
+ .cp = 14, .opc1 = 0, .crn = 0, .crm = 1, .opc2 = 0,
53
+{
36
.type = ARM_CP_ALIAS,
54
+ if (!read) {
37
.access = PL1_R, .accessfn = access_tda,
55
+ int el = arm_current_el(env);
38
.fieldoffset = offsetof(CPUARMState, cp15.mdscr_el1), },
56
+
57
+ /* Because ACTLR_EL2 is constant 0, writes below EL2 trap to EL2. */
58
+ if (el < 2 && arm_is_el2_enabled(env)) {
59
+ return CP_ACCESS_TRAP_EL2;
60
+ }
61
+ /* Because ACTLR_EL3 is constant 0, writes below EL3 trap to EL3. */
62
+ if (el < 3 && arm_feature(env, ARM_FEATURE_EL3)) {
63
+ return CP_ACCESS_TRAP_EL3;
64
+ }
65
+ }
66
+ return CP_ACCESS_OK;
67
+}
68
+
69
static const ARMCPRegInfo neoverse_n1_cp_reginfo[] = {
70
{ .name = "ATCR_EL1", .state = ARM_CP_STATE_AA64,
71
.opc0 = 3, .opc1 = 0, .crn = 15, .crm = 7, .opc2 = 0,
72
- .access = PL1_RW, .type = ARM_CP_CONST, .resetvalue = 0 },
73
+ .access = PL1_RW, .type = ARM_CP_CONST, .resetvalue = 0,
74
+ /* Traps and enables are the same as for TCR_EL1. */
75
+ .accessfn = access_tvm_trvm, .fgt = FGT_TCR_EL1, },
76
{ .name = "ATCR_EL2", .state = ARM_CP_STATE_AA64,
77
.opc0 = 3, .opc1 = 4, .crn = 15, .crm = 7, .opc2 = 0,
78
.access = PL2_RW, .type = ARM_CP_CONST, .resetvalue = 0 },
79
@@ -XXX,XX +XXX,XX @@ static const ARMCPRegInfo neoverse_n1_cp_reginfo[] = {
80
.access = PL2_RW, .type = ARM_CP_CONST, .resetvalue = 0 },
81
{ .name = "CPUACTLR_EL1", .state = ARM_CP_STATE_AA64,
82
.opc0 = 3, .opc1 = 0, .crn = 15, .crm = 1, .opc2 = 0,
83
- .access = PL1_RW, .type = ARM_CP_CONST, .resetvalue = 0 },
84
+ .access = PL1_RW, .type = ARM_CP_CONST, .resetvalue = 0,
85
+ .accessfn = access_actlr_w },
86
{ .name = "CPUACTLR2_EL1", .state = ARM_CP_STATE_AA64,
87
.opc0 = 3, .opc1 = 0, .crn = 15, .crm = 1, .opc2 = 1,
88
- .access = PL1_RW, .type = ARM_CP_CONST, .resetvalue = 0 },
89
+ .access = PL1_RW, .type = ARM_CP_CONST, .resetvalue = 0,
90
+ .accessfn = access_actlr_w },
91
{ .name = "CPUACTLR3_EL1", .state = ARM_CP_STATE_AA64,
92
.opc0 = 3, .opc1 = 0, .crn = 15, .crm = 1, .opc2 = 2,
93
- .access = PL1_RW, .type = ARM_CP_CONST, .resetvalue = 0 },
94
+ .access = PL1_RW, .type = ARM_CP_CONST, .resetvalue = 0,
95
+ .accessfn = access_actlr_w },
96
/*
97
* Report CPUCFR_EL1.SCU as 1, as we do not implement the DSU
98
* (and in particular its system registers).
99
@@ -XXX,XX +XXX,XX @@ static const ARMCPRegInfo neoverse_n1_cp_reginfo[] = {
100
.access = PL1_R, .type = ARM_CP_CONST, .resetvalue = 4 },
101
{ .name = "CPUECTLR_EL1", .state = ARM_CP_STATE_AA64,
102
.opc0 = 3, .opc1 = 0, .crn = 15, .crm = 1, .opc2 = 4,
103
- .access = PL1_RW, .type = ARM_CP_CONST, .resetvalue = 0x961563010 },
104
+ .access = PL1_RW, .type = ARM_CP_CONST, .resetvalue = 0x961563010,
105
+ .accessfn = access_actlr_w },
106
{ .name = "CPUPCR_EL3", .state = ARM_CP_STATE_AA64,
107
.opc0 = 3, .opc1 = 6, .crn = 15, .crm = 8, .opc2 = 1,
108
.access = PL3_RW, .type = ARM_CP_CONST, .resetvalue = 0 },
109
@@ -XXX,XX +XXX,XX @@ static const ARMCPRegInfo neoverse_n1_cp_reginfo[] = {
110
.access = PL3_RW, .type = ARM_CP_CONST, .resetvalue = 0 },
111
{ .name = "CPUPWRCTLR_EL1", .state = ARM_CP_STATE_AA64,
112
.opc0 = 3, .opc1 = 0, .crn = 15, .crm = 2, .opc2 = 7,
113
- .access = PL1_RW, .type = ARM_CP_CONST, .resetvalue = 0 },
114
+ .access = PL1_RW, .type = ARM_CP_CONST, .resetvalue = 0,
115
+ .accessfn = access_actlr_w },
116
{ .name = "ERXPFGCDN_EL1", .state = ARM_CP_STATE_AA64,
117
.opc0 = 3, .opc1 = 0, .crn = 15, .crm = 2, .opc2 = 2,
118
- .access = PL1_RW, .type = ARM_CP_CONST, .resetvalue = 0 },
119
+ .access = PL1_RW, .type = ARM_CP_CONST, .resetvalue = 0,
120
+ .accessfn = access_actlr_w },
121
{ .name = "ERXPFGCTL_EL1", .state = ARM_CP_STATE_AA64,
122
.opc0 = 3, .opc1 = 0, .crn = 15, .crm = 2, .opc2 = 1,
123
- .access = PL1_RW, .type = ARM_CP_CONST, .resetvalue = 0 },
124
+ .access = PL1_RW, .type = ARM_CP_CONST, .resetvalue = 0,
125
+ .accessfn = access_actlr_w },
126
{ .name = "ERXPFGF_EL1", .state = ARM_CP_STATE_AA64,
127
.opc0 = 3, .opc1 = 0, .crn = 15, .crm = 2, .opc2 = 0,
128
- .access = PL1_RW, .type = ARM_CP_CONST, .resetvalue = 0 },
129
+ .access = PL1_RW, .type = ARM_CP_CONST, .resetvalue = 0,
130
+ .accessfn = access_actlr_w },
131
};
132
133
static void define_neoverse_n1_cp_reginfo(ARMCPU *cpu)
39
--
134
--
40
2.20.1
135
2.34.1
41
42
diff view generated by jsdifflib
New patch
1
From: Richard Henderson <richard.henderson@linaro.org>
1
2
3
There is only one additional EL1 register modeled, which
4
also needs to use access_actlr_w.
5
6
Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
7
Reviewed-by: Peter Maydell <peter.maydell@linaro.org>
8
Message-id: 20230811214031.171020-8-richard.henderson@linaro.org
9
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
10
---
11
target/arm/tcg/cpu64.c | 3 ++-
12
1 file changed, 2 insertions(+), 1 deletion(-)
13
14
diff --git a/target/arm/tcg/cpu64.c b/target/arm/tcg/cpu64.c
15
index XXXXXXX..XXXXXXX 100644
16
--- a/target/arm/tcg/cpu64.c
17
+++ b/target/arm/tcg/cpu64.c
18
@@ -XXX,XX +XXX,XX @@ static void define_neoverse_n1_cp_reginfo(ARMCPU *cpu)
19
static const ARMCPRegInfo neoverse_v1_cp_reginfo[] = {
20
{ .name = "CPUECTLR2_EL1", .state = ARM_CP_STATE_AA64,
21
.opc0 = 3, .opc1 = 0, .crn = 15, .crm = 1, .opc2 = 5,
22
- .access = PL1_RW, .type = ARM_CP_CONST, .resetvalue = 0 },
23
+ .access = PL1_RW, .type = ARM_CP_CONST, .resetvalue = 0,
24
+ .accessfn = access_actlr_w },
25
{ .name = "CPUPPMCR_EL3", .state = ARM_CP_STATE_AA64,
26
.opc0 = 3, .opc1 = 6, .crn = 15, .crm = 2, .opc2 = 0,
27
.access = PL3_RW, .type = ARM_CP_CONST, .resetvalue = 0 },
28
--
29
2.34.1
diff view generated by jsdifflib
New patch
1
From: Richard Henderson <richard.henderson@linaro.org>
1
2
3
Like FEAT_TRF (Self-hosted Trace Extension), suppress tracing
4
external to the cpu, which is out of scope for QEMU.
5
6
Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
7
Reviewed-by: Peter Maydell <peter.maydell@linaro.org>
8
Message-id: 20230811214031.171020-10-richard.henderson@linaro.org
9
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
10
---
11
target/arm/cpu.c | 3 +++
12
1 file changed, 3 insertions(+)
13
14
diff --git a/target/arm/cpu.c b/target/arm/cpu.c
15
index XXXXXXX..XXXXXXX 100644
16
--- a/target/arm/cpu.c
17
+++ b/target/arm/cpu.c
18
@@ -XXX,XX +XXX,XX @@ static void arm_cpu_realizefn(DeviceState *dev, Error **errp)
19
/* FEAT_SPE (Statistical Profiling Extension) */
20
cpu->isar.id_aa64dfr0 =
21
FIELD_DP64(cpu->isar.id_aa64dfr0, ID_AA64DFR0, PMSVER, 0);
22
+ /* FEAT_TRBE (Trace Buffer Extension) */
23
+ cpu->isar.id_aa64dfr0 =
24
+ FIELD_DP64(cpu->isar.id_aa64dfr0, ID_AA64DFR0, TRACEBUFFER, 0);
25
/* FEAT_TRF (Self-hosted Trace Extension) */
26
cpu->isar.id_aa64dfr0 =
27
FIELD_DP64(cpu->isar.id_aa64dfr0, ID_AA64DFR0, TRACEFILT, 0);
28
--
29
2.34.1
diff view generated by jsdifflib
New patch
1
From: Richard Henderson <richard.henderson@linaro.org>
1
2
3
This feature allows the operating system to set TCR_ELx.HWU*
4
to allow the implementation to use the PBHA bits from the
5
block and page descriptors for for IMPLEMENTATION DEFINED
6
purposes. Since QEMU has no need to use these bits, we may
7
simply ignore them.
8
9
Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
10
Reviewed-by: Peter Maydell <peter.maydell@linaro.org>
11
Message-id: 20230811214031.171020-11-richard.henderson@linaro.org
12
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
13
---
14
docs/system/arm/emulation.rst | 1 +
15
target/arm/tcg/cpu32.c | 2 +-
16
target/arm/tcg/cpu64.c | 2 +-
17
3 files changed, 3 insertions(+), 2 deletions(-)
18
19
diff --git a/docs/system/arm/emulation.rst b/docs/system/arm/emulation.rst
20
index XXXXXXX..XXXXXXX 100644
21
--- a/docs/system/arm/emulation.rst
22
+++ b/docs/system/arm/emulation.rst
23
@@ -XXX,XX +XXX,XX @@ the following architecture extensions:
24
- FEAT_HAFDBS (Hardware management of the access flag and dirty bit state)
25
- FEAT_HCX (Support for the HCRX_EL2 register)
26
- FEAT_HPDS (Hierarchical permission disables)
27
+- FEAT_HPDS2 (Translation table page-based hardware attributes)
28
- FEAT_I8MM (AArch64 Int8 matrix multiplication instructions)
29
- FEAT_IDST (ID space trap handling)
30
- FEAT_IESB (Implicit error synchronization event)
31
diff --git a/target/arm/tcg/cpu32.c b/target/arm/tcg/cpu32.c
32
index XXXXXXX..XXXXXXX 100644
33
--- a/target/arm/tcg/cpu32.c
34
+++ b/target/arm/tcg/cpu32.c
35
@@ -XXX,XX +XXX,XX @@ void aa32_max_features(ARMCPU *cpu)
36
cpu->isar.id_mmfr3 = t;
37
38
t = cpu->isar.id_mmfr4;
39
- t = FIELD_DP32(t, ID_MMFR4, HPDS, 1); /* FEAT_AA32HPD */
40
+ t = FIELD_DP32(t, ID_MMFR4, HPDS, 2); /* FEAT_HPDS2 */
41
t = FIELD_DP32(t, ID_MMFR4, AC2, 1); /* ACTLR2, HACTLR2 */
42
t = FIELD_DP32(t, ID_MMFR4, CNP, 1); /* FEAT_TTCNP */
43
t = FIELD_DP32(t, ID_MMFR4, XNX, 1); /* FEAT_XNX */
44
diff --git a/target/arm/tcg/cpu64.c b/target/arm/tcg/cpu64.c
45
index XXXXXXX..XXXXXXX 100644
46
--- a/target/arm/tcg/cpu64.c
47
+++ b/target/arm/tcg/cpu64.c
48
@@ -XXX,XX +XXX,XX @@ void aarch64_max_tcg_initfn(Object *obj)
49
t = FIELD_DP64(t, ID_AA64MMFR1, HAFDBS, 2); /* FEAT_HAFDBS */
50
t = FIELD_DP64(t, ID_AA64MMFR1, VMIDBITS, 2); /* FEAT_VMID16 */
51
t = FIELD_DP64(t, ID_AA64MMFR1, VH, 1); /* FEAT_VHE */
52
- t = FIELD_DP64(t, ID_AA64MMFR1, HPDS, 1); /* FEAT_HPDS */
53
+ t = FIELD_DP64(t, ID_AA64MMFR1, HPDS, 2); /* FEAT_HPDS2 */
54
t = FIELD_DP64(t, ID_AA64MMFR1, LO, 1); /* FEAT_LOR */
55
t = FIELD_DP64(t, ID_AA64MMFR1, PAN, 3); /* FEAT_PAN3 */
56
t = FIELD_DP64(t, ID_AA64MMFR1, XNX, 1); /* FEAT_XNX */
57
--
58
2.34.1
diff view generated by jsdifflib
1
From: Alexandre Iooss <erdnaxe@crans.org>
1
From: Alex Bennée <alex.bennee@linaro.org>
2
2
3
This adds the target guide for Netduino 2, Netduino Plus 2 and STM32VLDISCOVERY.
3
This is a mandatory feature for Armv8.1 architectures but we don't
4
state the feature clearly in our emulation list. Also include
5
FEAT_CRC32 comment in aarch64_max_tcg_initfn for ease of grepping.
4
6
5
Signed-off-by: Alexandre Iooss <erdnaxe@crans.org>
7
Reviewed-by: Philippe Mathieu-Daudé <philmd@linaro.org>
6
Reviewed-by: Alistair Francis <alistair.francis@wdc.com>
8
Signed-off-by: Alex Bennée <alex.bennee@linaro.org>
7
Message-id: 20210617165647.2575955-4-erdnaxe@crans.org
9
Message-id: 20230824075406.1515566-1-alex.bennee@linaro.org
10
Cc: qemu-stable@nongnu.org
11
Message-Id: <20230222110104.3996971-1-alex.bennee@linaro.org>
12
[PMM: pluralize 'instructions' in docs]
8
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
13
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
9
---
14
---
10
docs/system/arm/stm32.rst | 66 ++++++++++++++++++++++++++++++++++++++
15
docs/system/arm/emulation.rst | 1 +
11
docs/system/target-arm.rst | 1 +
16
target/arm/tcg/cpu64.c | 2 +-
12
MAINTAINERS | 1 +
17
2 files changed, 2 insertions(+), 1 deletion(-)
13
3 files changed, 68 insertions(+)
14
create mode 100644 docs/system/arm/stm32.rst
15
18
16
diff --git a/docs/system/arm/stm32.rst b/docs/system/arm/stm32.rst
19
diff --git a/docs/system/arm/emulation.rst b/docs/system/arm/emulation.rst
17
new file mode 100644
18
index XXXXXXX..XXXXXXX
19
--- /dev/null
20
+++ b/docs/system/arm/stm32.rst
21
@@ -XXX,XX +XXX,XX @@
22
+STMicroelectronics STM32 boards (``netduino2``, ``netduinoplus2``, ``stm32vldiscovery``)
23
+========================================================================================
24
+
25
+The `STM32`_ chips are a family of 32-bit ARM-based microcontroller by
26
+STMicroelectronics.
27
+
28
+.. _STM32: https://www.st.com/en/microcontrollers-microprocessors/stm32-32-bit-arm-cortex-mcus.html
29
+
30
+The STM32F1 series is based on ARM Cortex-M3 core. The following machines are
31
+based on this chip :
32
+
33
+- ``stm32vldiscovery`` STM32VLDISCOVERY board with STM32F100RBT6 microcontroller
34
+
35
+The STM32F2 series is based on ARM Cortex-M3 core. The following machines are
36
+based on this chip :
37
+
38
+- ``netduino2`` Netduino 2 board with STM32F205RFT6 microcontroller
39
+
40
+The STM32F4 series is based on ARM Cortex-M4F core. This series is pin-to-pin
41
+compatible with STM32F2 series. The following machines are based on this chip :
42
+
43
+- ``netduinoplus2`` Netduino Plus 2 board with STM32F405RGT6 microcontroller
44
+
45
+There are many other STM32 series that are currently not supported by QEMU.
46
+
47
+Supported devices
48
+-----------------
49
+
50
+ * ARM Cortex-M3, Cortex M4F
51
+ * Analog to Digital Converter (ADC)
52
+ * EXTI interrupt
53
+ * Serial ports (USART)
54
+ * SPI controller
55
+ * System configuration (SYSCFG)
56
+ * Timer controller (TIMER)
57
+
58
+Missing devices
59
+---------------
60
+
61
+ * Camera interface (DCMI)
62
+ * Controller Area Network (CAN)
63
+ * Cycle Redundancy Check (CRC) calculation unit
64
+ * Digital to Analog Converter (DAC)
65
+ * DMA controller
66
+ * Ethernet controller
67
+ * Flash Interface Unit
68
+ * GPIO controller
69
+ * I2C controller
70
+ * Inter-Integrated Sound (I2S) controller
71
+ * Power supply configuration (PWR)
72
+ * Random Number Generator (RNG)
73
+ * Real-Time Clock (RTC) controller
74
+ * Reset and Clock Controller (RCC)
75
+ * Secure Digital Input/Output (SDIO) interface
76
+ * USB OTG
77
+ * Watchdog controller (IWDG, WWDG)
78
+
79
+Boot options
80
+------------
81
+
82
+The STM32 machines can be started using the ``-kernel`` option to load a
83
+firmware. Example:
84
+
85
+.. code-block:: bash
86
+
87
+ $ qemu-system-arm -M stm32vldiscovery -kernel firmware.bin
88
diff --git a/docs/system/target-arm.rst b/docs/system/target-arm.rst
89
index XXXXXXX..XXXXXXX 100644
20
index XXXXXXX..XXXXXXX 100644
90
--- a/docs/system/target-arm.rst
21
--- a/docs/system/arm/emulation.rst
91
+++ b/docs/system/target-arm.rst
22
+++ b/docs/system/arm/emulation.rst
92
@@ -XXX,XX +XXX,XX @@ undocumented; you can get a complete list by running
23
@@ -XXX,XX +XXX,XX @@ the following architecture extensions:
93
arm/collie
24
- FEAT_BBM at level 2 (Translation table break-before-make levels)
94
arm/sx1
25
- FEAT_BF16 (AArch64 BFloat16 instructions)
95
arm/stellaris
26
- FEAT_BTI (Branch Target Identification)
96
+ arm/stm32
27
+- FEAT_CRC32 (CRC32 instructions)
97
arm/virt
28
- FEAT_CSV2 (Cache speculation variant 2)
98
arm/xlnx-versal-virt
29
- FEAT_CSV2_1p1 (Cache speculation variant 2, version 1.1)
99
30
- FEAT_CSV2_1p2 (Cache speculation variant 2, version 1.2)
100
diff --git a/MAINTAINERS b/MAINTAINERS
31
diff --git a/target/arm/tcg/cpu64.c b/target/arm/tcg/cpu64.c
101
index XXXXXXX..XXXXXXX 100644
32
index XXXXXXX..XXXXXXX 100644
102
--- a/MAINTAINERS
33
--- a/target/arm/tcg/cpu64.c
103
+++ b/MAINTAINERS
34
+++ b/target/arm/tcg/cpu64.c
104
@@ -XXX,XX +XXX,XX @@ M: Alexandre Iooss <erdnaxe@crans.org>
35
@@ -XXX,XX +XXX,XX @@ void aarch64_max_tcg_initfn(Object *obj)
105
L: qemu-arm@nongnu.org
36
t = FIELD_DP64(t, ID_AA64ISAR0, AES, 2); /* FEAT_PMULL */
106
S: Maintained
37
t = FIELD_DP64(t, ID_AA64ISAR0, SHA1, 1); /* FEAT_SHA1 */
107
F: hw/arm/stm32vldiscovery.c
38
t = FIELD_DP64(t, ID_AA64ISAR0, SHA2, 2); /* FEAT_SHA512 */
108
+F: docs/system/arm/stm32.rst
39
- t = FIELD_DP64(t, ID_AA64ISAR0, CRC32, 1);
109
40
+ t = FIELD_DP64(t, ID_AA64ISAR0, CRC32, 1); /* FEAT_CRC32 */
110
Versatile Express
41
t = FIELD_DP64(t, ID_AA64ISAR0, ATOMIC, 2); /* FEAT_LSE */
111
M: Peter Maydell <peter.maydell@linaro.org>
42
t = FIELD_DP64(t, ID_AA64ISAR0, RDM, 1); /* FEAT_RDM */
43
t = FIELD_DP64(t, ID_AA64ISAR0, SHA3, 1); /* FEAT_SHA3 */
112
--
44
--
113
2.20.1
45
2.34.1
114
46
115
47
diff view generated by jsdifflib
New patch
1
From: Jean-Christophe Dubois <jcd@tribudubois.net>
1
2
3
i.MX7 IOMUX GPR device is not equivalent to i.MX6UL IOMUXC GPR device.
4
In particular, register 22 is not present on i.MX6UL and this is actualy
5
The only register that is really emulated in the i.MX7 IOMUX GPR device.
6
7
Note: The i.MX6UL code is actually also implementing the IOMUX GPR device
8
as an unimplemented device at the same bus adress and the 2 instantiations
9
were actualy colliding. So we go back to the unimplemented device for now.
10
11
Signed-off-by: Jean-Christophe Dubois <jcd@tribudubois.net>
12
Message-id: 48681bf51ee97646479bb261bee19abebbc8074e.1692964892.git.jcd@tribudubois.net
13
Reviewed-by: Peter Maydell <peter.maydell@linaro.org>
14
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
15
---
16
include/hw/arm/fsl-imx6ul.h | 2 --
17
hw/arm/fsl-imx6ul.c | 11 -----------
18
2 files changed, 13 deletions(-)
19
20
diff --git a/include/hw/arm/fsl-imx6ul.h b/include/hw/arm/fsl-imx6ul.h
21
index XXXXXXX..XXXXXXX 100644
22
--- a/include/hw/arm/fsl-imx6ul.h
23
+++ b/include/hw/arm/fsl-imx6ul.h
24
@@ -XXX,XX +XXX,XX @@
25
#include "hw/misc/imx6ul_ccm.h"
26
#include "hw/misc/imx6_src.h"
27
#include "hw/misc/imx7_snvs.h"
28
-#include "hw/misc/imx7_gpr.h"
29
#include "hw/intc/imx_gpcv2.h"
30
#include "hw/watchdog/wdt_imx2.h"
31
#include "hw/gpio/imx_gpio.h"
32
@@ -XXX,XX +XXX,XX @@ struct FslIMX6ULState {
33
IMX6SRCState src;
34
IMX7SNVSState snvs;
35
IMXGPCv2State gpcv2;
36
- IMX7GPRState gpr;
37
IMXSPIState spi[FSL_IMX6UL_NUM_ECSPIS];
38
IMXI2CState i2c[FSL_IMX6UL_NUM_I2CS];
39
IMXSerialState uart[FSL_IMX6UL_NUM_UARTS];
40
diff --git a/hw/arm/fsl-imx6ul.c b/hw/arm/fsl-imx6ul.c
41
index XXXXXXX..XXXXXXX 100644
42
--- a/hw/arm/fsl-imx6ul.c
43
+++ b/hw/arm/fsl-imx6ul.c
44
@@ -XXX,XX +XXX,XX @@ static void fsl_imx6ul_init(Object *obj)
45
*/
46
object_initialize_child(obj, "snvs", &s->snvs, TYPE_IMX7_SNVS);
47
48
- /*
49
- * GPR
50
- */
51
- object_initialize_child(obj, "gpr", &s->gpr, TYPE_IMX7_GPR);
52
-
53
/*
54
* GPIOs 1 to 5
55
*/
56
@@ -XXX,XX +XXX,XX @@ static void fsl_imx6ul_realize(DeviceState *dev, Error **errp)
57
FSL_IMX6UL_WDOGn_IRQ[i]));
58
}
59
60
- /*
61
- * GPR
62
- */
63
- sysbus_realize(SYS_BUS_DEVICE(&s->gpr), &error_abort);
64
- sysbus_mmio_map(SYS_BUS_DEVICE(&s->gpr), 0, FSL_IMX6UL_IOMUXC_GPR_ADDR);
65
-
66
/*
67
* SDMA
68
*/
69
--
70
2.34.1
diff view generated by jsdifflib
New patch
1
From: Jean-Christophe Dubois <jcd@tribudubois.net>
1
2
3
* Add Addr and size definition for most i.MX6UL devices in i.MX6UL header file.
4
* Use those newly defined named constants whenever possible.
5
* Standardize the way we init a familly of unimplemented devices
6
- SAI
7
- PWM
8
- CAN
9
* Add/rework few comments
10
11
Signed-off-by: Jean-Christophe Dubois <jcd@tribudubois.net>
12
Message-id: d579043fbd4e4b490370783fda43fc02c8e9be75.1692964892.git.jcd@tribudubois.net
13
Reviewed-by: Peter Maydell <peter.maydell@linaro.org>
14
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
15
---
16
include/hw/arm/fsl-imx6ul.h | 156 +++++++++++++++++++++++++++++++-----
17
hw/arm/fsl-imx6ul.c | 147 ++++++++++++++++++++++-----------
18
2 files changed, 232 insertions(+), 71 deletions(-)
19
20
diff --git a/include/hw/arm/fsl-imx6ul.h b/include/hw/arm/fsl-imx6ul.h
21
index XXXXXXX..XXXXXXX 100644
22
--- a/include/hw/arm/fsl-imx6ul.h
23
+++ b/include/hw/arm/fsl-imx6ul.h
24
@@ -XXX,XX +XXX,XX @@
25
#include "exec/memory.h"
26
#include "cpu.h"
27
#include "qom/object.h"
28
+#include "qemu/units.h"
29
30
#define TYPE_FSL_IMX6UL "fsl-imx6ul"
31
OBJECT_DECLARE_SIMPLE_TYPE(FslIMX6ULState, FSL_IMX6UL)
32
@@ -XXX,XX +XXX,XX @@ enum FslIMX6ULConfiguration {
33
FSL_IMX6UL_NUM_ADCS = 2,
34
FSL_IMX6UL_NUM_USB_PHYS = 2,
35
FSL_IMX6UL_NUM_USBS = 2,
36
+ FSL_IMX6UL_NUM_SAIS = 3,
37
+ FSL_IMX6UL_NUM_CANS = 2,
38
+ FSL_IMX6UL_NUM_PWMS = 4,
39
};
40
41
struct FslIMX6ULState {
42
@@ -XXX,XX +XXX,XX @@ struct FslIMX6ULState {
43
44
enum FslIMX6ULMemoryMap {
45
FSL_IMX6UL_MMDC_ADDR = 0x80000000,
46
- FSL_IMX6UL_MMDC_SIZE = 2 * 1024 * 1024 * 1024UL,
47
+ FSL_IMX6UL_MMDC_SIZE = (2 * GiB),
48
49
FSL_IMX6UL_QSPI1_MEM_ADDR = 0x60000000,
50
- FSL_IMX6UL_EIM_ALIAS_ADDR = 0x58000000,
51
- FSL_IMX6UL_EIM_CS_ADDR = 0x50000000,
52
- FSL_IMX6UL_AES_ENCRYPT_ADDR = 0x10000000,
53
- FSL_IMX6UL_QSPI1_RX_ADDR = 0x0C000000,
54
+ FSL_IMX6UL_QSPI1_MEM_SIZE = (256 * MiB),
55
56
- /* AIPS-2 */
57
+ FSL_IMX6UL_EIM_ALIAS_ADDR = 0x58000000,
58
+ FSL_IMX6UL_EIM_ALIAS_SIZE = (128 * MiB),
59
+
60
+ FSL_IMX6UL_EIM_CS_ADDR = 0x50000000,
61
+ FSL_IMX6UL_EIM_CS_SIZE = (128 * MiB),
62
+
63
+ FSL_IMX6UL_AES_ENCRYPT_ADDR = 0x10000000,
64
+ FSL_IMX6UL_AES_ENCRYPT_SIZE = (1 * MiB),
65
+
66
+ FSL_IMX6UL_QSPI1_RX_ADDR = 0x0C000000,
67
+ FSL_IMX6UL_QSPI1_RX_SIZE = (32 * MiB),
68
+
69
+ /* AIPS-2 Begin */
70
FSL_IMX6UL_UART6_ADDR = 0x021FC000,
71
+
72
FSL_IMX6UL_I2C4_ADDR = 0x021F8000,
73
+
74
FSL_IMX6UL_UART5_ADDR = 0x021F4000,
75
FSL_IMX6UL_UART4_ADDR = 0x021F0000,
76
FSL_IMX6UL_UART3_ADDR = 0x021EC000,
77
FSL_IMX6UL_UART2_ADDR = 0x021E8000,
78
+
79
FSL_IMX6UL_WDOG3_ADDR = 0x021E4000,
80
+
81
FSL_IMX6UL_QSPI_ADDR = 0x021E0000,
82
+ FSL_IMX6UL_QSPI_SIZE = 0x500,
83
+
84
FSL_IMX6UL_SYS_CNT_CTRL_ADDR = 0x021DC000,
85
+ FSL_IMX6UL_SYS_CNT_CTRL_SIZE = (16 * KiB),
86
+
87
FSL_IMX6UL_SYS_CNT_CMP_ADDR = 0x021D8000,
88
+ FSL_IMX6UL_SYS_CNT_CMP_SIZE = (16 * KiB),
89
+
90
FSL_IMX6UL_SYS_CNT_RD_ADDR = 0x021D4000,
91
+ FSL_IMX6UL_SYS_CNT_RD_SIZE = (16 * KiB),
92
+
93
FSL_IMX6UL_TZASC_ADDR = 0x021D0000,
94
+ FSL_IMX6UL_TZASC_SIZE = (16 * KiB),
95
+
96
FSL_IMX6UL_PXP_ADDR = 0x021CC000,
97
+ FSL_IMX6UL_PXP_SIZE = (16 * KiB),
98
+
99
FSL_IMX6UL_LCDIF_ADDR = 0x021C8000,
100
+ FSL_IMX6UL_LCDIF_SIZE = 0x100,
101
+
102
FSL_IMX6UL_CSI_ADDR = 0x021C4000,
103
+ FSL_IMX6UL_CSI_SIZE = 0x100,
104
+
105
FSL_IMX6UL_CSU_ADDR = 0x021C0000,
106
+ FSL_IMX6UL_CSU_SIZE = (16 * KiB),
107
+
108
FSL_IMX6UL_OCOTP_CTRL_ADDR = 0x021BC000,
109
+ FSL_IMX6UL_OCOTP_CTRL_SIZE = (4 * KiB),
110
+
111
FSL_IMX6UL_EIM_ADDR = 0x021B8000,
112
+ FSL_IMX6UL_EIM_SIZE = 0x100,
113
+
114
FSL_IMX6UL_SIM2_ADDR = 0x021B4000,
115
+
116
FSL_IMX6UL_MMDC_CFG_ADDR = 0x021B0000,
117
+ FSL_IMX6UL_MMDC_CFG_SIZE = (4 * KiB),
118
+
119
FSL_IMX6UL_ROMCP_ADDR = 0x021AC000,
120
+ FSL_IMX6UL_ROMCP_SIZE = 0x300,
121
+
122
FSL_IMX6UL_I2C3_ADDR = 0x021A8000,
123
FSL_IMX6UL_I2C2_ADDR = 0x021A4000,
124
FSL_IMX6UL_I2C1_ADDR = 0x021A0000,
125
+
126
FSL_IMX6UL_ADC2_ADDR = 0x0219C000,
127
FSL_IMX6UL_ADC1_ADDR = 0x02198000,
128
+ FSL_IMX6UL_ADCn_SIZE = 0x100,
129
+
130
FSL_IMX6UL_USDHC2_ADDR = 0x02194000,
131
FSL_IMX6UL_USDHC1_ADDR = 0x02190000,
132
- FSL_IMX6UL_SIM1_ADDR = 0x0218C000,
133
- FSL_IMX6UL_ENET1_ADDR = 0x02188000,
134
- FSL_IMX6UL_USBO2_USBMISC_ADDR = 0x02184800,
135
- FSL_IMX6UL_USBO2_USB_ADDR = 0x02184000,
136
- FSL_IMX6UL_USBO2_PL301_ADDR = 0x02180000,
137
- FSL_IMX6UL_AIPS2_CFG_ADDR = 0x0217C000,
138
- FSL_IMX6UL_CAAM_ADDR = 0x02140000,
139
- FSL_IMX6UL_A7MPCORE_DAP_ADDR = 0x02100000,
140
141
- /* AIPS-1 */
142
+ FSL_IMX6UL_SIM1_ADDR = 0x0218C000,
143
+ FSL_IMX6UL_SIMn_SIZE = (16 * KiB),
144
+
145
+ FSL_IMX6UL_ENET1_ADDR = 0x02188000,
146
+
147
+ FSL_IMX6UL_USBO2_USBMISC_ADDR = 0x02184800,
148
+ FSL_IMX6UL_USBO2_USB1_ADDR = 0x02184000,
149
+ FSL_IMX6UL_USBO2_USB2_ADDR = 0x02184200,
150
+
151
+ FSL_IMX6UL_USBO2_PL301_ADDR = 0x02180000,
152
+ FSL_IMX6UL_USBO2_PL301_SIZE = (16 * KiB),
153
+
154
+ FSL_IMX6UL_AIPS2_CFG_ADDR = 0x0217C000,
155
+ FSL_IMX6UL_AIPS2_CFG_SIZE = 0x100,
156
+
157
+ FSL_IMX6UL_CAAM_ADDR = 0x02140000,
158
+ FSL_IMX6UL_CAAM_SIZE = (16 * KiB),
159
+
160
+ FSL_IMX6UL_A7MPCORE_DAP_ADDR = 0x02100000,
161
+ FSL_IMX6UL_A7MPCORE_DAP_SIZE = (4 * KiB),
162
+ /* AIPS-2 End */
163
+
164
+ /* AIPS-1 Begin */
165
FSL_IMX6UL_PWM8_ADDR = 0x020FC000,
166
FSL_IMX6UL_PWM7_ADDR = 0x020F8000,
167
FSL_IMX6UL_PWM6_ADDR = 0x020F4000,
168
FSL_IMX6UL_PWM5_ADDR = 0x020F0000,
169
+
170
FSL_IMX6UL_SDMA_ADDR = 0x020EC000,
171
+ FSL_IMX6UL_SDMA_SIZE = 0x300,
172
+
173
FSL_IMX6UL_GPT2_ADDR = 0x020E8000,
174
+
175
FSL_IMX6UL_IOMUXC_GPR_ADDR = 0x020E4000,
176
+ FSL_IMX6UL_IOMUXC_GPR_SIZE = 0x40,
177
+
178
FSL_IMX6UL_IOMUXC_ADDR = 0x020E0000,
179
+ FSL_IMX6UL_IOMUXC_SIZE = 0x700,
180
+
181
FSL_IMX6UL_GPC_ADDR = 0x020DC000,
182
+
183
FSL_IMX6UL_SRC_ADDR = 0x020D8000,
184
+
185
FSL_IMX6UL_EPIT2_ADDR = 0x020D4000,
186
FSL_IMX6UL_EPIT1_ADDR = 0x020D0000,
187
+
188
FSL_IMX6UL_SNVS_HP_ADDR = 0x020CC000,
189
+
190
FSL_IMX6UL_USBPHY2_ADDR = 0x020CA000,
191
- FSL_IMX6UL_USBPHY2_SIZE = (4 * 1024),
192
FSL_IMX6UL_USBPHY1_ADDR = 0x020C9000,
193
- FSL_IMX6UL_USBPHY1_SIZE = (4 * 1024),
194
+
195
FSL_IMX6UL_ANALOG_ADDR = 0x020C8000,
196
+ FSL_IMX6UL_ANALOG_SIZE = 0x300,
197
+
198
FSL_IMX6UL_CCM_ADDR = 0x020C4000,
199
+
200
FSL_IMX6UL_WDOG2_ADDR = 0x020C0000,
201
FSL_IMX6UL_WDOG1_ADDR = 0x020BC000,
202
+
203
FSL_IMX6UL_KPP_ADDR = 0x020B8000,
204
+ FSL_IMX6UL_KPP_SIZE = 0x10,
205
+
206
FSL_IMX6UL_ENET2_ADDR = 0x020B4000,
207
+
208
FSL_IMX6UL_SNVS_LP_ADDR = 0x020B0000,
209
+ FSL_IMX6UL_SNVS_LP_SIZE = (16 * KiB),
210
+
211
FSL_IMX6UL_GPIO5_ADDR = 0x020AC000,
212
FSL_IMX6UL_GPIO4_ADDR = 0x020A8000,
213
FSL_IMX6UL_GPIO3_ADDR = 0x020A4000,
214
FSL_IMX6UL_GPIO2_ADDR = 0x020A0000,
215
FSL_IMX6UL_GPIO1_ADDR = 0x0209C000,
216
+
217
FSL_IMX6UL_GPT1_ADDR = 0x02098000,
218
+
219
FSL_IMX6UL_CAN2_ADDR = 0x02094000,
220
FSL_IMX6UL_CAN1_ADDR = 0x02090000,
221
+ FSL_IMX6UL_CANn_SIZE = (4 * KiB),
222
+
223
FSL_IMX6UL_PWM4_ADDR = 0x0208C000,
224
FSL_IMX6UL_PWM3_ADDR = 0x02088000,
225
FSL_IMX6UL_PWM2_ADDR = 0x02084000,
226
FSL_IMX6UL_PWM1_ADDR = 0x02080000,
227
+ FSL_IMX6UL_PWMn_SIZE = 0x20,
228
+
229
FSL_IMX6UL_AIPS1_CFG_ADDR = 0x0207C000,
230
+ FSL_IMX6UL_AIPS1_CFG_SIZE = (16 * KiB),
231
+
232
FSL_IMX6UL_BEE_ADDR = 0x02044000,
233
+ FSL_IMX6UL_BEE_SIZE = (16 * KiB),
234
+
235
FSL_IMX6UL_TOUCH_CTRL_ADDR = 0x02040000,
236
+ FSL_IMX6UL_TOUCH_CTRL_SIZE = 0x100,
237
+
238
FSL_IMX6UL_SPBA_ADDR = 0x0203C000,
239
+ FSL_IMX6UL_SPBA_SIZE = 0x100,
240
+
241
FSL_IMX6UL_ASRC_ADDR = 0x02034000,
242
+ FSL_IMX6UL_ASRC_SIZE = 0x100,
243
+
244
FSL_IMX6UL_SAI3_ADDR = 0x02030000,
245
FSL_IMX6UL_SAI2_ADDR = 0x0202C000,
246
FSL_IMX6UL_SAI1_ADDR = 0x02028000,
247
+ FSL_IMX6UL_SAIn_SIZE = 0x200,
248
+
249
FSL_IMX6UL_UART8_ADDR = 0x02024000,
250
FSL_IMX6UL_UART1_ADDR = 0x02020000,
251
FSL_IMX6UL_UART7_ADDR = 0x02018000,
252
+
253
FSL_IMX6UL_ECSPI4_ADDR = 0x02014000,
254
FSL_IMX6UL_ECSPI3_ADDR = 0x02010000,
255
FSL_IMX6UL_ECSPI2_ADDR = 0x0200C000,
256
FSL_IMX6UL_ECSPI1_ADDR = 0x02008000,
257
+
258
FSL_IMX6UL_SPDIF_ADDR = 0x02004000,
259
+ FSL_IMX6UL_SPDIF_SIZE = 0x100,
260
+ /* AIPS-1 End */
261
+
262
+ FSL_IMX6UL_BCH_ADDR = 0x01808000,
263
+ FSL_IMX6UL_BCH_SIZE = 0x200,
264
+
265
+ FSL_IMX6UL_GPMI_ADDR = 0x01806000,
266
+ FSL_IMX6UL_GPMI_SIZE = 0x200,
267
268
FSL_IMX6UL_APBH_DMA_ADDR = 0x01804000,
269
- FSL_IMX6UL_APBH_DMA_SIZE = (32 * 1024),
270
+ FSL_IMX6UL_APBH_DMA_SIZE = (4 * KiB),
271
272
FSL_IMX6UL_A7MPCORE_ADDR = 0x00A00000,
273
274
FSL_IMX6UL_OCRAM_ALIAS_ADDR = 0x00920000,
275
- FSL_IMX6UL_OCRAM_ALIAS_SIZE = 0x00060000,
276
+ FSL_IMX6UL_OCRAM_ALIAS_SIZE = (384 * KiB),
277
+
278
FSL_IMX6UL_OCRAM_MEM_ADDR = 0x00900000,
279
- FSL_IMX6UL_OCRAM_MEM_SIZE = 0x00020000,
280
+ FSL_IMX6UL_OCRAM_MEM_SIZE = (128 * KiB),
281
+
282
FSL_IMX6UL_CAAM_MEM_ADDR = 0x00100000,
283
- FSL_IMX6UL_CAAM_MEM_SIZE = 0x00008000,
284
+ FSL_IMX6UL_CAAM_MEM_SIZE = (32 * KiB),
285
+
286
FSL_IMX6UL_ROM_ADDR = 0x00000000,
287
- FSL_IMX6UL_ROM_SIZE = 0x00018000,
288
+ FSL_IMX6UL_ROM_SIZE = (96 * KiB),
289
};
290
291
enum FslIMX6ULIRQs {
292
diff --git a/hw/arm/fsl-imx6ul.c b/hw/arm/fsl-imx6ul.c
293
index XXXXXXX..XXXXXXX 100644
294
--- a/hw/arm/fsl-imx6ul.c
295
+++ b/hw/arm/fsl-imx6ul.c
296
@@ -XXX,XX +XXX,XX @@ static void fsl_imx6ul_init(Object *obj)
297
object_initialize_child(obj, "snvs", &s->snvs, TYPE_IMX7_SNVS);
298
299
/*
300
- * GPIOs 1 to 5
301
+ * GPIOs
302
*/
303
for (i = 0; i < FSL_IMX6UL_NUM_GPIOS; i++) {
304
snprintf(name, NAME_SIZE, "gpio%d", i);
305
@@ -XXX,XX +XXX,XX @@ static void fsl_imx6ul_init(Object *obj)
306
}
307
308
/*
309
- * GPT 1, 2
310
+ * GPTs
311
*/
312
for (i = 0; i < FSL_IMX6UL_NUM_GPTS; i++) {
313
snprintf(name, NAME_SIZE, "gpt%d", i);
314
@@ -XXX,XX +XXX,XX @@ static void fsl_imx6ul_init(Object *obj)
315
}
316
317
/*
318
- * EPIT 1, 2
319
+ * EPITs
320
*/
321
for (i = 0; i < FSL_IMX6UL_NUM_EPITS; i++) {
322
snprintf(name, NAME_SIZE, "epit%d", i + 1);
323
@@ -XXX,XX +XXX,XX @@ static void fsl_imx6ul_init(Object *obj)
324
}
325
326
/*
327
- * eCSPI
328
+ * eCSPIs
329
*/
330
for (i = 0; i < FSL_IMX6UL_NUM_ECSPIS; i++) {
331
snprintf(name, NAME_SIZE, "spi%d", i + 1);
332
@@ -XXX,XX +XXX,XX @@ static void fsl_imx6ul_init(Object *obj)
333
}
334
335
/*
336
- * I2C
337
+ * I2Cs
338
*/
339
for (i = 0; i < FSL_IMX6UL_NUM_I2CS; i++) {
340
snprintf(name, NAME_SIZE, "i2c%d", i + 1);
341
@@ -XXX,XX +XXX,XX @@ static void fsl_imx6ul_init(Object *obj)
342
}
343
344
/*
345
- * UART
346
+ * UARTs
347
*/
348
for (i = 0; i < FSL_IMX6UL_NUM_UARTS; i++) {
349
snprintf(name, NAME_SIZE, "uart%d", i);
350
@@ -XXX,XX +XXX,XX @@ static void fsl_imx6ul_init(Object *obj)
351
}
352
353
/*
354
- * Ethernet
355
+ * Ethernets
356
*/
357
for (i = 0; i < FSL_IMX6UL_NUM_ETHS; i++) {
358
snprintf(name, NAME_SIZE, "eth%d", i);
359
object_initialize_child(obj, name, &s->eth[i], TYPE_IMX_ENET);
360
}
361
362
- /* USB */
363
+ /*
364
+ * USB PHYs
365
+ */
366
for (i = 0; i < FSL_IMX6UL_NUM_USB_PHYS; i++) {
367
snprintf(name, NAME_SIZE, "usbphy%d", i);
368
object_initialize_child(obj, name, &s->usbphy[i], TYPE_IMX_USBPHY);
369
}
370
+
371
+ /*
372
+ * USBs
373
+ */
374
for (i = 0; i < FSL_IMX6UL_NUM_USBS; i++) {
375
snprintf(name, NAME_SIZE, "usb%d", i);
376
object_initialize_child(obj, name, &s->usb[i], TYPE_CHIPIDEA);
377
}
378
379
/*
380
- * SDHCI
381
+ * SDHCIs
382
*/
383
for (i = 0; i < FSL_IMX6UL_NUM_USDHCS; i++) {
384
snprintf(name, NAME_SIZE, "usdhc%d", i);
385
@@ -XXX,XX +XXX,XX @@ static void fsl_imx6ul_init(Object *obj)
386
}
387
388
/*
389
- * Watchdog
390
+ * Watchdogs
391
*/
392
for (i = 0; i < FSL_IMX6UL_NUM_WDTS; i++) {
393
snprintf(name, NAME_SIZE, "wdt%d", i);
394
@@ -XXX,XX +XXX,XX @@ static void fsl_imx6ul_realize(DeviceState *dev, Error **errp)
395
* A7MPCORE DAP
396
*/
397
create_unimplemented_device("a7mpcore-dap", FSL_IMX6UL_A7MPCORE_DAP_ADDR,
398
- 0x100000);
399
+ FSL_IMX6UL_A7MPCORE_DAP_SIZE);
400
401
/*
402
- * GPT 1, 2
403
+ * GPTs
404
*/
405
for (i = 0; i < FSL_IMX6UL_NUM_GPTS; i++) {
406
static const hwaddr FSL_IMX6UL_GPTn_ADDR[FSL_IMX6UL_NUM_GPTS] = {
407
@@ -XXX,XX +XXX,XX @@ static void fsl_imx6ul_realize(DeviceState *dev, Error **errp)
408
}
409
410
/*
411
- * EPIT 1, 2
412
+ * EPITs
413
*/
414
for (i = 0; i < FSL_IMX6UL_NUM_EPITS; i++) {
415
static const hwaddr FSL_IMX6UL_EPITn_ADDR[FSL_IMX6UL_NUM_EPITS] = {
416
@@ -XXX,XX +XXX,XX @@ static void fsl_imx6ul_realize(DeviceState *dev, Error **errp)
417
}
418
419
/*
420
- * GPIO
421
+ * GPIOs
422
*/
423
for (i = 0; i < FSL_IMX6UL_NUM_GPIOS; i++) {
424
static const hwaddr FSL_IMX6UL_GPIOn_ADDR[FSL_IMX6UL_NUM_GPIOS] = {
425
@@ -XXX,XX +XXX,XX @@ static void fsl_imx6ul_realize(DeviceState *dev, Error **errp)
426
}
427
428
/*
429
- * IOMUXC and IOMUXC_GPR
430
+ * IOMUXC
431
*/
432
- for (i = 0; i < 1; i++) {
433
- static const hwaddr FSL_IMX6UL_IOMUXCn_ADDR[FSL_IMX6UL_NUM_IOMUXCS] = {
434
- FSL_IMX6UL_IOMUXC_ADDR,
435
- FSL_IMX6UL_IOMUXC_GPR_ADDR,
436
- };
437
-
438
- snprintf(name, NAME_SIZE, "iomuxc%d", i);
439
- create_unimplemented_device(name, FSL_IMX6UL_IOMUXCn_ADDR[i], 0x4000);
440
- }
441
+ create_unimplemented_device("iomuxc", FSL_IMX6UL_IOMUXC_ADDR,
442
+ FSL_IMX6UL_IOMUXC_SIZE);
443
+ create_unimplemented_device("iomuxc_gpr", FSL_IMX6UL_IOMUXC_GPR_ADDR,
444
+ FSL_IMX6UL_IOMUXC_GPR_SIZE);
445
446
/*
447
* CCM
448
@@ -XXX,XX +XXX,XX @@ static void fsl_imx6ul_realize(DeviceState *dev, Error **errp)
449
sysbus_realize(SYS_BUS_DEVICE(&s->gpcv2), &error_abort);
450
sysbus_mmio_map(SYS_BUS_DEVICE(&s->gpcv2), 0, FSL_IMX6UL_GPC_ADDR);
451
452
- /* Initialize all ECSPI */
453
+ /*
454
+ * ECSPIs
455
+ */
456
for (i = 0; i < FSL_IMX6UL_NUM_ECSPIS; i++) {
457
static const hwaddr FSL_IMX6UL_SPIn_ADDR[FSL_IMX6UL_NUM_ECSPIS] = {
458
FSL_IMX6UL_ECSPI1_ADDR,
459
@@ -XXX,XX +XXX,XX @@ static void fsl_imx6ul_realize(DeviceState *dev, Error **errp)
460
}
461
462
/*
463
- * I2C
464
+ * I2Cs
465
*/
466
for (i = 0; i < FSL_IMX6UL_NUM_I2CS; i++) {
467
static const hwaddr FSL_IMX6UL_I2Cn_ADDR[FSL_IMX6UL_NUM_I2CS] = {
468
@@ -XXX,XX +XXX,XX @@ static void fsl_imx6ul_realize(DeviceState *dev, Error **errp)
469
}
470
471
/*
472
- * UART
473
+ * UARTs
474
*/
475
for (i = 0; i < FSL_IMX6UL_NUM_UARTS; i++) {
476
static const hwaddr FSL_IMX6UL_UARTn_ADDR[FSL_IMX6UL_NUM_UARTS] = {
477
@@ -XXX,XX +XXX,XX @@ static void fsl_imx6ul_realize(DeviceState *dev, Error **errp)
478
}
479
480
/*
481
- * Ethernet
482
+ * Ethernets
483
*
484
* We must use two loops since phy_connected affects the other interface
485
* and we have to set all properties before calling sysbus_realize().
486
@@ -XXX,XX +XXX,XX @@ static void fsl_imx6ul_realize(DeviceState *dev, Error **errp)
487
FSL_IMX6UL_ENETn_TIMER_IRQ[i]));
488
}
489
490
- /* USB */
491
+ /*
492
+ * USB PHYs
493
+ */
494
for (i = 0; i < FSL_IMX6UL_NUM_USB_PHYS; i++) {
495
+ static const hwaddr
496
+ FSL_IMX6UL_USB_PHYn_ADDR[FSL_IMX6UL_NUM_USB_PHYS] = {
497
+ FSL_IMX6UL_USBPHY1_ADDR,
498
+ FSL_IMX6UL_USBPHY2_ADDR,
499
+ };
500
+
501
sysbus_realize(SYS_BUS_DEVICE(&s->usbphy[i]), &error_abort);
502
sysbus_mmio_map(SYS_BUS_DEVICE(&s->usbphy[i]), 0,
503
- FSL_IMX6UL_USBPHY1_ADDR + i * 0x1000);
504
+ FSL_IMX6UL_USB_PHYn_ADDR[i]);
505
}
506
507
+ /*
508
+ * USBs
509
+ */
510
for (i = 0; i < FSL_IMX6UL_NUM_USBS; i++) {
511
+ static const hwaddr FSL_IMX6UL_USB02_USBn_ADDR[FSL_IMX6UL_NUM_USBS] = {
512
+ FSL_IMX6UL_USBO2_USB1_ADDR,
513
+ FSL_IMX6UL_USBO2_USB2_ADDR,
514
+ };
515
+
516
static const int FSL_IMX6UL_USBn_IRQ[] = {
517
FSL_IMX6UL_USB1_IRQ,
518
FSL_IMX6UL_USB2_IRQ,
519
};
520
+
521
sysbus_realize(SYS_BUS_DEVICE(&s->usb[i]), &error_abort);
522
sysbus_mmio_map(SYS_BUS_DEVICE(&s->usb[i]), 0,
523
- FSL_IMX6UL_USBO2_USB_ADDR + i * 0x200);
524
+ FSL_IMX6UL_USB02_USBn_ADDR[i]);
525
sysbus_connect_irq(SYS_BUS_DEVICE(&s->usb[i]), 0,
526
qdev_get_gpio_in(DEVICE(&s->a7mpcore),
527
FSL_IMX6UL_USBn_IRQ[i]));
528
}
529
530
/*
531
- * USDHC
532
+ * USDHCs
533
*/
534
for (i = 0; i < FSL_IMX6UL_NUM_USDHCS; i++) {
535
static const hwaddr FSL_IMX6UL_USDHCn_ADDR[FSL_IMX6UL_NUM_USDHCS] = {
536
@@ -XXX,XX +XXX,XX @@ static void fsl_imx6ul_realize(DeviceState *dev, Error **errp)
537
sysbus_mmio_map(SYS_BUS_DEVICE(&s->snvs), 0, FSL_IMX6UL_SNVS_HP_ADDR);
538
539
/*
540
- * Watchdog
541
+ * Watchdogs
542
*/
543
for (i = 0; i < FSL_IMX6UL_NUM_WDTS; i++) {
544
static const hwaddr FSL_IMX6UL_WDOGn_ADDR[FSL_IMX6UL_NUM_WDTS] = {
545
@@ -XXX,XX +XXX,XX @@ static void fsl_imx6ul_realize(DeviceState *dev, Error **errp)
546
FSL_IMX6UL_WDOG2_ADDR,
547
FSL_IMX6UL_WDOG3_ADDR,
548
};
549
+
550
static const int FSL_IMX6UL_WDOGn_IRQ[FSL_IMX6UL_NUM_WDTS] = {
551
FSL_IMX6UL_WDOG1_IRQ,
552
FSL_IMX6UL_WDOG2_IRQ,
553
@@ -XXX,XX +XXX,XX @@ static void fsl_imx6ul_realize(DeviceState *dev, Error **errp)
554
/*
555
* SDMA
556
*/
557
- create_unimplemented_device("sdma", FSL_IMX6UL_SDMA_ADDR, 0x4000);
558
+ create_unimplemented_device("sdma", FSL_IMX6UL_SDMA_ADDR,
559
+ FSL_IMX6UL_SDMA_SIZE);
560
561
/*
562
- * SAI (Audio SSI (Synchronous Serial Interface))
563
+ * SAIs (Audio SSI (Synchronous Serial Interface))
564
*/
565
- create_unimplemented_device("sai1", FSL_IMX6UL_SAI1_ADDR, 0x4000);
566
- create_unimplemented_device("sai2", FSL_IMX6UL_SAI2_ADDR, 0x4000);
567
- create_unimplemented_device("sai3", FSL_IMX6UL_SAI3_ADDR, 0x4000);
568
+ for (i = 0; i < FSL_IMX6UL_NUM_SAIS; i++) {
569
+ static const hwaddr FSL_IMX6UL_SAIn_ADDR[FSL_IMX6UL_NUM_SAIS] = {
570
+ FSL_IMX6UL_SAI1_ADDR,
571
+ FSL_IMX6UL_SAI2_ADDR,
572
+ FSL_IMX6UL_SAI3_ADDR,
573
+ };
574
+
575
+ snprintf(name, NAME_SIZE, "sai%d", i);
576
+ create_unimplemented_device(name, FSL_IMX6UL_SAIn_ADDR[i],
577
+ FSL_IMX6UL_SAIn_SIZE);
578
+ }
579
580
/*
581
- * PWM
582
+ * PWMs
583
*/
584
- create_unimplemented_device("pwm1", FSL_IMX6UL_PWM1_ADDR, 0x4000);
585
- create_unimplemented_device("pwm2", FSL_IMX6UL_PWM2_ADDR, 0x4000);
586
- create_unimplemented_device("pwm3", FSL_IMX6UL_PWM3_ADDR, 0x4000);
587
- create_unimplemented_device("pwm4", FSL_IMX6UL_PWM4_ADDR, 0x4000);
588
+ for (i = 0; i < FSL_IMX6UL_NUM_PWMS; i++) {
589
+ static const hwaddr FSL_IMX6UL_PWMn_ADDR[FSL_IMX6UL_NUM_PWMS] = {
590
+ FSL_IMX6UL_PWM1_ADDR,
591
+ FSL_IMX6UL_PWM2_ADDR,
592
+ FSL_IMX6UL_PWM3_ADDR,
593
+ FSL_IMX6UL_PWM4_ADDR,
594
+ };
595
+
596
+ snprintf(name, NAME_SIZE, "pwm%d", i);
597
+ create_unimplemented_device(name, FSL_IMX6UL_PWMn_ADDR[i],
598
+ FSL_IMX6UL_PWMn_SIZE);
599
+ }
600
601
/*
602
* Audio ASRC (asynchronous sample rate converter)
603
*/
604
- create_unimplemented_device("asrc", FSL_IMX6UL_ASRC_ADDR, 0x4000);
605
+ create_unimplemented_device("asrc", FSL_IMX6UL_ASRC_ADDR,
606
+ FSL_IMX6UL_ASRC_SIZE);
607
608
/*
609
- * CAN
610
+ * CANs
611
*/
612
- create_unimplemented_device("can1", FSL_IMX6UL_CAN1_ADDR, 0x4000);
613
- create_unimplemented_device("can2", FSL_IMX6UL_CAN2_ADDR, 0x4000);
614
+ for (i = 0; i < FSL_IMX6UL_NUM_CANS; i++) {
615
+ static const hwaddr FSL_IMX6UL_CANn_ADDR[FSL_IMX6UL_NUM_CANS] = {
616
+ FSL_IMX6UL_CAN1_ADDR,
617
+ FSL_IMX6UL_CAN2_ADDR,
618
+ };
619
+
620
+ snprintf(name, NAME_SIZE, "can%d", i);
621
+ create_unimplemented_device(name, FSL_IMX6UL_CANn_ADDR[i],
622
+ FSL_IMX6UL_CANn_SIZE);
623
+ }
624
625
/*
626
* APHB_DMA
627
@@ -XXX,XX +XXX,XX @@ static void fsl_imx6ul_realize(DeviceState *dev, Error **errp)
628
};
629
630
snprintf(name, NAME_SIZE, "adc%d", i);
631
- create_unimplemented_device(name, FSL_IMX6UL_ADCn_ADDR[i], 0x4000);
632
+ create_unimplemented_device(name, FSL_IMX6UL_ADCn_ADDR[i],
633
+ FSL_IMX6UL_ADCn_SIZE);
634
}
635
636
/*
637
* LCD
638
*/
639
- create_unimplemented_device("lcdif", FSL_IMX6UL_LCDIF_ADDR, 0x4000);
640
+ create_unimplemented_device("lcdif", FSL_IMX6UL_LCDIF_ADDR,
641
+ FSL_IMX6UL_LCDIF_SIZE);
642
643
/*
644
* ROM memory
645
--
646
2.34.1
diff view generated by jsdifflib
1
From: Alexandre Iooss <erdnaxe@crans.org>
1
From: Jean-Christophe Dubois <jcd@tribudubois.net>
2
2
3
New mini-kernel test for STM32VLDISCOVERY USART1.
3
* Add TZASC as unimplemented device.
4
- Allow bare metal application to access this (unimplemented) device
5
* Add CSU as unimplemented device.
6
- Allow bare metal application to access this (unimplemented) device
7
* Add 4 missing PWM devices
4
8
5
Signed-off-by: Alexandre Iooss <erdnaxe@crans.org>
9
Signed-off-by: Jean-Christophe Dubois <jcd@tribudubois.net>
6
Acked-by: Thomas Huth <thuth@redhat.com>
10
Reviewed-by: Philippe Mathieu-Daudé <philmd@linaro.org>
7
Acked-by: Alistair Francis <alistair.francis@wdc.com>
11
Message-id: 59e4dc56e14eccfefd379275ec19048dff9c10b3.1692964892.git.jcd@tribudubois.net
8
Message-id: 20210617165647.2575955-5-erdnaxe@crans.org
9
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
12
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
10
---
13
---
11
tests/qtest/boot-serial-test.c | 37 ++++++++++++++++++++++++++++++++++
14
include/hw/arm/fsl-imx6ul.h | 2 +-
12
1 file changed, 37 insertions(+)
15
hw/arm/fsl-imx6ul.c | 16 ++++++++++++++++
16
2 files changed, 17 insertions(+), 1 deletion(-)
13
17
14
diff --git a/tests/qtest/boot-serial-test.c b/tests/qtest/boot-serial-test.c
18
diff --git a/include/hw/arm/fsl-imx6ul.h b/include/hw/arm/fsl-imx6ul.h
15
index XXXXXXX..XXXXXXX 100644
19
index XXXXXXX..XXXXXXX 100644
16
--- a/tests/qtest/boot-serial-test.c
20
--- a/include/hw/arm/fsl-imx6ul.h
17
+++ b/tests/qtest/boot-serial-test.c
21
+++ b/include/hw/arm/fsl-imx6ul.h
18
@@ -XXX,XX +XXX,XX @@ static const uint8_t kernel_nrf51[] = {
22
@@ -XXX,XX +XXX,XX @@ enum FslIMX6ULConfiguration {
19
0x1c, 0x25, 0x00, 0x40 /* 0x4000251c = UART TXD */
23
FSL_IMX6UL_NUM_USBS = 2,
24
FSL_IMX6UL_NUM_SAIS = 3,
25
FSL_IMX6UL_NUM_CANS = 2,
26
- FSL_IMX6UL_NUM_PWMS = 4,
27
+ FSL_IMX6UL_NUM_PWMS = 8,
20
};
28
};
21
29
22
+static const uint8_t kernel_stm32vldiscovery[] = {
30
struct FslIMX6ULState {
23
+ 0x00, 0x00, 0x00, 0x00, /* Stack top address */
31
diff --git a/hw/arm/fsl-imx6ul.c b/hw/arm/fsl-imx6ul.c
24
+ 0x1d, 0x00, 0x00, 0x00, /* Reset handler address */
32
index XXXXXXX..XXXXXXX 100644
25
+ 0x00, 0x00, 0x00, 0x00, /* NMI */
33
--- a/hw/arm/fsl-imx6ul.c
26
+ 0x00, 0x00, 0x00, 0x00, /* Hard fault */
34
+++ b/hw/arm/fsl-imx6ul.c
27
+ 0x00, 0x00, 0x00, 0x00, /* Memory management fault */
35
@@ -XXX,XX +XXX,XX @@ static void fsl_imx6ul_realize(DeviceState *dev, Error **errp)
28
+ 0x00, 0x00, 0x00, 0x00, /* Bus fault */
36
FSL_IMX6UL_PWM2_ADDR,
29
+ 0x00, 0x00, 0x00, 0x00, /* Usage fault */
37
FSL_IMX6UL_PWM3_ADDR,
30
+ 0x0b, 0x4b, /* ldr r3, [pc, #44] Get RCC */
38
FSL_IMX6UL_PWM4_ADDR,
31
+ 0x44, 0xf2, 0x04, 0x02, /* movw r2, #16388 */
39
+ FSL_IMX6UL_PWM5_ADDR,
32
+ 0x1a, 0x60, /* str r2, [r3] */
40
+ FSL_IMX6UL_PWM6_ADDR,
33
+ 0x0a, 0x4b, /* ldr r3, [pc, #40] Get GPIOA */
41
+ FSL_IMX6UL_PWM7_ADDR,
34
+ 0x1a, 0x68, /* ldr r2, [r3] */
42
+ FSL_IMX6UL_PWM8_ADDR,
35
+ 0x22, 0xf0, 0xf0, 0x02, /* bic r2, r2, #240 */
43
};
36
+ 0x1a, 0x60, /* str r2, [r3] */
44
37
+ 0x1a, 0x68, /* ldr r2, [r3] */
45
snprintf(name, NAME_SIZE, "pwm%d", i);
38
+ 0x42, 0xf0, 0xb0, 0x02, /* orr r2, r2, #176 */
46
@@ -XXX,XX +XXX,XX @@ static void fsl_imx6ul_realize(DeviceState *dev, Error **errp)
39
+ 0x1a, 0x60, /* str r2, [r3] */
47
create_unimplemented_device("lcdif", FSL_IMX6UL_LCDIF_ADDR,
40
+ 0x07, 0x4b, /* ldr r3, [pc, #26] Get BAUD */
48
FSL_IMX6UL_LCDIF_SIZE);
41
+ 0x45, 0x22, /* movs r2, #69 */
49
42
+ 0x1a, 0x60, /* str r2, [r3] */
50
+ /*
43
+ 0x06, 0x4b, /* ldr r3, [pc, #24] Get ENABLE */
51
+ * CSU
44
+ 0x42, 0xf2, 0x08, 0x02, /* movw r2, #8200 */
52
+ */
45
+ 0x1a, 0x60, /* str r2, [r3] */
53
+ create_unimplemented_device("csu", FSL_IMX6UL_CSU_ADDR,
46
+ 0x05, 0x4b, /* ldr r3, [pc, #20] Get TXD */
54
+ FSL_IMX6UL_CSU_SIZE);
47
+ 0x54, 0x22, /* movs r2, 'T' */
48
+ 0x1a, 0x60, /* str r2, [r3] */
49
+ 0xfe, 0xe7, /* b . */
50
+ 0x18, 0x10, 0x02, 0x40, /* 0x40021018 = RCC */
51
+ 0x04, 0x08, 0x01, 0x40, /* 0x40010804 = GPIOA */
52
+ 0x08, 0x38, 0x01, 0x40, /* 0x40013808 = USART1 BAUD */
53
+ 0x0c, 0x38, 0x01, 0x40, /* 0x4001380c = USART1 ENABLE */
54
+ 0x04, 0x38, 0x01, 0x40 /* 0x40013804 = USART1 TXD */
55
+};
56
+
55
+
57
typedef struct testdef {
56
+ /*
58
const char *arch; /* Target architecture */
57
+ * TZASC
59
const char *machine; /* Name of the machine */
58
+ */
60
@@ -XXX,XX +XXX,XX @@ static testdef_t tests[] = {
59
+ create_unimplemented_device("tzasc", FSL_IMX6UL_TZASC_ADDR,
61
{ "aarch64", "virt", "-cpu max", "TT", sizeof(kernel_aarch64),
60
+ FSL_IMX6UL_TZASC_SIZE);
62
kernel_aarch64 },
61
+
63
{ "arm", "microbit", "", "T", sizeof(kernel_nrf51), kernel_nrf51 },
62
/*
64
+ { "arm", "stm32vldiscovery", "", "T",
63
* ROM memory
65
+ sizeof(kernel_stm32vldiscovery), kernel_stm32vldiscovery },
64
*/
66
67
{ NULL }
68
};
69
--
65
--
70
2.20.1
66
2.34.1
71
67
72
68
diff view generated by jsdifflib
1
From: Ricardo Koller <ricarkol@google.com>
1
From: Jean-Christophe Dubois <jcd@tribudubois.net>
2
2
3
icv_eoir_write() and icv_dir_write() ignore invalid virtual IRQ numbers
3
* Add Addr and size definition for all i.MX7 devices in i.MX7 header file.
4
(like LPIs). The issue is that these functions check against the number
4
* Use those newly defined named constants whenever possible.
5
of implemented IRQs (QEMU's default is num_irq=288) which can be lower
5
* Standardize the way we init a familly of unimplemented devices
6
than the maximum virtual IRQ number (1020 - 1). The consequence is that
6
- SAI
7
if a hypervisor creates an LR for an IRQ between 288 and 1020, then the
7
- PWM
8
guest is unable to deactivate the resulting IRQ. Note that other
8
- CAN
9
functions that deal with large IRQ numbers, like icv_iar_read, check
9
* Add/rework few comments
10
against 1020 and not against num_irq.
11
10
12
Fix the checks by using GICV3_MAXIRQ (1020) instead of the number of
11
Signed-off-by: Jean-Christophe Dubois <jcd@tribudubois.net>
13
implemented IRQs.
12
Message-id: 59e195d33e4d486a8d131392acd46633c8c10ed7.1692964892.git.jcd@tribudubois.net
14
15
Signed-off-by: Ricardo Koller <ricarkol@google.com>
16
Message-id: 20210702233701.3369-1-ricarkol@google.com
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
hw/intc/arm_gicv3_cpuif.c | 4 ++--
16
include/hw/arm/fsl-imx7.h | 330 ++++++++++++++++++++++++++++----------
21
1 file changed, 2 insertions(+), 2 deletions(-)
17
hw/arm/fsl-imx7.c | 130 ++++++++++-----
18
2 files changed, 335 insertions(+), 125 deletions(-)
22
19
23
diff --git a/hw/intc/arm_gicv3_cpuif.c b/hw/intc/arm_gicv3_cpuif.c
20
diff --git a/include/hw/arm/fsl-imx7.h b/include/hw/arm/fsl-imx7.h
24
index XXXXXXX..XXXXXXX 100644
21
index XXXXXXX..XXXXXXX 100644
25
--- a/hw/intc/arm_gicv3_cpuif.c
22
--- a/include/hw/arm/fsl-imx7.h
26
+++ b/hw/intc/arm_gicv3_cpuif.c
23
+++ b/include/hw/arm/fsl-imx7.h
27
@@ -XXX,XX +XXX,XX @@ static void icv_dir_write(CPUARMState *env, const ARMCPRegInfo *ri,
24
@@ -XXX,XX +XXX,XX @@
28
25
#include "hw/misc/imx7_ccm.h"
29
trace_gicv3_icv_dir_write(gicv3_redist_affid(cs), value);
26
#include "hw/misc/imx7_snvs.h"
30
27
#include "hw/misc/imx7_gpr.h"
31
- if (irq >= cs->gic->num_irq) {
28
-#include "hw/misc/imx6_src.h"
32
+ if (irq >= GICV3_MAXIRQ) {
29
#include "hw/watchdog/wdt_imx2.h"
33
/* Also catches special interrupt numbers and LPIs */
30
#include "hw/gpio/imx_gpio.h"
31
#include "hw/char/imx_serial.h"
32
@@ -XXX,XX +XXX,XX @@
33
#include "hw/usb/chipidea.h"
34
#include "cpu.h"
35
#include "qom/object.h"
36
+#include "qemu/units.h"
37
38
#define TYPE_FSL_IMX7 "fsl-imx7"
39
OBJECT_DECLARE_SIMPLE_TYPE(FslIMX7State, FSL_IMX7)
40
@@ -XXX,XX +XXX,XX @@ enum FslIMX7Configuration {
41
FSL_IMX7_NUM_ECSPIS = 4,
42
FSL_IMX7_NUM_USBS = 3,
43
FSL_IMX7_NUM_ADCS = 2,
44
+ FSL_IMX7_NUM_SAIS = 3,
45
+ FSL_IMX7_NUM_CANS = 2,
46
+ FSL_IMX7_NUM_PWMS = 4,
47
};
48
49
struct FslIMX7State {
50
@@ -XXX,XX +XXX,XX @@ struct FslIMX7State {
51
52
enum FslIMX7MemoryMap {
53
FSL_IMX7_MMDC_ADDR = 0x80000000,
54
- FSL_IMX7_MMDC_SIZE = 2 * 1024 * 1024 * 1024UL,
55
+ FSL_IMX7_MMDC_SIZE = (2 * GiB),
56
57
- FSL_IMX7_GPIO1_ADDR = 0x30200000,
58
- FSL_IMX7_GPIO2_ADDR = 0x30210000,
59
- FSL_IMX7_GPIO3_ADDR = 0x30220000,
60
- FSL_IMX7_GPIO4_ADDR = 0x30230000,
61
- FSL_IMX7_GPIO5_ADDR = 0x30240000,
62
- FSL_IMX7_GPIO6_ADDR = 0x30250000,
63
- FSL_IMX7_GPIO7_ADDR = 0x30260000,
64
+ FSL_IMX7_QSPI1_MEM_ADDR = 0x60000000,
65
+ FSL_IMX7_QSPI1_MEM_SIZE = (256 * MiB),
66
67
- FSL_IMX7_IOMUXC_LPSR_GPR_ADDR = 0x30270000,
68
+ FSL_IMX7_PCIE1_MEM_ADDR = 0x40000000,
69
+ FSL_IMX7_PCIE1_MEM_SIZE = (256 * MiB),
70
71
- FSL_IMX7_WDOG1_ADDR = 0x30280000,
72
- FSL_IMX7_WDOG2_ADDR = 0x30290000,
73
- FSL_IMX7_WDOG3_ADDR = 0x302A0000,
74
- FSL_IMX7_WDOG4_ADDR = 0x302B0000,
75
+ FSL_IMX7_QSPI1_RX_BUF_ADDR = 0x34000000,
76
+ FSL_IMX7_QSPI1_RX_BUF_SIZE = (32 * MiB),
77
78
- FSL_IMX7_IOMUXC_LPSR_ADDR = 0x302C0000,
79
+ /* PCIe Peripherals */
80
+ FSL_IMX7_PCIE_REG_ADDR = 0x33800000,
81
82
- FSL_IMX7_GPT1_ADDR = 0x302D0000,
83
- FSL_IMX7_GPT2_ADDR = 0x302E0000,
84
- FSL_IMX7_GPT3_ADDR = 0x302F0000,
85
- FSL_IMX7_GPT4_ADDR = 0x30300000,
86
+ /* MMAP Peripherals */
87
+ FSL_IMX7_DMA_APBH_ADDR = 0x33000000,
88
+ FSL_IMX7_DMA_APBH_SIZE = 0x8000,
89
90
- FSL_IMX7_IOMUXC_ADDR = 0x30330000,
91
- FSL_IMX7_IOMUXC_GPR_ADDR = 0x30340000,
92
- FSL_IMX7_IOMUXCn_SIZE = 0x1000,
93
+ /* GPV configuration */
94
+ FSL_IMX7_GPV6_ADDR = 0x32600000,
95
+ FSL_IMX7_GPV5_ADDR = 0x32500000,
96
+ FSL_IMX7_GPV4_ADDR = 0x32400000,
97
+ FSL_IMX7_GPV3_ADDR = 0x32300000,
98
+ FSL_IMX7_GPV2_ADDR = 0x32200000,
99
+ FSL_IMX7_GPV1_ADDR = 0x32100000,
100
+ FSL_IMX7_GPV0_ADDR = 0x32000000,
101
+ FSL_IMX7_GPVn_SIZE = (1 * MiB),
102
103
- FSL_IMX7_OCOTP_ADDR = 0x30350000,
104
- FSL_IMX7_OCOTP_SIZE = 0x10000,
105
+ /* Arm Peripherals */
106
+ FSL_IMX7_A7MPCORE_ADDR = 0x31000000,
107
108
- FSL_IMX7_ANALOG_ADDR = 0x30360000,
109
- FSL_IMX7_SNVS_ADDR = 0x30370000,
110
- FSL_IMX7_CCM_ADDR = 0x30380000,
111
+ /* AIPS-3 Begin */
112
113
- FSL_IMX7_SRC_ADDR = 0x30390000,
114
- FSL_IMX7_SRC_SIZE = 0x1000,
115
+ FSL_IMX7_ENET2_ADDR = 0x30BF0000,
116
+ FSL_IMX7_ENET1_ADDR = 0x30BE0000,
117
118
- FSL_IMX7_ADC1_ADDR = 0x30610000,
119
- FSL_IMX7_ADC2_ADDR = 0x30620000,
120
- FSL_IMX7_ADCn_SIZE = 0x1000,
121
+ FSL_IMX7_SDMA_ADDR = 0x30BD0000,
122
+ FSL_IMX7_SDMA_SIZE = (4 * KiB),
123
124
- FSL_IMX7_PWM1_ADDR = 0x30660000,
125
- FSL_IMX7_PWM2_ADDR = 0x30670000,
126
- FSL_IMX7_PWM3_ADDR = 0x30680000,
127
- FSL_IMX7_PWM4_ADDR = 0x30690000,
128
- FSL_IMX7_PWMn_SIZE = 0x10000,
129
+ FSL_IMX7_EIM_ADDR = 0x30BC0000,
130
+ FSL_IMX7_EIM_SIZE = (4 * KiB),
131
132
- FSL_IMX7_PCIE_PHY_ADDR = 0x306D0000,
133
- FSL_IMX7_PCIE_PHY_SIZE = 0x10000,
134
+ FSL_IMX7_QSPI_ADDR = 0x30BB0000,
135
+ FSL_IMX7_QSPI_SIZE = 0x8000,
136
137
- FSL_IMX7_GPC_ADDR = 0x303A0000,
138
+ FSL_IMX7_SIM2_ADDR = 0x30BA0000,
139
+ FSL_IMX7_SIM1_ADDR = 0x30B90000,
140
+ FSL_IMX7_SIMn_SIZE = (4 * KiB),
141
+
142
+ FSL_IMX7_USDHC3_ADDR = 0x30B60000,
143
+ FSL_IMX7_USDHC2_ADDR = 0x30B50000,
144
+ FSL_IMX7_USDHC1_ADDR = 0x30B40000,
145
+
146
+ FSL_IMX7_USB3_ADDR = 0x30B30000,
147
+ FSL_IMX7_USBMISC3_ADDR = 0x30B30200,
148
+ FSL_IMX7_USB2_ADDR = 0x30B20000,
149
+ FSL_IMX7_USBMISC2_ADDR = 0x30B20200,
150
+ FSL_IMX7_USB1_ADDR = 0x30B10000,
151
+ FSL_IMX7_USBMISC1_ADDR = 0x30B10200,
152
+ FSL_IMX7_USBMISCn_SIZE = 0x200,
153
+
154
+ FSL_IMX7_USB_PL301_ADDR = 0x30AD0000,
155
+ FSL_IMX7_USB_PL301_SIZE = (64 * KiB),
156
+
157
+ FSL_IMX7_SEMAPHORE_HS_ADDR = 0x30AC0000,
158
+ FSL_IMX7_SEMAPHORE_HS_SIZE = (64 * KiB),
159
+
160
+ FSL_IMX7_MUB_ADDR = 0x30AB0000,
161
+ FSL_IMX7_MUA_ADDR = 0x30AA0000,
162
+ FSL_IMX7_MUn_SIZE = (KiB),
163
+
164
+ FSL_IMX7_UART7_ADDR = 0x30A90000,
165
+ FSL_IMX7_UART6_ADDR = 0x30A80000,
166
+ FSL_IMX7_UART5_ADDR = 0x30A70000,
167
+ FSL_IMX7_UART4_ADDR = 0x30A60000,
168
+
169
+ FSL_IMX7_I2C4_ADDR = 0x30A50000,
170
+ FSL_IMX7_I2C3_ADDR = 0x30A40000,
171
+ FSL_IMX7_I2C2_ADDR = 0x30A30000,
172
+ FSL_IMX7_I2C1_ADDR = 0x30A20000,
173
+
174
+ FSL_IMX7_CAN2_ADDR = 0x30A10000,
175
+ FSL_IMX7_CAN1_ADDR = 0x30A00000,
176
+ FSL_IMX7_CANn_SIZE = (4 * KiB),
177
+
178
+ FSL_IMX7_AIPS3_CONF_ADDR = 0x309F0000,
179
+ FSL_IMX7_AIPS3_CONF_SIZE = (64 * KiB),
180
181
FSL_IMX7_CAAM_ADDR = 0x30900000,
182
- FSL_IMX7_CAAM_SIZE = 0x40000,
183
+ FSL_IMX7_CAAM_SIZE = (256 * KiB),
184
185
- FSL_IMX7_CAN1_ADDR = 0x30A00000,
186
- FSL_IMX7_CAN2_ADDR = 0x30A10000,
187
- FSL_IMX7_CANn_SIZE = 0x10000,
188
+ FSL_IMX7_SPBA_ADDR = 0x308F0000,
189
+ FSL_IMX7_SPBA_SIZE = (4 * KiB),
190
191
- FSL_IMX7_I2C1_ADDR = 0x30A20000,
192
- FSL_IMX7_I2C2_ADDR = 0x30A30000,
193
- FSL_IMX7_I2C3_ADDR = 0x30A40000,
194
- FSL_IMX7_I2C4_ADDR = 0x30A50000,
195
+ FSL_IMX7_SAI3_ADDR = 0x308C0000,
196
+ FSL_IMX7_SAI2_ADDR = 0x308B0000,
197
+ FSL_IMX7_SAI1_ADDR = 0x308A0000,
198
+ FSL_IMX7_SAIn_SIZE = (4 * KiB),
199
200
- FSL_IMX7_ECSPI1_ADDR = 0x30820000,
201
- FSL_IMX7_ECSPI2_ADDR = 0x30830000,
202
- FSL_IMX7_ECSPI3_ADDR = 0x30840000,
203
- FSL_IMX7_ECSPI4_ADDR = 0x30630000,
204
-
205
- FSL_IMX7_LCDIF_ADDR = 0x30730000,
206
- FSL_IMX7_LCDIF_SIZE = 0x1000,
207
-
208
- FSL_IMX7_UART1_ADDR = 0x30860000,
209
+ FSL_IMX7_UART3_ADDR = 0x30880000,
210
/*
211
* Some versions of the reference manual claim that UART2 is @
212
* 0x30870000, but experiments with HW + DT files in upstream
213
@@ -XXX,XX +XXX,XX @@ enum FslIMX7MemoryMap {
214
* actually located @ 0x30890000
215
*/
216
FSL_IMX7_UART2_ADDR = 0x30890000,
217
- FSL_IMX7_UART3_ADDR = 0x30880000,
218
- FSL_IMX7_UART4_ADDR = 0x30A60000,
219
- FSL_IMX7_UART5_ADDR = 0x30A70000,
220
- FSL_IMX7_UART6_ADDR = 0x30A80000,
221
- FSL_IMX7_UART7_ADDR = 0x30A90000,
222
+ FSL_IMX7_UART1_ADDR = 0x30860000,
223
224
- FSL_IMX7_SAI1_ADDR = 0x308A0000,
225
- FSL_IMX7_SAI2_ADDR = 0x308B0000,
226
- FSL_IMX7_SAI3_ADDR = 0x308C0000,
227
- FSL_IMX7_SAIn_SIZE = 0x10000,
228
+ FSL_IMX7_ECSPI3_ADDR = 0x30840000,
229
+ FSL_IMX7_ECSPI2_ADDR = 0x30830000,
230
+ FSL_IMX7_ECSPI1_ADDR = 0x30820000,
231
+ FSL_IMX7_ECSPIn_SIZE = (4 * KiB),
232
233
- FSL_IMX7_ENET1_ADDR = 0x30BE0000,
234
- FSL_IMX7_ENET2_ADDR = 0x30BF0000,
235
+ /* AIPS-3 End */
236
237
- FSL_IMX7_USB1_ADDR = 0x30B10000,
238
- FSL_IMX7_USBMISC1_ADDR = 0x30B10200,
239
- FSL_IMX7_USB2_ADDR = 0x30B20000,
240
- FSL_IMX7_USBMISC2_ADDR = 0x30B20200,
241
- FSL_IMX7_USB3_ADDR = 0x30B30000,
242
- FSL_IMX7_USBMISC3_ADDR = 0x30B30200,
243
- FSL_IMX7_USBMISCn_SIZE = 0x200,
244
+ /* AIPS-2 Begin */
245
246
- FSL_IMX7_USDHC1_ADDR = 0x30B40000,
247
- FSL_IMX7_USDHC2_ADDR = 0x30B50000,
248
- FSL_IMX7_USDHC3_ADDR = 0x30B60000,
249
+ FSL_IMX7_AXI_DEBUG_MON_ADDR = 0x307E0000,
250
+ FSL_IMX7_AXI_DEBUG_MON_SIZE = (64 * KiB),
251
252
- FSL_IMX7_SDMA_ADDR = 0x30BD0000,
253
- FSL_IMX7_SDMA_SIZE = 0x1000,
254
+ FSL_IMX7_PERFMON2_ADDR = 0x307D0000,
255
+ FSL_IMX7_PERFMON1_ADDR = 0x307C0000,
256
+ FSL_IMX7_PERFMONn_SIZE = (64 * KiB),
257
+
258
+ FSL_IMX7_DDRC_ADDR = 0x307A0000,
259
+ FSL_IMX7_DDRC_SIZE = (4 * KiB),
260
+
261
+ FSL_IMX7_DDRC_PHY_ADDR = 0x30790000,
262
+ FSL_IMX7_DDRC_PHY_SIZE = (4 * KiB),
263
+
264
+ FSL_IMX7_TZASC_ADDR = 0x30780000,
265
+ FSL_IMX7_TZASC_SIZE = (64 * KiB),
266
+
267
+ FSL_IMX7_MIPI_DSI_ADDR = 0x30760000,
268
+ FSL_IMX7_MIPI_DSI_SIZE = (4 * KiB),
269
+
270
+ FSL_IMX7_MIPI_CSI_ADDR = 0x30750000,
271
+ FSL_IMX7_MIPI_CSI_SIZE = 0x4000,
272
+
273
+ FSL_IMX7_LCDIF_ADDR = 0x30730000,
274
+ FSL_IMX7_LCDIF_SIZE = 0x8000,
275
+
276
+ FSL_IMX7_CSI_ADDR = 0x30710000,
277
+ FSL_IMX7_CSI_SIZE = (4 * KiB),
278
+
279
+ FSL_IMX7_PXP_ADDR = 0x30700000,
280
+ FSL_IMX7_PXP_SIZE = 0x4000,
281
+
282
+ FSL_IMX7_EPDC_ADDR = 0x306F0000,
283
+ FSL_IMX7_EPDC_SIZE = (4 * KiB),
284
+
285
+ FSL_IMX7_PCIE_PHY_ADDR = 0x306D0000,
286
+ FSL_IMX7_PCIE_PHY_SIZE = (4 * KiB),
287
+
288
+ FSL_IMX7_SYSCNT_CTRL_ADDR = 0x306C0000,
289
+ FSL_IMX7_SYSCNT_CMP_ADDR = 0x306B0000,
290
+ FSL_IMX7_SYSCNT_RD_ADDR = 0x306A0000,
291
+
292
+ FSL_IMX7_PWM4_ADDR = 0x30690000,
293
+ FSL_IMX7_PWM3_ADDR = 0x30680000,
294
+ FSL_IMX7_PWM2_ADDR = 0x30670000,
295
+ FSL_IMX7_PWM1_ADDR = 0x30660000,
296
+ FSL_IMX7_PWMn_SIZE = (4 * KiB),
297
+
298
+ FSL_IMX7_FlEXTIMER2_ADDR = 0x30650000,
299
+ FSL_IMX7_FlEXTIMER1_ADDR = 0x30640000,
300
+ FSL_IMX7_FLEXTIMERn_SIZE = (4 * KiB),
301
+
302
+ FSL_IMX7_ECSPI4_ADDR = 0x30630000,
303
+
304
+ FSL_IMX7_ADC2_ADDR = 0x30620000,
305
+ FSL_IMX7_ADC1_ADDR = 0x30610000,
306
+ FSL_IMX7_ADCn_SIZE = (4 * KiB),
307
+
308
+ FSL_IMX7_AIPS2_CONF_ADDR = 0x305F0000,
309
+ FSL_IMX7_AIPS2_CONF_SIZE = (64 * KiB),
310
+
311
+ /* AIPS-2 End */
312
+
313
+ /* AIPS-1 Begin */
314
+
315
+ FSL_IMX7_CSU_ADDR = 0x303E0000,
316
+ FSL_IMX7_CSU_SIZE = (64 * KiB),
317
+
318
+ FSL_IMX7_RDC_ADDR = 0x303D0000,
319
+ FSL_IMX7_RDC_SIZE = (4 * KiB),
320
+
321
+ FSL_IMX7_SEMAPHORE2_ADDR = 0x303C0000,
322
+ FSL_IMX7_SEMAPHORE1_ADDR = 0x303B0000,
323
+ FSL_IMX7_SEMAPHOREn_SIZE = (4 * KiB),
324
+
325
+ FSL_IMX7_GPC_ADDR = 0x303A0000,
326
+
327
+ FSL_IMX7_SRC_ADDR = 0x30390000,
328
+ FSL_IMX7_SRC_SIZE = (4 * KiB),
329
+
330
+ FSL_IMX7_CCM_ADDR = 0x30380000,
331
+
332
+ FSL_IMX7_SNVS_HP_ADDR = 0x30370000,
333
+
334
+ FSL_IMX7_ANALOG_ADDR = 0x30360000,
335
+
336
+ FSL_IMX7_OCOTP_ADDR = 0x30350000,
337
+ FSL_IMX7_OCOTP_SIZE = 0x10000,
338
+
339
+ FSL_IMX7_IOMUXC_GPR_ADDR = 0x30340000,
340
+ FSL_IMX7_IOMUXC_GPR_SIZE = (4 * KiB),
341
+
342
+ FSL_IMX7_IOMUXC_ADDR = 0x30330000,
343
+ FSL_IMX7_IOMUXC_SIZE = (4 * KiB),
344
+
345
+ FSL_IMX7_KPP_ADDR = 0x30320000,
346
+ FSL_IMX7_KPP_SIZE = (4 * KiB),
347
+
348
+ FSL_IMX7_ROMCP_ADDR = 0x30310000,
349
+ FSL_IMX7_ROMCP_SIZE = (4 * KiB),
350
+
351
+ FSL_IMX7_GPT4_ADDR = 0x30300000,
352
+ FSL_IMX7_GPT3_ADDR = 0x302F0000,
353
+ FSL_IMX7_GPT2_ADDR = 0x302E0000,
354
+ FSL_IMX7_GPT1_ADDR = 0x302D0000,
355
+
356
+ FSL_IMX7_IOMUXC_LPSR_ADDR = 0x302C0000,
357
+ FSL_IMX7_IOMUXC_LPSR_SIZE = (4 * KiB),
358
+
359
+ FSL_IMX7_WDOG4_ADDR = 0x302B0000,
360
+ FSL_IMX7_WDOG3_ADDR = 0x302A0000,
361
+ FSL_IMX7_WDOG2_ADDR = 0x30290000,
362
+ FSL_IMX7_WDOG1_ADDR = 0x30280000,
363
+
364
+ FSL_IMX7_IOMUXC_LPSR_GPR_ADDR = 0x30270000,
365
+
366
+ FSL_IMX7_GPIO7_ADDR = 0x30260000,
367
+ FSL_IMX7_GPIO6_ADDR = 0x30250000,
368
+ FSL_IMX7_GPIO5_ADDR = 0x30240000,
369
+ FSL_IMX7_GPIO4_ADDR = 0x30230000,
370
+ FSL_IMX7_GPIO3_ADDR = 0x30220000,
371
+ FSL_IMX7_GPIO2_ADDR = 0x30210000,
372
+ FSL_IMX7_GPIO1_ADDR = 0x30200000,
373
+
374
+ FSL_IMX7_AIPS1_CONF_ADDR = 0x301F0000,
375
+ FSL_IMX7_AIPS1_CONF_SIZE = (64 * KiB),
376
377
- FSL_IMX7_A7MPCORE_ADDR = 0x31000000,
378
FSL_IMX7_A7MPCORE_DAP_ADDR = 0x30000000,
379
+ FSL_IMX7_A7MPCORE_DAP_SIZE = (1 * MiB),
380
381
- FSL_IMX7_PCIE_REG_ADDR = 0x33800000,
382
- FSL_IMX7_PCIE_REG_SIZE = 16 * 1024,
383
+ /* AIPS-1 End */
384
385
- FSL_IMX7_GPR_ADDR = 0x30340000,
386
+ FSL_IMX7_EIM_CS0_ADDR = 0x28000000,
387
+ FSL_IMX7_EIM_CS0_SIZE = (128 * MiB),
388
389
- FSL_IMX7_DMA_APBH_ADDR = 0x33000000,
390
- FSL_IMX7_DMA_APBH_SIZE = 0x2000,
391
+ FSL_IMX7_OCRAM_PXP_ADDR = 0x00940000,
392
+ FSL_IMX7_OCRAM_PXP_SIZE = (32 * KiB),
393
+
394
+ FSL_IMX7_OCRAM_EPDC_ADDR = 0x00920000,
395
+ FSL_IMX7_OCRAM_EPDC_SIZE = (128 * KiB),
396
+
397
+ FSL_IMX7_OCRAM_MEM_ADDR = 0x00900000,
398
+ FSL_IMX7_OCRAM_MEM_SIZE = (128 * KiB),
399
+
400
+ FSL_IMX7_TCMU_ADDR = 0x00800000,
401
+ FSL_IMX7_TCMU_SIZE = (32 * KiB),
402
+
403
+ FSL_IMX7_TCML_ADDR = 0x007F8000,
404
+ FSL_IMX7_TCML_SIZE = (32 * KiB),
405
+
406
+ FSL_IMX7_OCRAM_S_ADDR = 0x00180000,
407
+ FSL_IMX7_OCRAM_S_SIZE = (32 * KiB),
408
+
409
+ FSL_IMX7_CAAM_MEM_ADDR = 0x00100000,
410
+ FSL_IMX7_CAAM_MEM_SIZE = (32 * KiB),
411
+
412
+ FSL_IMX7_ROM_ADDR = 0x00000000,
413
+ FSL_IMX7_ROM_SIZE = (96 * KiB),
414
};
415
416
enum FslIMX7IRQs {
417
diff --git a/hw/arm/fsl-imx7.c b/hw/arm/fsl-imx7.c
418
index XXXXXXX..XXXXXXX 100644
419
--- a/hw/arm/fsl-imx7.c
420
+++ b/hw/arm/fsl-imx7.c
421
@@ -XXX,XX +XXX,XX @@ static void fsl_imx7_init(Object *obj)
422
char name[NAME_SIZE];
423
int i;
424
425
+ /*
426
+ * CPUs
427
+ */
428
for (i = 0; i < MIN(ms->smp.cpus, FSL_IMX7_NUM_CPUS); i++) {
429
snprintf(name, NAME_SIZE, "cpu%d", i);
430
object_initialize_child(obj, name, &s->cpu[i],
431
@@ -XXX,XX +XXX,XX @@ static void fsl_imx7_init(Object *obj)
432
TYPE_A15MPCORE_PRIV);
433
434
/*
435
- * GPIOs 1 to 7
436
+ * GPIOs
437
*/
438
for (i = 0; i < FSL_IMX7_NUM_GPIOS; i++) {
439
snprintf(name, NAME_SIZE, "gpio%d", i);
440
@@ -XXX,XX +XXX,XX @@ static void fsl_imx7_init(Object *obj)
441
}
442
443
/*
444
- * GPT1, 2, 3, 4
445
+ * GPTs
446
*/
447
for (i = 0; i < FSL_IMX7_NUM_GPTS; i++) {
448
snprintf(name, NAME_SIZE, "gpt%d", i);
449
@@ -XXX,XX +XXX,XX @@ static void fsl_imx7_init(Object *obj)
450
*/
451
object_initialize_child(obj, "gpcv2", &s->gpcv2, TYPE_IMX_GPCV2);
452
453
+ /*
454
+ * ECSPIs
455
+ */
456
for (i = 0; i < FSL_IMX7_NUM_ECSPIS; i++) {
457
snprintf(name, NAME_SIZE, "spi%d", i + 1);
458
object_initialize_child(obj, name, &s->spi[i], TYPE_IMX_SPI);
459
}
460
461
-
462
+ /*
463
+ * I2Cs
464
+ */
465
for (i = 0; i < FSL_IMX7_NUM_I2CS; i++) {
466
snprintf(name, NAME_SIZE, "i2c%d", i + 1);
467
object_initialize_child(obj, name, &s->i2c[i], TYPE_IMX_I2C);
468
}
469
470
/*
471
- * UART
472
+ * UARTs
473
*/
474
for (i = 0; i < FSL_IMX7_NUM_UARTS; i++) {
475
snprintf(name, NAME_SIZE, "uart%d", i);
476
@@ -XXX,XX +XXX,XX @@ static void fsl_imx7_init(Object *obj)
477
}
478
479
/*
480
- * Ethernet
481
+ * Ethernets
482
*/
483
for (i = 0; i < FSL_IMX7_NUM_ETHS; i++) {
484
snprintf(name, NAME_SIZE, "eth%d", i);
485
@@ -XXX,XX +XXX,XX @@ static void fsl_imx7_init(Object *obj)
486
}
487
488
/*
489
- * SDHCI
490
+ * SDHCIs
491
*/
492
for (i = 0; i < FSL_IMX7_NUM_USDHCS; i++) {
493
snprintf(name, NAME_SIZE, "usdhc%d", i);
494
@@ -XXX,XX +XXX,XX @@ static void fsl_imx7_init(Object *obj)
495
object_initialize_child(obj, "snvs", &s->snvs, TYPE_IMX7_SNVS);
496
497
/*
498
- * Watchdog
499
+ * Watchdogs
500
*/
501
for (i = 0; i < FSL_IMX7_NUM_WDTS; i++) {
502
snprintf(name, NAME_SIZE, "wdt%d", i);
503
@@ -XXX,XX +XXX,XX @@ static void fsl_imx7_init(Object *obj)
504
*/
505
object_initialize_child(obj, "gpr", &s->gpr, TYPE_IMX7_GPR);
506
507
+ /*
508
+ * PCIE
509
+ */
510
object_initialize_child(obj, "pcie", &s->pcie, TYPE_DESIGNWARE_PCIE_HOST);
511
512
+ /*
513
+ * USBs
514
+ */
515
for (i = 0; i < FSL_IMX7_NUM_USBS; i++) {
516
snprintf(name, NAME_SIZE, "usb%d", i);
517
object_initialize_child(obj, name, &s->usb[i], TYPE_CHIPIDEA);
518
@@ -XXX,XX +XXX,XX @@ static void fsl_imx7_realize(DeviceState *dev, Error **errp)
34
return;
519
return;
35
}
520
}
36
@@ -XXX,XX +XXX,XX @@ static void icv_eoir_write(CPUARMState *env, const ARMCPRegInfo *ri,
521
37
trace_gicv3_icv_eoir_write(ri->crm == 8 ? 0 : 1,
522
+ /*
38
gicv3_redist_affid(cs), value);
523
+ * CPUs
39
524
+ */
40
- if (irq >= cs->gic->num_irq) {
525
for (i = 0; i < smp_cpus; i++) {
41
+ if (irq >= GICV3_MAXIRQ) {
526
o = OBJECT(&s->cpu[i]);
42
/* Also catches special interrupt numbers and LPIs */
527
43
return;
528
@@ -XXX,XX +XXX,XX @@ static void fsl_imx7_realize(DeviceState *dev, Error **errp)
44
}
529
* A7MPCORE DAP
530
*/
531
create_unimplemented_device("a7mpcore-dap", FSL_IMX7_A7MPCORE_DAP_ADDR,
532
- 0x100000);
533
+ FSL_IMX7_A7MPCORE_DAP_SIZE);
534
535
/*
536
- * GPT1, 2, 3, 4
537
+ * GPTs
538
*/
539
for (i = 0; i < FSL_IMX7_NUM_GPTS; i++) {
540
static const hwaddr FSL_IMX7_GPTn_ADDR[FSL_IMX7_NUM_GPTS] = {
541
@@ -XXX,XX +XXX,XX @@ static void fsl_imx7_realize(DeviceState *dev, Error **errp)
542
FSL_IMX7_GPTn_IRQ[i]));
543
}
544
545
+ /*
546
+ * GPIOs
547
+ */
548
for (i = 0; i < FSL_IMX7_NUM_GPIOS; i++) {
549
static const hwaddr FSL_IMX7_GPIOn_ADDR[FSL_IMX7_NUM_GPIOS] = {
550
FSL_IMX7_GPIO1_ADDR,
551
@@ -XXX,XX +XXX,XX @@ static void fsl_imx7_realize(DeviceState *dev, Error **errp)
552
/*
553
* IOMUXC and IOMUXC_LPSR
554
*/
555
- for (i = 0; i < FSL_IMX7_NUM_IOMUXCS; i++) {
556
- static const hwaddr FSL_IMX7_IOMUXCn_ADDR[FSL_IMX7_NUM_IOMUXCS] = {
557
- FSL_IMX7_IOMUXC_ADDR,
558
- FSL_IMX7_IOMUXC_LPSR_ADDR,
559
- };
560
-
561
- snprintf(name, NAME_SIZE, "iomuxc%d", i);
562
- create_unimplemented_device(name, FSL_IMX7_IOMUXCn_ADDR[i],
563
- FSL_IMX7_IOMUXCn_SIZE);
564
- }
565
+ create_unimplemented_device("iomuxc", FSL_IMX7_IOMUXC_ADDR,
566
+ FSL_IMX7_IOMUXC_SIZE);
567
+ create_unimplemented_device("iomuxc_lspr", FSL_IMX7_IOMUXC_LPSR_ADDR,
568
+ FSL_IMX7_IOMUXC_LPSR_SIZE);
569
570
/*
571
* CCM
572
@@ -XXX,XX +XXX,XX @@ static void fsl_imx7_realize(DeviceState *dev, Error **errp)
573
sysbus_realize(SYS_BUS_DEVICE(&s->gpcv2), &error_abort);
574
sysbus_mmio_map(SYS_BUS_DEVICE(&s->gpcv2), 0, FSL_IMX7_GPC_ADDR);
575
576
- /* Initialize all ECSPI */
577
+ /*
578
+ * ECSPIs
579
+ */
580
for (i = 0; i < FSL_IMX7_NUM_ECSPIS; i++) {
581
static const hwaddr FSL_IMX7_SPIn_ADDR[FSL_IMX7_NUM_ECSPIS] = {
582
FSL_IMX7_ECSPI1_ADDR,
583
@@ -XXX,XX +XXX,XX @@ static void fsl_imx7_realize(DeviceState *dev, Error **errp)
584
FSL_IMX7_SPIn_IRQ[i]));
585
}
586
587
+ /*
588
+ * I2Cs
589
+ */
590
for (i = 0; i < FSL_IMX7_NUM_I2CS; i++) {
591
static const hwaddr FSL_IMX7_I2Cn_ADDR[FSL_IMX7_NUM_I2CS] = {
592
FSL_IMX7_I2C1_ADDR,
593
@@ -XXX,XX +XXX,XX @@ static void fsl_imx7_realize(DeviceState *dev, Error **errp)
594
}
595
596
/*
597
- * UART
598
+ * UARTs
599
*/
600
for (i = 0; i < FSL_IMX7_NUM_UARTS; i++) {
601
static const hwaddr FSL_IMX7_UARTn_ADDR[FSL_IMX7_NUM_UARTS] = {
602
@@ -XXX,XX +XXX,XX @@ static void fsl_imx7_realize(DeviceState *dev, Error **errp)
603
}
604
605
/*
606
- * Ethernet
607
+ * Ethernets
608
*
609
* We must use two loops since phy_connected affects the other interface
610
* and we have to set all properties before calling sysbus_realize().
611
@@ -XXX,XX +XXX,XX @@ static void fsl_imx7_realize(DeviceState *dev, Error **errp)
612
}
613
614
/*
615
- * USDHC
616
+ * USDHCs
617
*/
618
for (i = 0; i < FSL_IMX7_NUM_USDHCS; i++) {
619
static const hwaddr FSL_IMX7_USDHCn_ADDR[FSL_IMX7_NUM_USDHCS] = {
620
@@ -XXX,XX +XXX,XX @@ static void fsl_imx7_realize(DeviceState *dev, Error **errp)
621
* SNVS
622
*/
623
sysbus_realize(SYS_BUS_DEVICE(&s->snvs), &error_abort);
624
- sysbus_mmio_map(SYS_BUS_DEVICE(&s->snvs), 0, FSL_IMX7_SNVS_ADDR);
625
+ sysbus_mmio_map(SYS_BUS_DEVICE(&s->snvs), 0, FSL_IMX7_SNVS_HP_ADDR);
626
627
/*
628
* SRC
629
@@ -XXX,XX +XXX,XX @@ static void fsl_imx7_realize(DeviceState *dev, Error **errp)
630
create_unimplemented_device("src", FSL_IMX7_SRC_ADDR, FSL_IMX7_SRC_SIZE);
631
632
/*
633
- * Watchdog
634
+ * Watchdogs
635
*/
636
for (i = 0; i < FSL_IMX7_NUM_WDTS; i++) {
637
static const hwaddr FSL_IMX7_WDOGn_ADDR[FSL_IMX7_NUM_WDTS] = {
638
@@ -XXX,XX +XXX,XX @@ static void fsl_imx7_realize(DeviceState *dev, Error **errp)
639
create_unimplemented_device("caam", FSL_IMX7_CAAM_ADDR, FSL_IMX7_CAAM_SIZE);
640
641
/*
642
- * PWM
643
+ * PWMs
644
*/
645
- create_unimplemented_device("pwm1", FSL_IMX7_PWM1_ADDR, FSL_IMX7_PWMn_SIZE);
646
- create_unimplemented_device("pwm2", FSL_IMX7_PWM2_ADDR, FSL_IMX7_PWMn_SIZE);
647
- create_unimplemented_device("pwm3", FSL_IMX7_PWM3_ADDR, FSL_IMX7_PWMn_SIZE);
648
- create_unimplemented_device("pwm4", FSL_IMX7_PWM4_ADDR, FSL_IMX7_PWMn_SIZE);
649
+ for (i = 0; i < FSL_IMX7_NUM_PWMS; i++) {
650
+ static const hwaddr FSL_IMX7_PWMn_ADDR[FSL_IMX7_NUM_PWMS] = {
651
+ FSL_IMX7_PWM1_ADDR,
652
+ FSL_IMX7_PWM2_ADDR,
653
+ FSL_IMX7_PWM3_ADDR,
654
+ FSL_IMX7_PWM4_ADDR,
655
+ };
656
+
657
+ snprintf(name, NAME_SIZE, "pwm%d", i);
658
+ create_unimplemented_device(name, FSL_IMX7_PWMn_ADDR[i],
659
+ FSL_IMX7_PWMn_SIZE);
660
+ }
661
662
/*
663
- * CAN
664
+ * CANs
665
*/
666
- create_unimplemented_device("can1", FSL_IMX7_CAN1_ADDR, FSL_IMX7_CANn_SIZE);
667
- create_unimplemented_device("can2", FSL_IMX7_CAN2_ADDR, FSL_IMX7_CANn_SIZE);
668
+ for (i = 0; i < FSL_IMX7_NUM_CANS; i++) {
669
+ static const hwaddr FSL_IMX7_CANn_ADDR[FSL_IMX7_NUM_CANS] = {
670
+ FSL_IMX7_CAN1_ADDR,
671
+ FSL_IMX7_CAN2_ADDR,
672
+ };
673
+
674
+ snprintf(name, NAME_SIZE, "can%d", i);
675
+ create_unimplemented_device(name, FSL_IMX7_CANn_ADDR[i],
676
+ FSL_IMX7_CANn_SIZE);
677
+ }
678
679
/*
680
- * SAI (Audio SSI (Synchronous Serial Interface))
681
+ * SAIs (Audio SSI (Synchronous Serial Interface))
682
*/
683
- create_unimplemented_device("sai1", FSL_IMX7_SAI1_ADDR, FSL_IMX7_SAIn_SIZE);
684
- create_unimplemented_device("sai2", FSL_IMX7_SAI2_ADDR, FSL_IMX7_SAIn_SIZE);
685
- create_unimplemented_device("sai2", FSL_IMX7_SAI3_ADDR, FSL_IMX7_SAIn_SIZE);
686
+ for (i = 0; i < FSL_IMX7_NUM_SAIS; i++) {
687
+ static const hwaddr FSL_IMX7_SAIn_ADDR[FSL_IMX7_NUM_SAIS] = {
688
+ FSL_IMX7_SAI1_ADDR,
689
+ FSL_IMX7_SAI2_ADDR,
690
+ FSL_IMX7_SAI3_ADDR,
691
+ };
692
+
693
+ snprintf(name, NAME_SIZE, "sai%d", i);
694
+ create_unimplemented_device(name, FSL_IMX7_SAIn_ADDR[i],
695
+ FSL_IMX7_SAIn_SIZE);
696
+ }
697
698
/*
699
* OCOTP
700
@@ -XXX,XX +XXX,XX @@ static void fsl_imx7_realize(DeviceState *dev, Error **errp)
701
create_unimplemented_device("ocotp", FSL_IMX7_OCOTP_ADDR,
702
FSL_IMX7_OCOTP_SIZE);
703
704
+ /*
705
+ * GPR
706
+ */
707
sysbus_realize(SYS_BUS_DEVICE(&s->gpr), &error_abort);
708
- sysbus_mmio_map(SYS_BUS_DEVICE(&s->gpr), 0, FSL_IMX7_GPR_ADDR);
709
+ sysbus_mmio_map(SYS_BUS_DEVICE(&s->gpr), 0, FSL_IMX7_IOMUXC_GPR_ADDR);
710
711
+ /*
712
+ * PCIE
713
+ */
714
sysbus_realize(SYS_BUS_DEVICE(&s->pcie), &error_abort);
715
sysbus_mmio_map(SYS_BUS_DEVICE(&s->pcie), 0, FSL_IMX7_PCIE_REG_ADDR);
716
717
@@ -XXX,XX +XXX,XX @@ static void fsl_imx7_realize(DeviceState *dev, Error **errp)
718
irq = qdev_get_gpio_in(DEVICE(&s->a7mpcore), FSL_IMX7_PCI_INTD_IRQ);
719
sysbus_connect_irq(SYS_BUS_DEVICE(&s->pcie), 3, irq);
720
721
-
722
+ /*
723
+ * USBs
724
+ */
725
for (i = 0; i < FSL_IMX7_NUM_USBS; i++) {
726
static const hwaddr FSL_IMX7_USBMISCn_ADDR[FSL_IMX7_NUM_USBS] = {
727
FSL_IMX7_USBMISC1_ADDR,
728
@@ -XXX,XX +XXX,XX @@ static void fsl_imx7_realize(DeviceState *dev, Error **errp)
729
*/
730
create_unimplemented_device("pcie-phy", FSL_IMX7_PCIE_PHY_ADDR,
731
FSL_IMX7_PCIE_PHY_SIZE);
732
+
733
}
734
735
static Property fsl_imx7_properties[] = {
45
--
736
--
46
2.20.1
737
2.34.1
47
48
diff view generated by jsdifflib
1
The Luminary PL061s in the Stellaris LM3S9695 don't all have the same
1
From: Jean-Christophe Dubois <jcd@tribudubois.net>
2
reset value for GPIOPUR. We can get away with not letting the board
3
configure the PUR reset value because we don't actually wire anything
4
up to the lines which should reset to pull-up. Add a comment noting
5
this omission.
6
2
3
* Add TZASC as unimplemented device.
4
- Allow bare metal application to access this (unimplemented) device
5
* Add CSU as unimplemented device.
6
- Allow bare metal application to access this (unimplemented) device
7
* Add various memory segments
8
- OCRAM
9
- OCRAM EPDC
10
- OCRAM PXP
11
- OCRAM S
12
- ROM
13
- CAAM
14
15
Signed-off-by: Jean-Christophe Dubois <jcd@tribudubois.net>
16
Reviewed-by: Philippe Mathieu-Daudé <philmd@linaro.org>
17
Message-id: f887a3483996ba06d40bd62ffdfb0ecf68621987.1692964892.git.jcd@tribudubois.net
7
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
18
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
8
Reviewed-by: Philippe Mathieu-Daudé <f4bug@amsat.org>
9
---
19
---
10
hw/gpio/pl061.c | 9 +++++++++
20
include/hw/arm/fsl-imx7.h | 7 +++++
11
1 file changed, 9 insertions(+)
21
hw/arm/fsl-imx7.c | 63 +++++++++++++++++++++++++++++++++++++++
22
2 files changed, 70 insertions(+)
12
23
13
diff --git a/hw/gpio/pl061.c b/hw/gpio/pl061.c
24
diff --git a/include/hw/arm/fsl-imx7.h b/include/hw/arm/fsl-imx7.h
14
index XXXXXXX..XXXXXXX 100644
25
index XXXXXXX..XXXXXXX 100644
15
--- a/hw/gpio/pl061.c
26
--- a/include/hw/arm/fsl-imx7.h
16
+++ b/hw/gpio/pl061.c
27
+++ b/include/hw/arm/fsl-imx7.h
17
@@ -XXX,XX +XXX,XX @@ static void pl061_enter_reset(Object *obj, ResetType type)
28
@@ -XXX,XX +XXX,XX @@ struct FslIMX7State {
18
trace_pl061_reset(DEVICE(s)->canonical_path);
29
IMX7GPRState gpr;
19
30
ChipideaState usb[FSL_IMX7_NUM_USBS];
20
/* reset values from PL061 TRM, Stellaris LM3S5P31 & LM3S8962 Data Sheet */
31
DesignwarePCIEHost pcie;
32
+ MemoryRegion rom;
33
+ MemoryRegion caam;
34
+ MemoryRegion ocram;
35
+ MemoryRegion ocram_epdc;
36
+ MemoryRegion ocram_pxp;
37
+ MemoryRegion ocram_s;
38
+
39
uint32_t phy_num[FSL_IMX7_NUM_ETHS];
40
bool phy_connected[FSL_IMX7_NUM_ETHS];
41
};
42
diff --git a/hw/arm/fsl-imx7.c b/hw/arm/fsl-imx7.c
43
index XXXXXXX..XXXXXXX 100644
44
--- a/hw/arm/fsl-imx7.c
45
+++ b/hw/arm/fsl-imx7.c
46
@@ -XXX,XX +XXX,XX @@ static void fsl_imx7_realize(DeviceState *dev, Error **errp)
47
create_unimplemented_device("pcie-phy", FSL_IMX7_PCIE_PHY_ADDR,
48
FSL_IMX7_PCIE_PHY_SIZE);
49
50
+ /*
51
+ * CSU
52
+ */
53
+ create_unimplemented_device("csu", FSL_IMX7_CSU_ADDR,
54
+ FSL_IMX7_CSU_SIZE);
21
+
55
+
22
+ /*
56
+ /*
23
+ * FIXME: For the LM3S6965, not all of the PL061 instances have the
57
+ * TZASC
24
+ * same reset values for GPIOPUR, GPIOAFSEL and GPIODEN, so in theory
25
+ * we should allow the board to configure these via properties.
26
+ * In practice, we don't wire anything up to the affected GPIO lines
27
+ * (PB7, PC0, PC1, PC2, PC3 -- they're used for JTAG), so we can
28
+ * get away with this inaccuracy.
29
+ */
58
+ */
30
s->data = 0;
59
+ create_unimplemented_device("tzasc", FSL_IMX7_TZASC_ADDR,
31
s->old_in_data = 0;
60
+ FSL_IMX7_TZASC_SIZE);
32
s->dir = 0;
61
+
62
+ /*
63
+ * OCRAM memory
64
+ */
65
+ memory_region_init_ram(&s->ocram, NULL, "imx7.ocram",
66
+ FSL_IMX7_OCRAM_MEM_SIZE,
67
+ &error_abort);
68
+ memory_region_add_subregion(get_system_memory(), FSL_IMX7_OCRAM_MEM_ADDR,
69
+ &s->ocram);
70
+
71
+ /*
72
+ * OCRAM EPDC memory
73
+ */
74
+ memory_region_init_ram(&s->ocram_epdc, NULL, "imx7.ocram_epdc",
75
+ FSL_IMX7_OCRAM_EPDC_SIZE,
76
+ &error_abort);
77
+ memory_region_add_subregion(get_system_memory(), FSL_IMX7_OCRAM_EPDC_ADDR,
78
+ &s->ocram_epdc);
79
+
80
+ /*
81
+ * OCRAM PXP memory
82
+ */
83
+ memory_region_init_ram(&s->ocram_pxp, NULL, "imx7.ocram_pxp",
84
+ FSL_IMX7_OCRAM_PXP_SIZE,
85
+ &error_abort);
86
+ memory_region_add_subregion(get_system_memory(), FSL_IMX7_OCRAM_PXP_ADDR,
87
+ &s->ocram_pxp);
88
+
89
+ /*
90
+ * OCRAM_S memory
91
+ */
92
+ memory_region_init_ram(&s->ocram_s, NULL, "imx7.ocram_s",
93
+ FSL_IMX7_OCRAM_S_SIZE,
94
+ &error_abort);
95
+ memory_region_add_subregion(get_system_memory(), FSL_IMX7_OCRAM_S_ADDR,
96
+ &s->ocram_s);
97
+
98
+ /*
99
+ * ROM memory
100
+ */
101
+ memory_region_init_rom(&s->rom, OBJECT(dev), "imx7.rom",
102
+ FSL_IMX7_ROM_SIZE, &error_abort);
103
+ memory_region_add_subregion(get_system_memory(), FSL_IMX7_ROM_ADDR,
104
+ &s->rom);
105
+
106
+ /*
107
+ * CAAM memory
108
+ */
109
+ memory_region_init_rom(&s->caam, OBJECT(dev), "imx7.caam",
110
+ FSL_IMX7_CAAM_MEM_SIZE, &error_abort);
111
+ memory_region_add_subregion(get_system_memory(), FSL_IMX7_CAAM_MEM_ADDR,
112
+ &s->caam);
113
}
114
115
static Property fsl_imx7_properties[] = {
33
--
116
--
34
2.20.1
117
2.34.1
35
118
36
119
diff view generated by jsdifflib
1
From: Alexandre Iooss <erdnaxe@crans.org>
1
From: Jean-Christophe Dubois <jcd@tribudubois.net>
2
2
3
This SoC is similar to stm32f205 SoC.
3
The SRC device is normally used to start the secondary CPU.
4
This will be used by the STM32VLDISCOVERY to create a machine.
4
5
5
When running Linux directly, QEMU is emulating a PSCI interface that UBOOT
6
Signed-off-by: Alexandre Iooss <erdnaxe@crans.org>
6
is installing at boot time and therefore the fact that the SRC device is
7
Reviewed-by: Alistair Francis <alistair.francis@wdc.com>
7
unimplemented is hidden as Qemu respond directly to PSCI requets without
8
Message-id: 20210617165647.2575955-2-erdnaxe@crans.org
8
using the SRC device.
9
10
But if you try to run a more bare metal application (maybe uboot itself),
11
then it is not possible to start the secondary CPU as the SRC is an
12
unimplemented device.
13
14
This patch adds the ability to start the secondary CPU through the SRC
15
device so that you can use this feature in bare metal applications.
16
17
Signed-off-by: Jean-Christophe Dubois <jcd@tribudubois.net>
18
Reviewed-by: Peter Maydell <peter.maydell@linaro.org>
19
Message-id: ce9a0162defd2acee5dc7f8a674743de0cded569.1692964892.git.jcd@tribudubois.net
9
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
20
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
10
---
21
---
11
include/hw/arm/stm32f100_soc.h | 57 +++++++++++
22
include/hw/arm/fsl-imx7.h | 3 +-
12
hw/arm/stm32f100_soc.c | 182 +++++++++++++++++++++++++++++++++
23
include/hw/misc/imx7_src.h | 66 +++++++++
13
MAINTAINERS | 6 ++
24
hw/arm/fsl-imx7.c | 8 +-
14
hw/arm/Kconfig | 6 ++
25
hw/misc/imx7_src.c | 276 +++++++++++++++++++++++++++++++++++++
15
hw/arm/meson.build | 1 +
26
hw/misc/meson.build | 1 +
16
5 files changed, 252 insertions(+)
27
hw/misc/trace-events | 4 +
17
create mode 100644 include/hw/arm/stm32f100_soc.h
28
6 files changed, 356 insertions(+), 2 deletions(-)
18
create mode 100644 hw/arm/stm32f100_soc.c
29
create mode 100644 include/hw/misc/imx7_src.h
19
30
create mode 100644 hw/misc/imx7_src.c
20
diff --git a/include/hw/arm/stm32f100_soc.h b/include/hw/arm/stm32f100_soc.h
31
32
diff --git a/include/hw/arm/fsl-imx7.h b/include/hw/arm/fsl-imx7.h
33
index XXXXXXX..XXXXXXX 100644
34
--- a/include/hw/arm/fsl-imx7.h
35
+++ b/include/hw/arm/fsl-imx7.h
36
@@ -XXX,XX +XXX,XX @@
37
#include "hw/misc/imx7_ccm.h"
38
#include "hw/misc/imx7_snvs.h"
39
#include "hw/misc/imx7_gpr.h"
40
+#include "hw/misc/imx7_src.h"
41
#include "hw/watchdog/wdt_imx2.h"
42
#include "hw/gpio/imx_gpio.h"
43
#include "hw/char/imx_serial.h"
44
@@ -XXX,XX +XXX,XX @@ struct FslIMX7State {
45
IMX7CCMState ccm;
46
IMX7AnalogState analog;
47
IMX7SNVSState snvs;
48
+ IMX7SRCState src;
49
IMXGPCv2State gpcv2;
50
IMXSPIState spi[FSL_IMX7_NUM_ECSPIS];
51
IMXI2CState i2c[FSL_IMX7_NUM_I2CS];
52
@@ -XXX,XX +XXX,XX @@ enum FslIMX7MemoryMap {
53
FSL_IMX7_GPC_ADDR = 0x303A0000,
54
55
FSL_IMX7_SRC_ADDR = 0x30390000,
56
- FSL_IMX7_SRC_SIZE = (4 * KiB),
57
58
FSL_IMX7_CCM_ADDR = 0x30380000,
59
60
diff --git a/include/hw/misc/imx7_src.h b/include/hw/misc/imx7_src.h
21
new file mode 100644
61
new file mode 100644
22
index XXXXXXX..XXXXXXX
62
index XXXXXXX..XXXXXXX
23
--- /dev/null
63
--- /dev/null
24
+++ b/include/hw/arm/stm32f100_soc.h
64
+++ b/include/hw/misc/imx7_src.h
25
@@ -XXX,XX +XXX,XX @@
65
@@ -XXX,XX +XXX,XX @@
26
+/*
66
+/*
27
+ * STM32F100 SoC
67
+ * IMX7 System Reset Controller
28
+ *
68
+ *
29
+ * Copyright (c) 2021 Alexandre Iooss <erdnaxe@crans.org>
69
+ * Copyright (C) 2023 Jean-Christophe Dubois <jcd@tribudubois.net>
30
+ *
70
+ *
31
+ * Permission is hereby granted, free of charge, to any person obtaining a copy
71
+ * This work is licensed under the terms of the GNU GPL, version 2 or later.
32
+ * of this software and associated documentation files (the "Software"), to deal
72
+ * See the COPYING file in the top-level directory.
33
+ * in the Software without restriction, including without limitation the rights
34
+ * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
35
+ * copies of the Software, and to permit persons to whom the Software is
36
+ * furnished to do so, subject to the following conditions:
37
+ *
38
+ * The above copyright notice and this permission notice shall be included in
39
+ * all copies or substantial portions of the Software.
40
+ *
41
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
42
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
43
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
44
+ * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
45
+ * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
46
+ * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
47
+ * THE SOFTWARE.
48
+ */
73
+ */
49
+
74
+
50
+#ifndef HW_ARM_STM32F100_SOC_H
75
+#ifndef IMX7_SRC_H
51
+#define HW_ARM_STM32F100_SOC_H
76
+#define IMX7_SRC_H
52
+
77
+
53
+#include "hw/char/stm32f2xx_usart.h"
78
+#include "hw/sysbus.h"
54
+#include "hw/ssi/stm32f2xx_spi.h"
79
+#include "qemu/bitops.h"
55
+#include "hw/arm/armv7m.h"
56
+#include "qom/object.h"
80
+#include "qom/object.h"
57
+
81
+
58
+#define TYPE_STM32F100_SOC "stm32f100-soc"
82
+#define SRC_SCR 0
59
+OBJECT_DECLARE_SIMPLE_TYPE(STM32F100State, STM32F100_SOC)
83
+#define SRC_A7RCR0 1
60
+
84
+#define SRC_A7RCR1 2
61
+#define STM_NUM_USARTS 3
85
+#define SRC_M4RCR 3
62
+#define STM_NUM_SPIS 2
86
+#define SRC_ERCR 5
63
+
87
+#define SRC_HSICPHY_RCR 7
64
+#define FLASH_BASE_ADDRESS 0x08000000
88
+#define SRC_USBOPHY1_RCR 8
65
+#define FLASH_SIZE (128 * 1024)
89
+#define SRC_USBOPHY2_RCR 9
66
+#define SRAM_BASE_ADDRESS 0x20000000
90
+#define SRC_MPIPHY_RCR 10
67
+#define SRAM_SIZE (8 * 1024)
91
+#define SRC_PCIEPHY_RCR 11
68
+
92
+#define SRC_SBMR1 22
69
+struct STM32F100State {
93
+#define SRC_SRSR 23
70
+ /*< private >*/
94
+#define SRC_SISR 26
95
+#define SRC_SIMR 27
96
+#define SRC_SBMR2 28
97
+#define SRC_GPR1 29
98
+#define SRC_GPR2 30
99
+#define SRC_GPR3 31
100
+#define SRC_GPR4 32
101
+#define SRC_GPR5 33
102
+#define SRC_GPR6 34
103
+#define SRC_GPR7 35
104
+#define SRC_GPR8 36
105
+#define SRC_GPR9 37
106
+#define SRC_GPR10 38
107
+#define SRC_MAX 39
108
+
109
+/* SRC_A7SCR1 */
110
+#define R_CORE1_ENABLE_SHIFT 1
111
+#define R_CORE1_ENABLE_LENGTH 1
112
+/* SRC_A7SCR0 */
113
+#define R_CORE1_RST_SHIFT 5
114
+#define R_CORE1_RST_LENGTH 1
115
+#define R_CORE0_RST_SHIFT 4
116
+#define R_CORE0_RST_LENGTH 1
117
+
118
+#define TYPE_IMX7_SRC "imx7.src"
119
+OBJECT_DECLARE_SIMPLE_TYPE(IMX7SRCState, IMX7_SRC)
120
+
121
+struct IMX7SRCState {
122
+ /* <private> */
71
+ SysBusDevice parent_obj;
123
+ SysBusDevice parent_obj;
72
+
124
+
73
+ /*< public >*/
125
+ /* <public> */
74
+ char *cpu_type;
126
+ MemoryRegion iomem;
75
+
127
+
76
+ ARMv7MState armv7m;
128
+ uint32_t regs[SRC_MAX];
77
+
78
+ STM32F2XXUsartState usart[STM_NUM_USARTS];
79
+ STM32F2XXSPIState spi[STM_NUM_SPIS];
80
+};
129
+};
81
+
130
+
82
+#endif
131
+#endif /* IMX7_SRC_H */
83
diff --git a/hw/arm/stm32f100_soc.c b/hw/arm/stm32f100_soc.c
132
diff --git a/hw/arm/fsl-imx7.c b/hw/arm/fsl-imx7.c
133
index XXXXXXX..XXXXXXX 100644
134
--- a/hw/arm/fsl-imx7.c
135
+++ b/hw/arm/fsl-imx7.c
136
@@ -XXX,XX +XXX,XX @@ static void fsl_imx7_init(Object *obj)
137
*/
138
object_initialize_child(obj, "gpcv2", &s->gpcv2, TYPE_IMX_GPCV2);
139
140
+ /*
141
+ * SRC
142
+ */
143
+ object_initialize_child(obj, "src", &s->src, TYPE_IMX7_SRC);
144
+
145
/*
146
* ECSPIs
147
*/
148
@@ -XXX,XX +XXX,XX @@ static void fsl_imx7_realize(DeviceState *dev, Error **errp)
149
/*
150
* SRC
151
*/
152
- create_unimplemented_device("src", FSL_IMX7_SRC_ADDR, FSL_IMX7_SRC_SIZE);
153
+ sysbus_realize(SYS_BUS_DEVICE(&s->src), &error_abort);
154
+ sysbus_mmio_map(SYS_BUS_DEVICE(&s->src), 0, FSL_IMX7_SRC_ADDR);
155
156
/*
157
* Watchdogs
158
diff --git a/hw/misc/imx7_src.c b/hw/misc/imx7_src.c
84
new file mode 100644
159
new file mode 100644
85
index XXXXXXX..XXXXXXX
160
index XXXXXXX..XXXXXXX
86
--- /dev/null
161
--- /dev/null
87
+++ b/hw/arm/stm32f100_soc.c
162
+++ b/hw/misc/imx7_src.c
88
@@ -XXX,XX +XXX,XX @@
163
@@ -XXX,XX +XXX,XX @@
89
+/*
164
+/*
90
+ * STM32F100 SoC
165
+ * IMX7 System Reset Controller
91
+ *
166
+ *
92
+ * Copyright (c) 2021 Alexandre Iooss <erdnaxe@crans.org>
167
+ * Copyright (c) 2023 Jean-Christophe Dubois <jcd@tribudubois.net>
93
+ * Copyright (c) 2014 Alistair Francis <alistair@alistair23.me>
94
+ *
168
+ *
95
+ * Permission is hereby granted, free of charge, to any person obtaining a copy
169
+ * This work is licensed under the terms of the GNU GPL, version 2 or later.
96
+ * of this software and associated documentation files (the "Software"), to deal
170
+ * See the COPYING file in the top-level directory.
97
+ * in the Software without restriction, including without limitation the rights
98
+ * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
99
+ * copies of the Software, and to permit persons to whom the Software is
100
+ * furnished to do so, subject to the following conditions:
101
+ *
171
+ *
102
+ * The above copyright notice and this permission notice shall be included in
103
+ * all copies or substantial portions of the Software.
104
+ *
105
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
106
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
107
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
108
+ * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
109
+ * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
110
+ * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
111
+ * THE SOFTWARE.
112
+ */
172
+ */
113
+
173
+
114
+#include "qemu/osdep.h"
174
+#include "qemu/osdep.h"
115
+#include "qapi/error.h"
175
+#include "hw/misc/imx7_src.h"
176
+#include "migration/vmstate.h"
177
+#include "qemu/bitops.h"
178
+#include "qemu/log.h"
179
+#include "qemu/main-loop.h"
116
+#include "qemu/module.h"
180
+#include "qemu/module.h"
117
+#include "hw/arm/boot.h"
181
+#include "target/arm/arm-powerctl.h"
118
+#include "exec/address-spaces.h"
182
+#include "hw/core/cpu.h"
119
+#include "hw/arm/stm32f100_soc.h"
183
+#include "hw/registerfields.h"
120
+#include "hw/qdev-properties.h"
184
+
121
+#include "hw/misc/unimp.h"
185
+#include "trace.h"
122
+#include "sysemu/sysemu.h"
186
+
123
+
187
+static const char *imx7_src_reg_name(uint32_t reg)
124
+/* stm32f100_soc implementation is derived from stm32f205_soc */
188
+{
125
+
189
+ static char unknown[20];
126
+static const uint32_t usart_addr[STM_NUM_USARTS] = { 0x40013800, 0x40004400,
190
+
127
+ 0x40004800 };
191
+ switch (reg) {
128
+static const uint32_t spi_addr[STM_NUM_SPIS] = { 0x40013000, 0x40003800 };
192
+ case SRC_SCR:
129
+
193
+ return "SRC_SCR";
130
+static const int usart_irq[STM_NUM_USARTS] = {37, 38, 39};
194
+ case SRC_A7RCR0:
131
+static const int spi_irq[STM_NUM_SPIS] = {35, 36};
195
+ return "SRC_A7RCR0";
132
+
196
+ case SRC_A7RCR1:
133
+static void stm32f100_soc_initfn(Object *obj)
197
+ return "SRC_A7RCR1";
134
+{
198
+ case SRC_M4RCR:
135
+ STM32F100State *s = STM32F100_SOC(obj);
199
+ return "SRC_M4RCR";
136
+ int i;
200
+ case SRC_ERCR:
137
+
201
+ return "SRC_ERCR";
138
+ object_initialize_child(obj, "armv7m", &s->armv7m, TYPE_ARMV7M);
202
+ case SRC_HSICPHY_RCR:
139
+
203
+ return "SRC_HSICPHY_RCR";
140
+ for (i = 0; i < STM_NUM_USARTS; i++) {
204
+ case SRC_USBOPHY1_RCR:
141
+ object_initialize_child(obj, "usart[*]", &s->usart[i],
205
+ return "SRC_USBOPHY1_RCR";
142
+ TYPE_STM32F2XX_USART);
206
+ case SRC_USBOPHY2_RCR:
207
+ return "SRC_USBOPHY2_RCR";
208
+ case SRC_PCIEPHY_RCR:
209
+ return "SRC_PCIEPHY_RCR";
210
+ case SRC_SBMR1:
211
+ return "SRC_SBMR1";
212
+ case SRC_SRSR:
213
+ return "SRC_SRSR";
214
+ case SRC_SISR:
215
+ return "SRC_SISR";
216
+ case SRC_SIMR:
217
+ return "SRC_SIMR";
218
+ case SRC_SBMR2:
219
+ return "SRC_SBMR2";
220
+ case SRC_GPR1:
221
+ return "SRC_GPR1";
222
+ case SRC_GPR2:
223
+ return "SRC_GPR2";
224
+ case SRC_GPR3:
225
+ return "SRC_GPR3";
226
+ case SRC_GPR4:
227
+ return "SRC_GPR4";
228
+ case SRC_GPR5:
229
+ return "SRC_GPR5";
230
+ case SRC_GPR6:
231
+ return "SRC_GPR6";
232
+ case SRC_GPR7:
233
+ return "SRC_GPR7";
234
+ case SRC_GPR8:
235
+ return "SRC_GPR8";
236
+ case SRC_GPR9:
237
+ return "SRC_GPR9";
238
+ case SRC_GPR10:
239
+ return "SRC_GPR10";
240
+ default:
241
+ sprintf(unknown, "%u ?", reg);
242
+ return unknown;
143
+ }
243
+ }
144
+
244
+}
145
+ for (i = 0; i < STM_NUM_SPIS; i++) {
245
+
146
+ object_initialize_child(obj, "spi[*]", &s->spi[i], TYPE_STM32F2XX_SPI);
246
+static const VMStateDescription vmstate_imx7_src = {
247
+ .name = TYPE_IMX7_SRC,
248
+ .version_id = 1,
249
+ .minimum_version_id = 1,
250
+ .fields = (VMStateField[]) {
251
+ VMSTATE_UINT32_ARRAY(regs, IMX7SRCState, SRC_MAX),
252
+ VMSTATE_END_OF_LIST()
253
+ },
254
+};
255
+
256
+static void imx7_src_reset(DeviceState *dev)
257
+{
258
+ IMX7SRCState *s = IMX7_SRC(dev);
259
+
260
+ memset(s->regs, 0, sizeof(s->regs));
261
+
262
+ /* Set reset values */
263
+ s->regs[SRC_SCR] = 0xA0;
264
+ s->regs[SRC_SRSR] = 0x1;
265
+ s->regs[SRC_SIMR] = 0x1F;
266
+}
267
+
268
+static uint64_t imx7_src_read(void *opaque, hwaddr offset, unsigned size)
269
+{
270
+ uint32_t value = 0;
271
+ IMX7SRCState *s = (IMX7SRCState *)opaque;
272
+ uint32_t index = offset >> 2;
273
+
274
+ if (index < SRC_MAX) {
275
+ value = s->regs[index];
276
+ } else {
277
+ qemu_log_mask(LOG_GUEST_ERROR, "[%s]%s: Bad register at offset 0x%"
278
+ HWADDR_PRIx "\n", TYPE_IMX7_SRC, __func__, offset);
147
+ }
279
+ }
148
+}
280
+
149
+
281
+ trace_imx7_src_read(imx7_src_reg_name(index), value);
150
+static void stm32f100_soc_realize(DeviceState *dev_soc, Error **errp)
282
+
151
+{
283
+ return value;
152
+ STM32F100State *s = STM32F100_SOC(dev_soc);
284
+}
153
+ DeviceState *dev, *armv7m;
285
+
154
+ SysBusDevice *busdev;
286
+
155
+ int i;
287
+/*
156
+
288
+ * The reset is asynchronous so we need to defer clearing the reset
157
+ MemoryRegion *system_memory = get_system_memory();
289
+ * bit until the work is completed.
158
+ MemoryRegion *sram = g_new(MemoryRegion, 1);
290
+ */
159
+ MemoryRegion *flash = g_new(MemoryRegion, 1);
291
+
160
+ MemoryRegion *flash_alias = g_new(MemoryRegion, 1);
292
+struct SRCSCRResetInfo {
161
+
293
+ IMX7SRCState *s;
162
+ /*
294
+ uint32_t reset_bit;
163
+ * Init flash region
295
+};
164
+ * Flash starts at 0x08000000 and then is aliased to boot memory at 0x0
296
+
165
+ */
297
+static void imx7_clear_reset_bit(CPUState *cpu, run_on_cpu_data data)
166
+ memory_region_init_rom(flash, OBJECT(dev_soc), "STM32F100.flash",
298
+{
167
+ FLASH_SIZE, &error_fatal);
299
+ struct SRCSCRResetInfo *ri = data.host_ptr;
168
+ memory_region_init_alias(flash_alias, OBJECT(dev_soc),
300
+ IMX7SRCState *s = ri->s;
169
+ "STM32F100.flash.alias", flash, 0, FLASH_SIZE);
301
+
170
+ memory_region_add_subregion(system_memory, FLASH_BASE_ADDRESS, flash);
302
+ assert(qemu_mutex_iothread_locked());
171
+ memory_region_add_subregion(system_memory, 0, flash_alias);
303
+
172
+
304
+ s->regs[SRC_A7RCR0] = deposit32(s->regs[SRC_A7RCR0], ri->reset_bit, 1, 0);
173
+ /* Init SRAM region */
305
+
174
+ memory_region_init_ram(sram, NULL, "STM32F100.sram", SRAM_SIZE,
306
+ trace_imx7_src_write(imx7_src_reg_name(SRC_A7RCR0), s->regs[SRC_A7RCR0]);
175
+ &error_fatal);
307
+
176
+ memory_region_add_subregion(system_memory, SRAM_BASE_ADDRESS, sram);
308
+ g_free(ri);
177
+
309
+}
178
+ /* Init ARMv7m */
310
+
179
+ armv7m = DEVICE(&s->armv7m);
311
+static void imx7_defer_clear_reset_bit(uint32_t cpuid,
180
+ qdev_prop_set_uint32(armv7m, "num-irq", 61);
312
+ IMX7SRCState *s,
181
+ qdev_prop_set_string(armv7m, "cpu-type", s->cpu_type);
313
+ uint32_t reset_shift)
182
+ qdev_prop_set_bit(armv7m, "enable-bitband", true);
314
+{
183
+ object_property_set_link(OBJECT(&s->armv7m), "memory",
315
+ struct SRCSCRResetInfo *ri;
184
+ OBJECT(get_system_memory()), &error_abort);
316
+ CPUState *cpu = arm_get_cpu_by_id(cpuid);
185
+ if (!sysbus_realize(SYS_BUS_DEVICE(&s->armv7m), errp)) {
317
+
318
+ if (!cpu) {
186
+ return;
319
+ return;
187
+ }
320
+ }
188
+
321
+
189
+ /* Attach UART (uses USART registers) and USART controllers */
322
+ ri = g_new(struct SRCSCRResetInfo, 1);
190
+ for (i = 0; i < STM_NUM_USARTS; i++) {
323
+ ri->s = s;
191
+ dev = DEVICE(&(s->usart[i]));
324
+ ri->reset_bit = reset_shift;
192
+ qdev_prop_set_chr(dev, "chardev", serial_hd(i));
325
+
193
+ if (!sysbus_realize(SYS_BUS_DEVICE(&s->usart[i]), errp)) {
326
+ async_run_on_cpu(cpu, imx7_clear_reset_bit, RUN_ON_CPU_HOST_PTR(ri));
194
+ return;
327
+}
328
+
329
+
330
+static void imx7_src_write(void *opaque, hwaddr offset, uint64_t value,
331
+ unsigned size)
332
+{
333
+ IMX7SRCState *s = (IMX7SRCState *)opaque;
334
+ uint32_t index = offset >> 2;
335
+ long unsigned int change_mask;
336
+ uint32_t current_value = value;
337
+
338
+ if (index >= SRC_MAX) {
339
+ qemu_log_mask(LOG_GUEST_ERROR, "[%s]%s: Bad register at offset 0x%"
340
+ HWADDR_PRIx "\n", TYPE_IMX7_SRC, __func__, offset);
341
+ return;
342
+ }
343
+
344
+ trace_imx7_src_write(imx7_src_reg_name(SRC_A7RCR0), s->regs[SRC_A7RCR0]);
345
+
346
+ change_mask = s->regs[index] ^ (uint32_t)current_value;
347
+
348
+ switch (index) {
349
+ case SRC_A7RCR0:
350
+ if (FIELD_EX32(change_mask, CORE0, RST)) {
351
+ arm_reset_cpu(0);
352
+ imx7_defer_clear_reset_bit(0, s, R_CORE0_RST_SHIFT);
195
+ }
353
+ }
196
+ busdev = SYS_BUS_DEVICE(dev);
354
+ if (FIELD_EX32(change_mask, CORE1, RST)) {
197
+ sysbus_mmio_map(busdev, 0, usart_addr[i]);
355
+ arm_reset_cpu(1);
198
+ sysbus_connect_irq(busdev, 0, qdev_get_gpio_in(armv7m, usart_irq[i]));
356
+ imx7_defer_clear_reset_bit(1, s, R_CORE1_RST_SHIFT);
357
+ }
358
+ s->regs[index] = current_value;
359
+ break;
360
+ case SRC_A7RCR1:
361
+ /*
362
+ * On real hardware when the system reset controller starts a
363
+ * secondary CPU it runs through some boot ROM code which reads
364
+ * the SRC_GPRX registers controlling the start address and branches
365
+ * to it.
366
+ * Here we are taking a short cut and branching directly to the
367
+ * requested address (we don't want to run the boot ROM code inside
368
+ * QEMU)
369
+ */
370
+ if (FIELD_EX32(change_mask, CORE1, ENABLE)) {
371
+ if (FIELD_EX32(current_value, CORE1, ENABLE)) {
372
+ /* CORE 1 is brought up */
373
+ arm_set_cpu_on(1, s->regs[SRC_GPR3], s->regs[SRC_GPR4],
374
+ 3, false);
375
+ } else {
376
+ /* CORE 1 is shut down */
377
+ arm_set_cpu_off(1);
378
+ }
379
+ /* We clear the reset bits as the processor changed state */
380
+ imx7_defer_clear_reset_bit(1, s, R_CORE1_RST_SHIFT);
381
+ clear_bit(R_CORE1_RST_SHIFT, &change_mask);
382
+ }
383
+ s->regs[index] = current_value;
384
+ break;
385
+ default:
386
+ s->regs[index] = current_value;
387
+ break;
199
+ }
388
+ }
200
+
389
+}
201
+ /* SPI 1 and 2 */
390
+
202
+ for (i = 0; i < STM_NUM_SPIS; i++) {
391
+static const struct MemoryRegionOps imx7_src_ops = {
203
+ dev = DEVICE(&(s->spi[i]));
392
+ .read = imx7_src_read,
204
+ if (!sysbus_realize(SYS_BUS_DEVICE(&s->spi[i]), errp)) {
393
+ .write = imx7_src_write,
205
+ return;
394
+ .endianness = DEVICE_NATIVE_ENDIAN,
206
+ }
395
+ .valid = {
207
+ busdev = SYS_BUS_DEVICE(dev);
396
+ /*
208
+ sysbus_mmio_map(busdev, 0, spi_addr[i]);
397
+ * Our device would not work correctly if the guest was doing
209
+ sysbus_connect_irq(busdev, 0, qdev_get_gpio_in(armv7m, spi_irq[i]));
398
+ * unaligned access. This might not be a limitation on the real
210
+ }
399
+ * device but in practice there is no reason for a guest to access
211
+
400
+ * this device unaligned.
212
+ create_unimplemented_device("timer[2]", 0x40000000, 0x400);
401
+ */
213
+ create_unimplemented_device("timer[3]", 0x40000400, 0x400);
402
+ .min_access_size = 4,
214
+ create_unimplemented_device("timer[4]", 0x40000800, 0x400);
403
+ .max_access_size = 4,
215
+ create_unimplemented_device("timer[6]", 0x40001000, 0x400);
404
+ .unaligned = false,
216
+ create_unimplemented_device("timer[7]", 0x40001400, 0x400);
405
+ },
217
+ create_unimplemented_device("RTC", 0x40002800, 0x400);
218
+ create_unimplemented_device("WWDG", 0x40002C00, 0x400);
219
+ create_unimplemented_device("IWDG", 0x40003000, 0x400);
220
+ create_unimplemented_device("I2C1", 0x40005400, 0x400);
221
+ create_unimplemented_device("I2C2", 0x40005800, 0x400);
222
+ create_unimplemented_device("BKP", 0x40006C00, 0x400);
223
+ create_unimplemented_device("PWR", 0x40007000, 0x400);
224
+ create_unimplemented_device("DAC", 0x40007400, 0x400);
225
+ create_unimplemented_device("CEC", 0x40007800, 0x400);
226
+ create_unimplemented_device("AFIO", 0x40010000, 0x400);
227
+ create_unimplemented_device("EXTI", 0x40010400, 0x400);
228
+ create_unimplemented_device("GPIOA", 0x40010800, 0x400);
229
+ create_unimplemented_device("GPIOB", 0x40010C00, 0x400);
230
+ create_unimplemented_device("GPIOC", 0x40011000, 0x400);
231
+ create_unimplemented_device("GPIOD", 0x40011400, 0x400);
232
+ create_unimplemented_device("GPIOE", 0x40011800, 0x400);
233
+ create_unimplemented_device("ADC1", 0x40012400, 0x400);
234
+ create_unimplemented_device("timer[1]", 0x40012C00, 0x400);
235
+ create_unimplemented_device("timer[15]", 0x40014000, 0x400);
236
+ create_unimplemented_device("timer[16]", 0x40014400, 0x400);
237
+ create_unimplemented_device("timer[17]", 0x40014800, 0x400);
238
+ create_unimplemented_device("DMA", 0x40020000, 0x400);
239
+ create_unimplemented_device("RCC", 0x40021000, 0x400);
240
+ create_unimplemented_device("Flash Int", 0x40022000, 0x400);
241
+ create_unimplemented_device("CRC", 0x40023000, 0x400);
242
+}
243
+
244
+static Property stm32f100_soc_properties[] = {
245
+ DEFINE_PROP_STRING("cpu-type", STM32F100State, cpu_type),
246
+ DEFINE_PROP_END_OF_LIST(),
247
+};
406
+};
248
+
407
+
249
+static void stm32f100_soc_class_init(ObjectClass *klass, void *data)
408
+static void imx7_src_realize(DeviceState *dev, Error **errp)
409
+{
410
+ IMX7SRCState *s = IMX7_SRC(dev);
411
+
412
+ memory_region_init_io(&s->iomem, OBJECT(dev), &imx7_src_ops, s,
413
+ TYPE_IMX7_SRC, 0x1000);
414
+ sysbus_init_mmio(SYS_BUS_DEVICE(dev), &s->iomem);
415
+}
416
+
417
+static void imx7_src_class_init(ObjectClass *klass, void *data)
250
+{
418
+{
251
+ DeviceClass *dc = DEVICE_CLASS(klass);
419
+ DeviceClass *dc = DEVICE_CLASS(klass);
252
+
420
+
253
+ dc->realize = stm32f100_soc_realize;
421
+ dc->realize = imx7_src_realize;
254
+ device_class_set_props(dc, stm32f100_soc_properties);
422
+ dc->reset = imx7_src_reset;
255
+}
423
+ dc->vmsd = &vmstate_imx7_src;
256
+
424
+ dc->desc = "i.MX6 System Reset Controller";
257
+static const TypeInfo stm32f100_soc_info = {
425
+}
258
+ .name = TYPE_STM32F100_SOC,
426
+
427
+static const TypeInfo imx7_src_info = {
428
+ .name = TYPE_IMX7_SRC,
259
+ .parent = TYPE_SYS_BUS_DEVICE,
429
+ .parent = TYPE_SYS_BUS_DEVICE,
260
+ .instance_size = sizeof(STM32F100State),
430
+ .instance_size = sizeof(IMX7SRCState),
261
+ .instance_init = stm32f100_soc_initfn,
431
+ .class_init = imx7_src_class_init,
262
+ .class_init = stm32f100_soc_class_init,
263
+};
432
+};
264
+
433
+
265
+static void stm32f100_soc_types(void)
434
+static void imx7_src_register_types(void)
266
+{
435
+{
267
+ type_register_static(&stm32f100_soc_info);
436
+ type_register_static(&imx7_src_info);
268
+}
437
+}
269
+
438
+
270
+type_init(stm32f100_soc_types)
439
+type_init(imx7_src_register_types)
271
diff --git a/MAINTAINERS b/MAINTAINERS
440
diff --git a/hw/misc/meson.build b/hw/misc/meson.build
272
index XXXXXXX..XXXXXXX 100644
441
index XXXXXXX..XXXXXXX 100644
273
--- a/MAINTAINERS
442
--- a/hw/misc/meson.build
274
+++ b/MAINTAINERS
443
+++ b/hw/misc/meson.build
275
@@ -XXX,XX +XXX,XX @@ L: qemu-arm@nongnu.org
444
@@ -XXX,XX +XXX,XX @@ system_ss.add(when: 'CONFIG_IMX', if_true: files(
276
S: Maintained
445
'imx6_src.c',
277
F: hw/arm/virt-acpi-build.c
446
'imx6ul_ccm.c',
278
447
'imx7_ccm.c',
279
+STM32F100
448
+ 'imx7_src.c',
280
+M: Alexandre Iooss <erdnaxe@crans.org>
449
'imx7_gpr.c',
281
+L: qemu-arm@nongnu.org
450
'imx7_snvs.c',
282
+S: Maintained
451
'imx_ccm.c',
283
+F: hw/arm/stm32f100_soc.c
452
diff --git a/hw/misc/trace-events b/hw/misc/trace-events
284
+
285
STM32F205
286
M: Alistair Francis <alistair@alistair23.me>
287
M: Peter Maydell <peter.maydell@linaro.org>
288
diff --git a/hw/arm/Kconfig b/hw/arm/Kconfig
289
index XXXXXXX..XXXXXXX 100644
453
index XXXXXXX..XXXXXXX 100644
290
--- a/hw/arm/Kconfig
454
--- a/hw/misc/trace-events
291
+++ b/hw/arm/Kconfig
455
+++ b/hw/misc/trace-events
292
@@ -XXX,XX +XXX,XX @@ config RASPI
456
@@ -XXX,XX +XXX,XX @@ ccm_clock_freq(uint32_t clock, uint32_t freq) "(Clock = %d) = %d"
293
select SDHCI
457
ccm_read_reg(const char *reg_name, uint32_t value) "reg[%s] <= 0x%" PRIx32
294
select USB_DWC2
458
ccm_write_reg(const char *reg_name, uint32_t value) "reg[%s] => 0x%" PRIx32
295
459
296
+config STM32F100_SOC
460
+# imx7_src.c
297
+ bool
461
+imx7_src_read(const char *reg_name, uint32_t value) "reg[%s] => 0x%" PRIx32
298
+ select ARM_V7M
462
+imx7_src_write(const char *reg_name, uint32_t value) "reg[%s] <= 0x%" PRIx32
299
+ select STM32F2XX_USART
463
+
300
+ select STM32F2XX_SPI
464
# iotkit-sysinfo.c
301
+
465
iotkit_sysinfo_read(uint64_t offset, uint64_t data, unsigned size) "IoTKit SysInfo read: offset 0x%" PRIx64 " data 0x%" PRIx64 " size %u"
302
config STM32F205_SOC
466
iotkit_sysinfo_write(uint64_t offset, uint64_t data, unsigned size) "IoTKit SysInfo write: offset 0x%" PRIx64 " data 0x%" PRIx64 " size %u"
303
bool
304
select ARM_V7M
305
diff --git a/hw/arm/meson.build b/hw/arm/meson.build
306
index XXXXXXX..XXXXXXX 100644
307
--- a/hw/arm/meson.build
308
+++ b/hw/arm/meson.build
309
@@ -XXX,XX +XXX,XX @@ arm_ss.add(when: 'CONFIG_STRONGARM', if_true: files('strongarm.c'))
310
arm_ss.add(when: 'CONFIG_ALLWINNER_A10', if_true: files('allwinner-a10.c', 'cubieboard.c'))
311
arm_ss.add(when: 'CONFIG_ALLWINNER_H3', if_true: files('allwinner-h3.c', 'orangepi.c'))
312
arm_ss.add(when: 'CONFIG_RASPI', if_true: files('bcm2835_peripherals.c', 'bcm2836.c', 'raspi.c'))
313
+arm_ss.add(when: 'CONFIG_STM32F100_SOC', if_true: files('stm32f100_soc.c'))
314
arm_ss.add(when: 'CONFIG_STM32F205_SOC', if_true: files('stm32f205_soc.c'))
315
arm_ss.add(when: 'CONFIG_STM32F405_SOC', if_true: files('stm32f405_soc.c'))
316
arm_ss.add(when: 'CONFIG_XLNX_ZYNQMP_ARM', if_true: files('xlnx-zynqmp.c', 'xlnx-zcu102.c'))
317
--
467
--
318
2.20.1
468
2.34.1
319
320
diff view generated by jsdifflib
1
For the virt board we have two PL061 devices -- one for NonSecure which
1
The architecture requires (R_TYTWB) that an attempt to return from EL3
2
is inputs only, and one for Secure which is outputs only. For the former,
2
when SCR_EL3.{NSE,NS} are {1,0} is an illegal exception return. (This
3
we don't care whether its outputs are pulled low or high when the line is
3
enforces that the CPU can't ever be executing below EL3 with the
4
configured as an input, because we don't connect them. For the latter,
4
NSE,NS bits indicating an invalid security state.)
5
we do care, because we wire the lines up to the gpio-pwr device, which
6
assumes that level 1 means "do the action" and 1 means "do nothing".
7
For consistency in case we add more outputs in future, configure both
8
PL061s to pull GPIO lines down to 0.
9
5
10
Reported-by: Maxim Uvarov <maxim.uvarov@linaro.org>
6
We were missing this check; add it.
7
11
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
8
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
12
Reviewed-by: Richard Henderson <richard.henderson@linaro.org>
9
Reviewed-by: Richard Henderson <richard.henderson@linaro.org>
10
Message-id: 20230807150618.101357-1-peter.maydell@linaro.org
13
---
11
---
14
hw/arm/virt.c | 3 +++
12
target/arm/tcg/helper-a64.c | 9 +++++++++
15
1 file changed, 3 insertions(+)
13
1 file changed, 9 insertions(+)
16
14
17
diff --git a/hw/arm/virt.c b/hw/arm/virt.c
15
diff --git a/target/arm/tcg/helper-a64.c b/target/arm/tcg/helper-a64.c
18
index XXXXXXX..XXXXXXX 100644
16
index XXXXXXX..XXXXXXX 100644
19
--- a/hw/arm/virt.c
17
--- a/target/arm/tcg/helper-a64.c
20
+++ b/hw/arm/virt.c
18
+++ b/target/arm/tcg/helper-a64.c
21
@@ -XXX,XX +XXX,XX @@ static void create_gpio_devices(const VirtMachineState *vms, int gpio,
19
@@ -XXX,XX +XXX,XX @@ void HELPER(exception_return)(CPUARMState *env, uint64_t new_pc)
22
MachineState *ms = MACHINE(vms);
20
spsr &= ~PSTATE_SS;
23
21
}
24
pl061_dev = qdev_new("pl061");
22
25
+ /* Pull lines down to 0 if not driven by the PL061 */
23
+ /*
26
+ qdev_prop_set_uint32(pl061_dev, "pullups", 0);
24
+ * FEAT_RME forbids return from EL3 with an invalid security state.
27
+ qdev_prop_set_uint32(pl061_dev, "pulldowns", 0xff);
25
+ * We don't need an explicit check for FEAT_RME here because we enforce
28
s = SYS_BUS_DEVICE(pl061_dev);
26
+ * in scr_write() that you can't set the NSE bit without it.
29
sysbus_realize_and_unref(s, &error_fatal);
27
+ */
30
memory_region_add_subregion(mem, base, sysbus_mmio_get_region(s, 0));
28
+ if (cur_el == 3 && (env->cp15.scr_el3 & (SCR_NS | SCR_NSE)) == SCR_NSE) {
29
+ goto illegal_return;
30
+ }
31
+
32
new_el = el_from_spsr(spsr);
33
if (new_el == -1) {
34
goto illegal_return;
31
--
35
--
32
2.20.1
36
2.34.1
33
34
diff view generated by jsdifflib
1
The PL061 GPIO does not itself include pullup or pulldown resistors
1
In the m48t59 device we almost always use 64-bit arithmetic when
2
to set the value of a GPIO line treated as an output when it is
2
dealing with time_t deltas. The one exception is in set_alarm(),
3
configured as an input (ie when the PL061 itself is not driving it).
3
which currently uses a plain 'int' to hold the difference between two
4
In real hardware it is up to the board to add suitable pullups or
4
time_t values. Switch to int64_t instead to avoid any possible
5
pulldowns. Currently our implementation hardwires this to "outputs
5
overflow issues.
6
pulled high", which is correct for some boards (eg the realview ones:
7
see figure 3-29 in the "RealView Platform Baseboard for ARM926EJ-S
8
User Guide" DUI0224I), but wrong for others.
9
10
In particular, the wiring in the 'virt' board and the gpio-pwr device
11
assumes that wires should be pulled low, because otherwise the
12
pull-to-high will trigger a shutdown or reset action. (The only
13
reason this doesn't happen immediately on startup is due to another
14
bug in the PL061, where we don't assert the GPIOs to the correct
15
value on reset, but will do so as soon as the guest touches a
16
register and pl061_update() gets called.)
17
18
Add properties to the pl061 so the board can configure whether it
19
wants GPIO lines to have pullup, pulldown, or neither.
20
6
21
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
7
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
22
Reviewed-by: Richard Henderson <richard.henderson@linaro.org>
8
Reviewed-by: Philippe Mathieu-Daudé <philmd@linaro.org>
23
---
9
---
24
hw/gpio/pl061.c | 51 +++++++++++++++++++++++++++++++++++++++++++++----
10
hw/rtc/m48t59.c | 2 +-
25
1 file changed, 47 insertions(+), 4 deletions(-)
11
1 file changed, 1 insertion(+), 1 deletion(-)
26
12
27
diff --git a/hw/gpio/pl061.c b/hw/gpio/pl061.c
13
diff --git a/hw/rtc/m48t59.c b/hw/rtc/m48t59.c
28
index XXXXXXX..XXXXXXX 100644
14
index XXXXXXX..XXXXXXX 100644
29
--- a/hw/gpio/pl061.c
15
--- a/hw/rtc/m48t59.c
30
+++ b/hw/gpio/pl061.c
16
+++ b/hw/rtc/m48t59.c
31
@@ -XXX,XX +XXX,XX @@
17
@@ -XXX,XX +XXX,XX @@ static void alarm_cb (void *opaque)
32
* + unnamed GPIO inputs 0..7: inputs to connect to the emulated GPIO lines
18
33
* + unnamed GPIO outputs 0..7: the emulated GPIO lines, considered as
19
static void set_alarm(M48t59State *NVRAM)
34
* outputs
35
+ * + QOM property "pullups": an integer defining whether non-floating lines
36
+ * configured as inputs should be pulled up to logical 1 (ie whether in
37
+ * real hardware they have a pullup resistor on the line out of the PL061).
38
+ * This should be an 8-bit value, where bit 0 is 1 if GPIO line 0 should
39
+ * be pulled high, bit 1 configures line 1, and so on. The default is 0xff,
40
+ * indicating that all GPIO lines are pulled up to logical 1.
41
+ * + QOM property "pulldowns": an integer defining whether non-floating lines
42
+ * configured as inputs should be pulled down to logical 0 (ie whether in
43
+ * real hardware they have a pulldown resistor on the line out of the PL061).
44
+ * This should be an 8-bit value, where bit 0 is 1 if GPIO line 0 should
45
+ * be pulled low, bit 1 configures line 1, and so on. The default is 0x0.
46
+ * It is an error to set a bit in both "pullups" and "pulldowns". If a bit
47
+ * is 0 in both, then the line is considered to be floating, and it will
48
+ * not have qemu_set_irq() called on it when it is configured as an input.
49
*/
50
51
#include "qemu/osdep.h"
52
#include "hw/irq.h"
53
#include "hw/sysbus.h"
54
+#include "hw/qdev-properties.h"
55
#include "migration/vmstate.h"
56
+#include "qapi/error.h"
57
#include "qemu/log.h"
58
#include "qemu/module.h"
59
#include "qom/object.h"
60
@@ -XXX,XX +XXX,XX @@ struct PL061State {
61
qemu_irq irq;
62
qemu_irq out[N_GPIOS];
63
const unsigned char *id;
64
+ /* Properties, for non-Luminary PL061 */
65
+ uint32_t pullups;
66
+ uint32_t pulldowns;
67
};
68
69
static const VMStateDescription vmstate_pl061 = {
70
@@ -XXX,XX +XXX,XX @@ static uint8_t pl061_floating(PL061State *s)
71
*/
72
floating = ~(s->pur | s->pdr);
73
} else {
74
- /* Assume outputs are pulled high. FIXME: this is board dependent. */
75
- floating = 0;
76
+ floating = ~(s->pullups | s->pulldowns);
77
}
78
return floating & ~s->dir;
79
}
80
@@ -XXX,XX +XXX,XX @@ static uint8_t pl061_pullups(PL061State *s)
81
*/
82
pullups = s->pur;
83
} else {
84
- /* Assume outputs are pulled high. FIXME: this is board dependent. */
85
- pullups = 0xff;
86
+ pullups = s->pullups;
87
}
88
return pullups & ~s->dir;
89
}
90
@@ -XXX,XX +XXX,XX @@ static void pl061_init(Object *obj)
91
qdev_init_gpio_out(dev, s->out, N_GPIOS);
92
}
93
94
+static void pl061_realize(DeviceState *dev, Error **errp)
95
+{
96
+ PL061State *s = PL061(dev);
97
+
98
+ if (s->pullups > 0xff) {
99
+ error_setg(errp, "pullups property must be between 0 and 0xff");
100
+ return;
101
+ }
102
+ if (s->pulldowns > 0xff) {
103
+ error_setg(errp, "pulldowns property must be between 0 and 0xff");
104
+ return;
105
+ }
106
+ if (s->pullups & s->pulldowns) {
107
+ error_setg(errp, "no bit may be set both in pullups and pulldowns");
108
+ return;
109
+ }
110
+}
111
+
112
+static Property pl061_props[] = {
113
+ DEFINE_PROP_UINT32("pullups", PL061State, pullups, 0xff),
114
+ DEFINE_PROP_UINT32("pulldowns", PL061State, pulldowns, 0x0),
115
+ DEFINE_PROP_END_OF_LIST()
116
+};
117
+
118
static void pl061_class_init(ObjectClass *klass, void *data)
119
{
20
{
120
DeviceClass *dc = DEVICE_CLASS(klass);
21
- int diff;
121
22
+ int64_t diff;
122
dc->vmsd = &vmstate_pl061;
23
if (NVRAM->alrm_timer != NULL) {
123
dc->reset = &pl061_reset;
24
timer_del(NVRAM->alrm_timer);
124
+ dc->realize = pl061_realize;
25
diff = qemu_timedate_diff(&NVRAM->alarm) - NVRAM->time_offset;
125
+ device_class_set_props(dc, pl061_props);
126
}
127
128
static const TypeInfo pl061_info = {
129
--
26
--
130
2.20.1
27
2.34.1
131
28
132
29
diff view generated by jsdifflib
1
From: Rebecca Cran <rebecca@nuviainc.com>
1
In the twl92230 device, use int64_t for the two state fields
2
sec_offset and alm_sec, because we set these to values that
3
are either time_t or differences between two time_t values.
2
4
3
Add a space in the message printed when gicr_read*/gicr_write* returns
5
These fields aren't saved in vmstate anywhere, so we can
4
MEMTX_ERROR in arm_gicv3_redist.c.
6
safely widen them.
5
7
6
Signed-off-by: Rebecca Cran <rebecca@nuviainc.com>
7
Reviewed-by: Philippe Mathieu-Daudé <f4bug@amsat.org>
8
Message-id: 20210706211432.31902-1-rebecca@nuviainc.com
9
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
8
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
9
Reviewed-by: Philippe Mathieu-Daudé <philmd@linaro.org>
10
---
10
---
11
hw/intc/arm_gicv3_redist.c | 4 ++--
11
hw/rtc/twl92230.c | 4 ++--
12
1 file changed, 2 insertions(+), 2 deletions(-)
12
1 file changed, 2 insertions(+), 2 deletions(-)
13
13
14
diff --git a/hw/intc/arm_gicv3_redist.c b/hw/intc/arm_gicv3_redist.c
14
diff --git a/hw/rtc/twl92230.c b/hw/rtc/twl92230.c
15
index XXXXXXX..XXXXXXX 100644
15
index XXXXXXX..XXXXXXX 100644
16
--- a/hw/intc/arm_gicv3_redist.c
16
--- a/hw/rtc/twl92230.c
17
+++ b/hw/intc/arm_gicv3_redist.c
17
+++ b/hw/rtc/twl92230.c
18
@@ -XXX,XX +XXX,XX @@ MemTxResult gicv3_redist_read(void *opaque, hwaddr offset, uint64_t *data,
18
@@ -XXX,XX +XXX,XX @@ struct MenelausState {
19
if (r == MEMTX_ERROR) {
19
struct tm tm;
20
qemu_log_mask(LOG_GUEST_ERROR,
20
struct tm new;
21
"%s: invalid guest read at offset " TARGET_FMT_plx
21
struct tm alm;
22
- "size %u\n", __func__, offset, size);
22
- int sec_offset;
23
+ " size %u\n", __func__, offset, size);
23
- int alm_sec;
24
trace_gicv3_redist_badread(gicv3_redist_affid(cs), offset,
24
+ int64_t sec_offset;
25
size, attrs.secure);
25
+ int64_t alm_sec;
26
/* The spec requires that reserved registers are RAZ/WI;
26
int next_comp;
27
@@ -XXX,XX +XXX,XX @@ MemTxResult gicv3_redist_write(void *opaque, hwaddr offset, uint64_t data,
27
} rtc;
28
if (r == MEMTX_ERROR) {
28
uint16_t rtc_next_vmstate;
29
qemu_log_mask(LOG_GUEST_ERROR,
30
"%s: invalid guest write at offset " TARGET_FMT_plx
31
- "size %u\n", __func__, offset, size);
32
+ " size %u\n", __func__, offset, size);
33
trace_gicv3_redist_badwrite(gicv3_redist_affid(cs), offset, data,
34
size, attrs.secure);
35
/* The spec requires that reserved registers are RAZ/WI;
36
--
29
--
37
2.20.1
30
2.34.1
38
31
39
32
diff view generated by jsdifflib
1
The Luminary variant of the PL061 has registers GPIOPUR and GPIOPDR
1
In the aspeed_rtc device we store a difference between two time_t
2
which lets the guest configure whether the GPIO lines are pull-up,
2
values in an 'int'. This is not really correct when time_t could
3
pull-down, or truly floating. Instead of assuming all lines are pulled
3
be 64 bits. Enlarge the field to 'int64_t'.
4
high, honour the PUR and PDR registers.
5
4
6
For the plain PL061, continue to assume that lines have an external
5
This is a migration compatibility break for the aspeed boards.
7
pull-up resistor, as we did before.
6
While we are changing the vmstate, remove the accidental
8
7
duplicate of the offset field.
9
The stellaris board actually relies on this behaviour -- the CD line
10
of the ssd0323 display device is connected to GPIO output C7, and it
11
is only because of a different bug which we're about to fix that we
12
weren't incorrectly driving this line high on reset and putting the
13
ssd0323 into data mode.
14
8
15
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
9
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
16
Reviewed-by: Richard Henderson <richard.henderson@linaro.org>
10
Reviewed-by: Cédric Le Goater <clg@kaod.org>
17
---
11
---
18
hw/gpio/pl061.c | 58 +++++++++++++++++++++++++++++++++++++++++---
12
include/hw/rtc/aspeed_rtc.h | 2 +-
19
hw/gpio/trace-events | 2 +-
13
hw/rtc/aspeed_rtc.c | 5 ++---
20
2 files changed, 55 insertions(+), 5 deletions(-)
14
2 files changed, 3 insertions(+), 4 deletions(-)
21
15
22
diff --git a/hw/gpio/pl061.c b/hw/gpio/pl061.c
16
diff --git a/include/hw/rtc/aspeed_rtc.h b/include/hw/rtc/aspeed_rtc.h
23
index XXXXXXX..XXXXXXX 100644
17
index XXXXXXX..XXXXXXX 100644
24
--- a/hw/gpio/pl061.c
18
--- a/include/hw/rtc/aspeed_rtc.h
25
+++ b/hw/gpio/pl061.c
19
+++ b/include/hw/rtc/aspeed_rtc.h
26
@@ -XXX,XX +XXX,XX @@ static const VMStateDescription vmstate_pl061 = {
20
@@ -XXX,XX +XXX,XX @@ struct AspeedRtcState {
21
qemu_irq irq;
22
23
uint32_t reg[0x18];
24
- int offset;
25
+ int64_t offset;
26
27
};
28
29
diff --git a/hw/rtc/aspeed_rtc.c b/hw/rtc/aspeed_rtc.c
30
index XXXXXXX..XXXXXXX 100644
31
--- a/hw/rtc/aspeed_rtc.c
32
+++ b/hw/rtc/aspeed_rtc.c
33
@@ -XXX,XX +XXX,XX @@ static const MemoryRegionOps aspeed_rtc_ops = {
34
35
static const VMStateDescription vmstate_aspeed_rtc = {
36
.name = TYPE_ASPEED_RTC,
37
- .version_id = 1,
38
+ .version_id = 2,
39
.fields = (VMStateField[]) {
40
VMSTATE_UINT32_ARRAY(reg, AspeedRtcState, 0x18),
41
- VMSTATE_INT32(offset, AspeedRtcState),
42
- VMSTATE_INT32(offset, AspeedRtcState),
43
+ VMSTATE_INT64(offset, AspeedRtcState),
44
VMSTATE_END_OF_LIST()
27
}
45
}
28
};
46
};
29
30
+static uint8_t pl061_floating(PL061State *s)
31
+{
32
+ /*
33
+ * Return mask of bits which correspond to pins configured as inputs
34
+ * and which are floating (neither pulled up to 1 nor down to 0).
35
+ */
36
+ uint8_t floating;
37
+
38
+ if (s->id == pl061_id_luminary) {
39
+ /*
40
+ * If both PUR and PDR bits are clear, there is neither a pullup
41
+ * nor a pulldown in place, and the output truly floats.
42
+ */
43
+ floating = ~(s->pur | s->pdr);
44
+ } else {
45
+ /* Assume outputs are pulled high. FIXME: this is board dependent. */
46
+ floating = 0;
47
+ }
48
+ return floating & ~s->dir;
49
+}
50
+
51
+static uint8_t pl061_pullups(PL061State *s)
52
+{
53
+ /*
54
+ * Return mask of bits which correspond to pins configured as inputs
55
+ * and which are pulled up to 1.
56
+ */
57
+ uint8_t pullups;
58
+
59
+ if (s->id == pl061_id_luminary) {
60
+ /*
61
+ * The Luminary variant of the PL061 has an extra registers which
62
+ * the guest can use to configure whether lines should be pullup
63
+ * or pulldown.
64
+ */
65
+ pullups = s->pur;
66
+ } else {
67
+ /* Assume outputs are pulled high. FIXME: this is board dependent. */
68
+ pullups = 0xff;
69
+ }
70
+ return pullups & ~s->dir;
71
+}
72
+
73
static void pl061_update(PL061State *s)
74
{
75
uint8_t changed;
76
uint8_t mask;
77
uint8_t out;
78
int i;
79
+ uint8_t pullups = pl061_pullups(s);
80
+ uint8_t floating = pl061_floating(s);
81
82
- trace_pl061_update(DEVICE(s)->canonical_path, s->dir, s->data);
83
+ trace_pl061_update(DEVICE(s)->canonical_path, s->dir, s->data,
84
+ pullups, floating);
85
86
- /* Outputs float high. */
87
- /* FIXME: This is board dependent. */
88
- out = (s->data & s->dir) | ~s->dir;
89
+ /*
90
+ * Pins configured as output are driven from the data register;
91
+ * otherwise if they're pulled up they're 1, and if they're floating
92
+ * then we give them the same value they had previously, so we don't
93
+ * report any change to the other end.
94
+ */
95
+ out = (s->data & s->dir) | pullups | (s->old_out_data & floating);
96
changed = s->old_out_data ^ out;
97
if (changed) {
98
s->old_out_data = out;
99
diff --git a/hw/gpio/trace-events b/hw/gpio/trace-events
100
index XXXXXXX..XXXXXXX 100644
101
--- a/hw/gpio/trace-events
102
+++ b/hw/gpio/trace-events
103
@@ -XXX,XX +XXX,XX @@ nrf51_gpio_set(int64_t line, int64_t value) "line %" PRIi64 " value %" PRIi64
104
nrf51_gpio_update_output_irq(int64_t line, int64_t value) "line %" PRIi64 " value %" PRIi64
105
106
# pl061.c
107
-pl061_update(const char *id, uint32_t dir, uint32_t data) "%s GPIODIR 0x%x GPIODATA 0x%x"
108
+pl061_update(const char *id, uint32_t dir, uint32_t data, uint32_t pullups, uint32_t floating) "%s GPIODIR 0x%x GPIODATA 0x%x pullups 0x%x floating 0x%x"
109
pl061_set_output(const char *id, int gpio, int level) "%s setting output %d to %d"
110
pl061_input_change(const char *id, int gpio, int level) "%s input %d changed to %d"
111
pl061_update_istate(const char *id, uint32_t istate, uint32_t im, int level) "%s GPIORIS 0x%x GPIOIE 0x%x interrupt level %d"
112
--
47
--
113
2.20.1
48
2.34.1
114
49
115
50
diff view generated by jsdifflib
1
Add tracepoints for reads and writes to the PL061 registers. This requires
1
The functions qemu_get_timedate() and qemu_timedate_diff() take
2
restructuring pl061_read() to only return after the tracepoint, rather
2
and return a time offset as an integer. Coverity points out that
3
than having lots of early-returns.
3
means that when an RTC device implementation holds an offset
4
as a time_t, as the m48t59 does, the time_t will get truncated.
5
(CID 1507157, 1517772).
6
7
The functions work with time_t internally, so make them use that type
8
in their APIs.
9
10
Note that this won't help any Y2038 issues where either the device
11
model itself is keeping the offset in a 32-bit integer, or where the
12
hardware under emulation has Y2038 or other rollover problems. If we
13
missed any cases of the former then hopefully Coverity will warn us
14
about them since after this patch we'd be truncating a time_t in
15
assignments from qemu_timedate_diff().)
4
16
5
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
17
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
6
Reviewed-by: Philippe Mathieu-Daudé <f4bug@amsat.org>
18
Reviewed-by: Philippe Mathieu-Daudé <philmd@linaro.org>
7
Reviewed-by: Richard Henderson <richard.henderson@linaro.org>
8
---
19
---
9
hw/gpio/pl061.c | 70 ++++++++++++++++++++++++++++++--------------
20
include/sysemu/rtc.h | 4 ++--
10
hw/gpio/trace-events | 2 ++
21
softmmu/rtc.c | 4 ++--
11
2 files changed, 50 insertions(+), 22 deletions(-)
22
2 files changed, 4 insertions(+), 4 deletions(-)
12
23
13
diff --git a/hw/gpio/pl061.c b/hw/gpio/pl061.c
24
diff --git a/include/sysemu/rtc.h b/include/sysemu/rtc.h
14
index XXXXXXX..XXXXXXX 100644
25
index XXXXXXX..XXXXXXX 100644
15
--- a/hw/gpio/pl061.c
26
--- a/include/sysemu/rtc.h
16
+++ b/hw/gpio/pl061.c
27
+++ b/include/sysemu/rtc.h
17
@@ -XXX,XX +XXX,XX @@ static uint64_t pl061_read(void *opaque, hwaddr offset,
28
@@ -XXX,XX +XXX,XX @@
18
unsigned size)
29
* The behaviour of the clock whose value this function returns will
30
* depend on the -rtc command line option passed by the user.
31
*/
32
-void qemu_get_timedate(struct tm *tm, int offset);
33
+void qemu_get_timedate(struct tm *tm, time_t offset);
34
35
/**
36
* qemu_timedate_diff: Return difference between a struct tm and the RTC
37
@@ -XXX,XX +XXX,XX @@ void qemu_get_timedate(struct tm *tm, int offset);
38
* a timestamp one hour further ahead than the current RTC time
39
* then this function will return 3600.
40
*/
41
-int qemu_timedate_diff(struct tm *tm);
42
+time_t qemu_timedate_diff(struct tm *tm);
43
44
#endif
45
diff --git a/softmmu/rtc.c b/softmmu/rtc.c
46
index XXXXXXX..XXXXXXX 100644
47
--- a/softmmu/rtc.c
48
+++ b/softmmu/rtc.c
49
@@ -XXX,XX +XXX,XX @@ static time_t qemu_ref_timedate(QEMUClockType clock)
50
return value;
51
}
52
53
-void qemu_get_timedate(struct tm *tm, int offset)
54
+void qemu_get_timedate(struct tm *tm, time_t offset)
19
{
55
{
20
PL061State *s = (PL061State *)opaque;
56
time_t ti = qemu_ref_timedate(rtc_clock);
21
+ uint64_t r = 0;
57
22
58
@@ -XXX,XX +XXX,XX @@ void qemu_get_timedate(struct tm *tm, int offset)
23
switch (offset) {
24
case 0x0 ... 0x3ff: /* Data */
25
- return s->data & (offset >> 2);
26
+ r = s->data & (offset >> 2);
27
+ break;
28
case 0x400: /* Direction */
29
- return s->dir;
30
+ r = s->dir;
31
+ break;
32
case 0x404: /* Interrupt sense */
33
- return s->isense;
34
+ r = s->isense;
35
+ break;
36
case 0x408: /* Interrupt both edges */
37
- return s->ibe;
38
+ r = s->ibe;
39
+ break;
40
case 0x40c: /* Interrupt event */
41
- return s->iev;
42
+ r = s->iev;
43
+ break;
44
case 0x410: /* Interrupt mask */
45
- return s->im;
46
+ r = s->im;
47
+ break;
48
case 0x414: /* Raw interrupt status */
49
- return s->istate;
50
+ r = s->istate;
51
+ break;
52
case 0x418: /* Masked interrupt status */
53
- return s->istate & s->im;
54
+ r = s->istate & s->im;
55
+ break;
56
case 0x420: /* Alternate function select */
57
- return s->afsel;
58
+ r = s->afsel;
59
+ break;
60
case 0x500: /* 2mA drive */
61
if (s->id != pl061_id_luminary) {
62
goto bad_offset;
63
}
64
- return s->dr2r;
65
+ r = s->dr2r;
66
+ break;
67
case 0x504: /* 4mA drive */
68
if (s->id != pl061_id_luminary) {
69
goto bad_offset;
70
}
71
- return s->dr4r;
72
+ r = s->dr4r;
73
+ break;
74
case 0x508: /* 8mA drive */
75
if (s->id != pl061_id_luminary) {
76
goto bad_offset;
77
}
78
- return s->dr8r;
79
+ r = s->dr8r;
80
+ break;
81
case 0x50c: /* Open drain */
82
if (s->id != pl061_id_luminary) {
83
goto bad_offset;
84
}
85
- return s->odr;
86
+ r = s->odr;
87
+ break;
88
case 0x510: /* Pull-up */
89
if (s->id != pl061_id_luminary) {
90
goto bad_offset;
91
}
92
- return s->pur;
93
+ r = s->pur;
94
+ break;
95
case 0x514: /* Pull-down */
96
if (s->id != pl061_id_luminary) {
97
goto bad_offset;
98
}
99
- return s->pdr;
100
+ r = s->pdr;
101
+ break;
102
case 0x518: /* Slew rate control */
103
if (s->id != pl061_id_luminary) {
104
goto bad_offset;
105
}
106
- return s->slr;
107
+ r = s->slr;
108
+ break;
109
case 0x51c: /* Digital enable */
110
if (s->id != pl061_id_luminary) {
111
goto bad_offset;
112
}
113
- return s->den;
114
+ r = s->den;
115
+ break;
116
case 0x520: /* Lock */
117
if (s->id != pl061_id_luminary) {
118
goto bad_offset;
119
}
120
- return s->locked;
121
+ r = s->locked;
122
+ break;
123
case 0x524: /* Commit */
124
if (s->id != pl061_id_luminary) {
125
goto bad_offset;
126
}
127
- return s->cr;
128
+ r = s->cr;
129
+ break;
130
case 0x528: /* Analog mode select */
131
if (s->id != pl061_id_luminary) {
132
goto bad_offset;
133
}
134
- return s->amsel;
135
+ r = s->amsel;
136
+ break;
137
case 0xfd0 ... 0xfff: /* ID registers */
138
- return s->id[(offset - 0xfd0) >> 2];
139
+ r = s->id[(offset - 0xfd0) >> 2];
140
+ break;
141
default:
142
bad_offset:
143
qemu_log_mask(LOG_GUEST_ERROR,
144
"pl061_read: Bad offset %x\n", (int)offset);
145
break;
146
}
59
}
147
- return 0;
148
+
149
+ trace_pl061_read(DEVICE(s)->canonical_path, offset, r);
150
+ return r;
151
}
60
}
152
61
153
static void pl061_write(void *opaque, hwaddr offset,
62
-int qemu_timedate_diff(struct tm *tm)
154
@@ -XXX,XX +XXX,XX @@ static void pl061_write(void *opaque, hwaddr offset,
63
+time_t qemu_timedate_diff(struct tm *tm)
155
PL061State *s = (PL061State *)opaque;
64
{
156
uint8_t mask;
65
time_t seconds;
157
66
158
+ trace_pl061_write(DEVICE(s)->canonical_path, offset, value);
159
+
160
switch (offset) {
161
case 0 ... 0x3ff:
162
mask = (offset >> 2) & s->dir;
163
diff --git a/hw/gpio/trace-events b/hw/gpio/trace-events
164
index XXXXXXX..XXXXXXX 100644
165
--- a/hw/gpio/trace-events
166
+++ b/hw/gpio/trace-events
167
@@ -XXX,XX +XXX,XX @@ pl061_update(const char *id, uint32_t dir, uint32_t data) "%s GPIODIR 0x%x GPIOD
168
pl061_set_output(const char *id, int gpio, int level) "%s setting output %d to %d"
169
pl061_input_change(const char *id, int gpio, int level) "%s input %d changed to %d"
170
pl061_update_istate(const char *id, uint32_t istate, uint32_t im, int level) "%s GPIORIS 0x%x GPIOIE 0x%x interrupt level %d"
171
+pl061_read(const char *id, uint64_t offset, uint64_t r) "%s offset 0x%" PRIx64 " value 0x%" PRIx64
172
+pl061_write(const char *id, uint64_t offset, uint64_t value) "%s offset 0x%" PRIx64 " value 0x%" PRIx64
173
174
# sifive_gpio.c
175
sifive_gpio_read(uint64_t offset, uint64_t r) "offset 0x%" PRIx64 " value 0x%" PRIx64
176
--
67
--
177
2.20.1
68
2.34.1
178
69
179
70
diff view generated by jsdifflib
1
Add a comment documenting the "QEMU interface" of this device:
1
Where architecturally one ARM_FEATURE_X flag implies another
2
which MMIO regions, IRQ lines, GPIO lines, etc it exposes.
2
ARM_FEATURE_Y, we allow the CPU init function to only set X, and then
3
set Y for it. Currently we do this in two places -- we set a few
4
flags in arm_cpu_post_init() because we need them to decide which
5
properties to create on the CPU object, and then we do the rest in
6
arm_cpu_realizefn(). However, this is fragile, because it's easy to
7
add a new property and not notice that this means that an X-implies-Y
8
check now has to move from realize to post-init.
9
10
As a specific example, the pmsav7-dregion property is conditional
11
on ARM_FEATURE_PMSA && ARM_FEATURE_V7, which means it won't appear
12
on the Cortex-M33 and -M55, because they set ARM_FEATURE_V8 and
13
rely on V8-implies-V7, which doesn't happen until the realizefn.
14
15
Move all of these X-implies-Y checks into a new function, which
16
we call at the top of arm_cpu_post_init(), so the feature bits
17
are available at that point.
18
19
This does now give us the reverse issue, that if there's a feature
20
bit which is enabled or disabled by the setting of a property then
21
then X-implies-Y features that are dependent on that property need to
22
be in realize, not in this new function. But the only one of those
23
is the "EL3 implies VBAR" which is already in the right place, so
24
putting things this way round seems better to me.
3
25
4
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
26
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
5
Reviewed-by: Richard Henderson <richard.henderson@linaro.org>
27
Reviewed-by: Richard Henderson <richard.henderson@linaro.org>
28
Message-id: 20230724174335.2150499-2-peter.maydell@linaro.org
6
---
29
---
7
hw/gpio/pl061.c | 7 +++++++
30
target/arm/cpu.c | 179 +++++++++++++++++++++++++----------------------
8
1 file changed, 7 insertions(+)
31
1 file changed, 97 insertions(+), 82 deletions(-)
9
32
10
diff --git a/hw/gpio/pl061.c b/hw/gpio/pl061.c
33
diff --git a/target/arm/cpu.c b/target/arm/cpu.c
11
index XXXXXXX..XXXXXXX 100644
34
index XXXXXXX..XXXXXXX 100644
12
--- a/hw/gpio/pl061.c
35
--- a/target/arm/cpu.c
13
+++ b/hw/gpio/pl061.c
36
+++ b/target/arm/cpu.c
14
@@ -XXX,XX +XXX,XX @@
37
@@ -XXX,XX +XXX,XX @@ unsigned int gt_cntfrq_period_ns(ARMCPU *cpu)
15
* Written by Paul Brook
38
NANOSECONDS_PER_SECOND / cpu->gt_cntfrq_hz : 1;
16
*
39
}
17
* This code is licensed under the GPL.
40
18
+ *
41
+static void arm_cpu_propagate_feature_implications(ARMCPU *cpu)
19
+ * QEMU interface:
42
+{
20
+ * + sysbus MMIO region 0: the device registers
43
+ CPUARMState *env = &cpu->env;
21
+ * + sysbus IRQ: the GPIOINTR interrupt line
44
+ bool no_aa32 = false;
22
+ * + unnamed GPIO inputs 0..7: inputs to connect to the emulated GPIO lines
45
+
23
+ * + unnamed GPIO outputs 0..7: the emulated GPIO lines, considered as
46
+ /*
24
+ * outputs
47
+ * Some features automatically imply others: set the feature
25
*/
48
+ * bits explicitly for these cases.
26
49
+ */
27
#include "qemu/osdep.h"
50
+
51
+ if (arm_feature(env, ARM_FEATURE_M)) {
52
+ set_feature(env, ARM_FEATURE_PMSA);
53
+ }
54
+
55
+ if (arm_feature(env, ARM_FEATURE_V8)) {
56
+ if (arm_feature(env, ARM_FEATURE_M)) {
57
+ set_feature(env, ARM_FEATURE_V7);
58
+ } else {
59
+ set_feature(env, ARM_FEATURE_V7VE);
60
+ }
61
+ }
62
+
63
+ /*
64
+ * There exist AArch64 cpus without AArch32 support. When KVM
65
+ * queries ID_ISAR0_EL1 on such a host, the value is UNKNOWN.
66
+ * Similarly, we cannot check ID_AA64PFR0 without AArch64 support.
67
+ * As a general principle, we also do not make ID register
68
+ * consistency checks anywhere unless using TCG, because only
69
+ * for TCG would a consistency-check failure be a QEMU bug.
70
+ */
71
+ if (arm_feature(&cpu->env, ARM_FEATURE_AARCH64)) {
72
+ no_aa32 = !cpu_isar_feature(aa64_aa32, cpu);
73
+ }
74
+
75
+ if (arm_feature(env, ARM_FEATURE_V7VE)) {
76
+ /*
77
+ * v7 Virtualization Extensions. In real hardware this implies
78
+ * EL2 and also the presence of the Security Extensions.
79
+ * For QEMU, for backwards-compatibility we implement some
80
+ * CPUs or CPU configs which have no actual EL2 or EL3 but do
81
+ * include the various other features that V7VE implies.
82
+ * Presence of EL2 itself is ARM_FEATURE_EL2, and of the
83
+ * Security Extensions is ARM_FEATURE_EL3.
84
+ */
85
+ assert(!tcg_enabled() || no_aa32 ||
86
+ cpu_isar_feature(aa32_arm_div, cpu));
87
+ set_feature(env, ARM_FEATURE_LPAE);
88
+ set_feature(env, ARM_FEATURE_V7);
89
+ }
90
+ if (arm_feature(env, ARM_FEATURE_V7)) {
91
+ set_feature(env, ARM_FEATURE_VAPA);
92
+ set_feature(env, ARM_FEATURE_THUMB2);
93
+ set_feature(env, ARM_FEATURE_MPIDR);
94
+ if (!arm_feature(env, ARM_FEATURE_M)) {
95
+ set_feature(env, ARM_FEATURE_V6K);
96
+ } else {
97
+ set_feature(env, ARM_FEATURE_V6);
98
+ }
99
+
100
+ /*
101
+ * Always define VBAR for V7 CPUs even if it doesn't exist in
102
+ * non-EL3 configs. This is needed by some legacy boards.
103
+ */
104
+ set_feature(env, ARM_FEATURE_VBAR);
105
+ }
106
+ if (arm_feature(env, ARM_FEATURE_V6K)) {
107
+ set_feature(env, ARM_FEATURE_V6);
108
+ set_feature(env, ARM_FEATURE_MVFR);
109
+ }
110
+ if (arm_feature(env, ARM_FEATURE_V6)) {
111
+ set_feature(env, ARM_FEATURE_V5);
112
+ if (!arm_feature(env, ARM_FEATURE_M)) {
113
+ assert(!tcg_enabled() || no_aa32 ||
114
+ cpu_isar_feature(aa32_jazelle, cpu));
115
+ set_feature(env, ARM_FEATURE_AUXCR);
116
+ }
117
+ }
118
+ if (arm_feature(env, ARM_FEATURE_V5)) {
119
+ set_feature(env, ARM_FEATURE_V4T);
120
+ }
121
+ if (arm_feature(env, ARM_FEATURE_LPAE)) {
122
+ set_feature(env, ARM_FEATURE_V7MP);
123
+ }
124
+ if (arm_feature(env, ARM_FEATURE_CBAR_RO)) {
125
+ set_feature(env, ARM_FEATURE_CBAR);
126
+ }
127
+ if (arm_feature(env, ARM_FEATURE_THUMB2) &&
128
+ !arm_feature(env, ARM_FEATURE_M)) {
129
+ set_feature(env, ARM_FEATURE_THUMB_DSP);
130
+ }
131
+}
132
+
133
void arm_cpu_post_init(Object *obj)
134
{
135
ARMCPU *cpu = ARM_CPU(obj);
136
137
- /* M profile implies PMSA. We have to do this here rather than
138
- * in realize with the other feature-implication checks because
139
- * we look at the PMSA bit to see if we should add some properties.
140
+ /*
141
+ * Some features imply others. Figure this out now, because we
142
+ * are going to look at the feature bits in deciding which
143
+ * properties to add.
144
*/
145
- if (arm_feature(&cpu->env, ARM_FEATURE_M)) {
146
- set_feature(&cpu->env, ARM_FEATURE_PMSA);
147
- }
148
+ arm_cpu_propagate_feature_implications(cpu);
149
150
if (arm_feature(&cpu->env, ARM_FEATURE_CBAR) ||
151
arm_feature(&cpu->env, ARM_FEATURE_CBAR_RO)) {
152
@@ -XXX,XX +XXX,XX @@ static void arm_cpu_realizefn(DeviceState *dev, Error **errp)
153
CPUARMState *env = &cpu->env;
154
int pagebits;
155
Error *local_err = NULL;
156
- bool no_aa32 = false;
157
158
/* Use pc-relative instructions in system-mode */
159
#ifndef CONFIG_USER_ONLY
160
@@ -XXX,XX +XXX,XX @@ static void arm_cpu_realizefn(DeviceState *dev, Error **errp)
161
cpu->isar.id_isar3 = u;
162
}
163
164
- /* Some features automatically imply others: */
165
- if (arm_feature(env, ARM_FEATURE_V8)) {
166
- if (arm_feature(env, ARM_FEATURE_M)) {
167
- set_feature(env, ARM_FEATURE_V7);
168
- } else {
169
- set_feature(env, ARM_FEATURE_V7VE);
170
- }
171
- }
172
-
173
- /*
174
- * There exist AArch64 cpus without AArch32 support. When KVM
175
- * queries ID_ISAR0_EL1 on such a host, the value is UNKNOWN.
176
- * Similarly, we cannot check ID_AA64PFR0 without AArch64 support.
177
- * As a general principle, we also do not make ID register
178
- * consistency checks anywhere unless using TCG, because only
179
- * for TCG would a consistency-check failure be a QEMU bug.
180
- */
181
- if (arm_feature(&cpu->env, ARM_FEATURE_AARCH64)) {
182
- no_aa32 = !cpu_isar_feature(aa64_aa32, cpu);
183
- }
184
-
185
- if (arm_feature(env, ARM_FEATURE_V7VE)) {
186
- /* v7 Virtualization Extensions. In real hardware this implies
187
- * EL2 and also the presence of the Security Extensions.
188
- * For QEMU, for backwards-compatibility we implement some
189
- * CPUs or CPU configs which have no actual EL2 or EL3 but do
190
- * include the various other features that V7VE implies.
191
- * Presence of EL2 itself is ARM_FEATURE_EL2, and of the
192
- * Security Extensions is ARM_FEATURE_EL3.
193
- */
194
- assert(!tcg_enabled() || no_aa32 ||
195
- cpu_isar_feature(aa32_arm_div, cpu));
196
- set_feature(env, ARM_FEATURE_LPAE);
197
- set_feature(env, ARM_FEATURE_V7);
198
- }
199
- if (arm_feature(env, ARM_FEATURE_V7)) {
200
- set_feature(env, ARM_FEATURE_VAPA);
201
- set_feature(env, ARM_FEATURE_THUMB2);
202
- set_feature(env, ARM_FEATURE_MPIDR);
203
- if (!arm_feature(env, ARM_FEATURE_M)) {
204
- set_feature(env, ARM_FEATURE_V6K);
205
- } else {
206
- set_feature(env, ARM_FEATURE_V6);
207
- }
208
-
209
- /* Always define VBAR for V7 CPUs even if it doesn't exist in
210
- * non-EL3 configs. This is needed by some legacy boards.
211
- */
212
- set_feature(env, ARM_FEATURE_VBAR);
213
- }
214
- if (arm_feature(env, ARM_FEATURE_V6K)) {
215
- set_feature(env, ARM_FEATURE_V6);
216
- set_feature(env, ARM_FEATURE_MVFR);
217
- }
218
- if (arm_feature(env, ARM_FEATURE_V6)) {
219
- set_feature(env, ARM_FEATURE_V5);
220
- if (!arm_feature(env, ARM_FEATURE_M)) {
221
- assert(!tcg_enabled() || no_aa32 ||
222
- cpu_isar_feature(aa32_jazelle, cpu));
223
- set_feature(env, ARM_FEATURE_AUXCR);
224
- }
225
- }
226
- if (arm_feature(env, ARM_FEATURE_V5)) {
227
- set_feature(env, ARM_FEATURE_V4T);
228
- }
229
- if (arm_feature(env, ARM_FEATURE_LPAE)) {
230
- set_feature(env, ARM_FEATURE_V7MP);
231
- }
232
- if (arm_feature(env, ARM_FEATURE_CBAR_RO)) {
233
- set_feature(env, ARM_FEATURE_CBAR);
234
- }
235
- if (arm_feature(env, ARM_FEATURE_THUMB2) &&
236
- !arm_feature(env, ARM_FEATURE_M)) {
237
- set_feature(env, ARM_FEATURE_THUMB_DSP);
238
- }
239
240
/*
241
* We rely on no XScale CPU having VFP so we can use the same bits in the
28
--
242
--
29
2.20.1
243
2.34.1
30
31
diff view generated by jsdifflib
1
Convert the use of the DPRINTF debug macro in the PL061 model to
1
M-profile CPUs generally allow configuration of the number of MPU
2
use tracepoints.
2
regions that they have. We don't currently model this, so our
3
implementations of some of the board models provide CPUs with the
4
wrong number of regions. RTOSes like Zephyr that hardcode the
5
expected number of regions may therefore not run on the model if they
6
are set up to run on real hardware.
7
8
Add properties mpu-ns-regions and mpu-s-regions to the ARMV7M object,
9
matching the ability of hardware to configure the number of Secure
10
and NonSecure regions separately. Our actual CPU implementation
11
doesn't currently support that, and it happens that none of the MPS
12
boards we model set the number of regions differently for Secure vs
13
NonSecure, so we provide an interface to the boards and SoCs that
14
won't need to change if we ever do add that functionality in future,
15
but make it an error to configure the two properties to different
16
values.
17
18
(The property name on the CPU is the somewhat misnamed-for-M-profile
19
"pmsav7-dregion", so we don't follow that naming convention for
20
the properties here. The TRM doesn't say what the CPU configuration
21
variable names are, so we pick something, and follow the lowercase
22
convention we already have for properties here.)
3
23
4
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
24
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
5
Reviewed-by: Philippe Mathieu-Daudé <f4bug@amsat.org>
25
Reviewed-by: Philippe Mathieu-Daudé <philmd@linaro.org>
6
Reviewed-by: Richard Henderson <richard.henderson@linaro.org>
26
Message-id: 20230724174335.2150499-3-peter.maydell@linaro.org
7
---
27
---
8
hw/gpio/pl061.c | 27 +++++++++------------------
28
include/hw/arm/armv7m.h | 8 ++++++++
9
hw/gpio/trace-events | 6 ++++++
29
hw/arm/armv7m.c | 21 +++++++++++++++++++++
10
2 files changed, 15 insertions(+), 18 deletions(-)
30
2 files changed, 29 insertions(+)
11
31
12
diff --git a/hw/gpio/pl061.c b/hw/gpio/pl061.c
32
diff --git a/include/hw/arm/armv7m.h b/include/hw/arm/armv7m.h
13
index XXXXXXX..XXXXXXX 100644
33
index XXXXXXX..XXXXXXX 100644
14
--- a/hw/gpio/pl061.c
34
--- a/include/hw/arm/armv7m.h
15
+++ b/hw/gpio/pl061.c
35
+++ b/include/hw/arm/armv7m.h
16
@@ -XXX,XX +XXX,XX @@
36
@@ -XXX,XX +XXX,XX @@ OBJECT_DECLARE_SIMPLE_TYPE(ARMv7MState, ARMV7M)
17
#include "qemu/log.h"
37
* + Property "vfp": enable VFP (forwarded to CPU object)
18
#include "qemu/module.h"
38
* + Property "dsp": enable DSP (forwarded to CPU object)
19
#include "qom/object.h"
39
* + Property "enable-bitband": expose bitbanded IO
20
-
40
+ * + Property "mpu-ns-regions": number of Non-Secure MPU regions (forwarded
21
-//#define DEBUG_PL061 1
41
+ * to CPU object pmsav7-dregion property; default is whatever the default
22
-
42
+ * for the CPU is)
23
-#ifdef DEBUG_PL061
43
+ * + Property "mpu-s-regions": number of Secure MPU regions (default is
24
-#define DPRINTF(fmt, ...) \
44
+ * whatever the default for the CPU is; must currently be set to the same
25
-do { printf("pl061: " fmt , ## __VA_ARGS__); } while (0)
45
+ * value as mpu-ns-regions if the CPU implements the Security Extension)
26
-#define BADF(fmt, ...) \
46
* + Clock input "refclk" is the external reference clock for the systick timers
27
-do { fprintf(stderr, "pl061: error: " fmt , ## __VA_ARGS__); exit(1);} while (0)
47
* + Clock input "cpuclk" is the main CPU clock
28
-#else
48
*/
29
-#define DPRINTF(fmt, ...) do {} while(0)
49
@@ -XXX,XX +XXX,XX @@ struct ARMv7MState {
30
-#define BADF(fmt, ...) \
50
Object *idau;
31
-do { fprintf(stderr, "pl061: error: " fmt , ## __VA_ARGS__);} while (0)
51
uint32_t init_svtor;
32
-#endif
52
uint32_t init_nsvtor;
33
+#include "trace.h"
53
+ uint32_t mpu_ns_regions;
34
54
+ uint32_t mpu_s_regions;
35
static const uint8_t pl061_id[12] =
55
bool enable_bitband;
36
{ 0x00, 0x00, 0x00, 0x00, 0x61, 0x10, 0x04, 0x00, 0x0d, 0xf0, 0x05, 0xb1 };
56
bool start_powered_off;
37
@@ -XXX,XX +XXX,XX @@ static void pl061_update(PL061State *s)
57
bool vfp;
38
uint8_t out;
58
diff --git a/hw/arm/armv7m.c b/hw/arm/armv7m.c
39
int i;
59
index XXXXXXX..XXXXXXX 100644
40
60
--- a/hw/arm/armv7m.c
41
- DPRINTF("dir = %d, data = %d\n", s->dir, s->data);
61
+++ b/hw/arm/armv7m.c
42
+ trace_pl061_update(DEVICE(s)->canonical_path, s->dir, s->data);
62
@@ -XXX,XX +XXX,XX @@ static void armv7m_realize(DeviceState *dev, Error **errp)
43
44
/* Outputs float high. */
45
/* FIXME: This is board dependent. */
46
@@ -XXX,XX +XXX,XX @@ static void pl061_update(PL061State *s)
47
for (i = 0; i < N_GPIOS; i++) {
48
mask = 1 << i;
49
if (changed & mask) {
50
- DPRINTF("Set output %d = %d\n", i, (out & mask) != 0);
51
- qemu_set_irq(s->out[i], (out & mask) != 0);
52
+ int level = (out & mask) != 0;
53
+ trace_pl061_set_output(DEVICE(s)->canonical_path, i, level);
54
+ qemu_set_irq(s->out[i], level);
55
}
56
}
63
}
57
}
64
}
58
@@ -XXX,XX +XXX,XX @@ static void pl061_update(PL061State *s)
65
59
for (i = 0; i < N_GPIOS; i++) {
66
+ /*
60
mask = 1 << i;
67
+ * Real M-profile hardware can be configured with a different number of
61
if (changed & mask) {
68
+ * MPU regions for Secure vs NonSecure. QEMU's CPU implementation doesn't
62
- DPRINTF("Changed input %d = %d\n", i, (s->data & mask) != 0);
69
+ * support that yet, so catch attempts to select that.
63
+ trace_pl061_input_change(DEVICE(s)->canonical_path, i,
70
+ */
64
+ (s->data & mask) != 0);
71
+ if (arm_feature(&s->cpu->env, ARM_FEATURE_M_SECURITY) &&
65
72
+ s->mpu_ns_regions != s->mpu_s_regions) {
66
if (!(s->isense & mask)) {
73
+ error_setg(errp,
67
/* Edge interrupt */
74
+ "mpu-ns-regions and mpu-s-regions properties must have the same value");
68
@@ -XXX,XX +XXX,XX @@ static void pl061_update(PL061State *s)
75
+ return;
69
/* Level interrupt */
76
+ }
70
s->istate |= ~(s->data ^ s->iev) & s->isense;
77
+ if (s->mpu_ns_regions != UINT_MAX &&
71
78
+ object_property_find(OBJECT(s->cpu), "pmsav7-dregion")) {
72
- DPRINTF("istate = %02X\n", s->istate);
79
+ if (!object_property_set_uint(OBJECT(s->cpu), "pmsav7-dregion",
73
+ trace_pl061_update_istate(DEVICE(s)->canonical_path,
80
+ s->mpu_ns_regions, errp)) {
74
+ s->istate, s->im, (s->istate & s->im) != 0);
81
+ return;
75
82
+ }
76
qemu_set_irq(s->irq, (s->istate & s->im) != 0);
83
+ }
77
}
78
diff --git a/hw/gpio/trace-events b/hw/gpio/trace-events
79
index XXXXXXX..XXXXXXX 100644
80
--- a/hw/gpio/trace-events
81
+++ b/hw/gpio/trace-events
82
@@ -XXX,XX +XXX,XX @@ nrf51_gpio_write(uint64_t offset, uint64_t value) "offset 0x%" PRIx64 " value 0x
83
nrf51_gpio_set(int64_t line, int64_t value) "line %" PRIi64 " value %" PRIi64
84
nrf51_gpio_update_output_irq(int64_t line, int64_t value) "line %" PRIi64 " value %" PRIi64
85
86
+# pl061.c
87
+pl061_update(const char *id, uint32_t dir, uint32_t data) "%s GPIODIR 0x%x GPIODATA 0x%x"
88
+pl061_set_output(const char *id, int gpio, int level) "%s setting output %d to %d"
89
+pl061_input_change(const char *id, int gpio, int level) "%s input %d changed to %d"
90
+pl061_update_istate(const char *id, uint32_t istate, uint32_t im, int level) "%s GPIORIS 0x%x GPIOIE 0x%x interrupt level %d"
91
+
84
+
92
# sifive_gpio.c
85
/*
93
sifive_gpio_read(uint64_t offset, uint64_t r) "offset 0x%" PRIx64 " value 0x%" PRIx64
86
* Tell the CPU where the NVIC is; it will fail realize if it doesn't
94
sifive_gpio_write(uint64_t offset, uint64_t value) "offset 0x%" PRIx64 " value 0x%" PRIx64
87
* have one. Similarly, tell the NVIC where its CPU is.
88
@@ -XXX,XX +XXX,XX @@ static Property armv7m_properties[] = {
89
false),
90
DEFINE_PROP_BOOL("vfp", ARMv7MState, vfp, true),
91
DEFINE_PROP_BOOL("dsp", ARMv7MState, dsp, true),
92
+ DEFINE_PROP_UINT32("mpu-ns-regions", ARMv7MState, mpu_ns_regions, UINT_MAX),
93
+ DEFINE_PROP_UINT32("mpu-s-regions", ARMv7MState, mpu_s_regions, UINT_MAX),
94
DEFINE_PROP_END_OF_LIST(),
95
};
96
95
--
97
--
96
2.20.1
98
2.34.1
97
99
98
100
diff view generated by jsdifflib
1
Currently the pl061_read() and pl061_write() functions handle offsets
1
The IoTKit, SSE200 and SSE300 all default to 8 MPU regions. The
2
using a combination of three if() statements and a switch(). Clean
2
MPS2/MPS3 FPGA images don't override these except in the case of
3
this up to use just a switch, using case ranges.
3
AN547, which uses 16 MPU regions.
4
4
5
This requires that instead of catching accesses to the luminary-only
5
Define properties on the ARMSSE object for the MPU regions (using the
6
registers on a stock PL061 via a check on s->rsvd_start we use
6
same names as the documented RTL configuration settings, and
7
an "is this luminary?" check in the cases for each luminary-only
7
following the pattern we already have for this device of using
8
register.
8
all-caps names as the RTL does), and set them in the board code.
9
9
10
We don't actually need to override the default except on AN547,
11
but it's simpler code to have the board code set them always
12
rather than tracking which board subtypes want to set them to
13
a non-default value separately from what that value is.
14
15
Tho overall effect is that for mps2-an505, mps2-an521 and mps3-an524
16
we now correctly use 8 MPU regions, while mps3-an547 stays at its
17
current 16 regions.
18
19
It's possible some guest code wrongly depended on the previous
20
incorrectly modeled number of memory regions. (Such guest code
21
should ideally check the number of regions via the MPU_TYPE
22
register.) The old behaviour can be obtained with additional
23
-global arguments to QEMU:
24
25
For mps2-an521 and mps2-an524:
26
-global sse-200.CPU0_MPU_NS=16 -global sse-200.CPU0_MPU_S=16 -global sse-200.CPU1_MPU_NS=16 -global sse-200.CPU1_MPU_S=16
27
28
For mps2-an505:
29
-global sse-200.CPU0_MPU_NS=16 -global sse-200.CPU0_MPU_S=16
30
31
NB that the way the implementation allows this use of -global
32
is slightly fragile: if the board code explicitly sets the
33
properties on the sse-200 object, this overrides the -global
34
command line option. So we rely on:
35
- the boards that need fixing all happen to use the SSE defaults
36
- we can write the board code to only set the property if it
37
is different from the default, rather than having all boards
38
explicitly set the property
39
- the board that does need to use a non-default value happens
40
to need to set it to the same value (16) we previously used
41
This works, but there are some kinds of refactoring of the
42
mps2-tz.c code that would break the support for -global here.
43
44
Resolves: https://gitlab.com/qemu-project/qemu/-/issues/1772
10
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
45
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
11
Reviewed-by: Richard Henderson <richard.henderson@linaro.org>
46
Reviewed-by: Richard Henderson <richard.henderson@linaro.org>
47
Reviewed-by: Philippe Mathieu-Daudé <philmd@linaro.org>
48
Message-id: 20230724174335.2150499-4-peter.maydell@linaro.org
12
---
49
---
13
hw/gpio/pl061.c | 104 ++++++++++++++++++++++++++++++++++++------------
50
include/hw/arm/armsse.h | 5 +++++
14
1 file changed, 79 insertions(+), 25 deletions(-)
51
hw/arm/armsse.c | 16 ++++++++++++++++
15
52
hw/arm/mps2-tz.c | 29 +++++++++++++++++++++++++++++
16
diff --git a/hw/gpio/pl061.c b/hw/gpio/pl061.c
53
3 files changed, 50 insertions(+)
54
55
diff --git a/include/hw/arm/armsse.h b/include/hw/arm/armsse.h
17
index XXXXXXX..XXXXXXX 100644
56
index XXXXXXX..XXXXXXX 100644
18
--- a/hw/gpio/pl061.c
57
--- a/include/hw/arm/armsse.h
19
+++ b/hw/gpio/pl061.c
58
+++ b/include/hw/arm/armsse.h
20
@@ -XXX,XX +XXX,XX @@ struct PL061State {
59
@@ -XXX,XX +XXX,XX @@
21
qemu_irq irq;
60
* (matching the hardware) is that for CPU0 in an IoTKit and CPU1 in an
22
qemu_irq out[N_GPIOS];
61
* SSE-200 both are present; CPU0 in an SSE-200 has neither.
23
const unsigned char *id;
62
* Since the IoTKit has only one CPU, it does not have the CPU1_* properties.
24
- uint32_t rsvd_start; /* reserved area: [rsvd_start, 0xfcc] */
63
+ * + QOM properties "CPU0_MPU_NS", "CPU0_MPU_S", "CPU1_MPU_NS" and "CPU1_MPU_S"
25
};
64
+ * which set the number of MPU regions on the CPUs. If there is only one
26
65
+ * CPU the CPU1 properties are not present.
27
static const VMStateDescription vmstate_pl061 = {
66
* + Named GPIO inputs "EXP_IRQ" 0..n are the expansion interrupts for CPU 0,
28
@@ -XXX,XX +XXX,XX @@ static uint64_t pl061_read(void *opaque, hwaddr offset,
67
* which are wired to its NVIC lines 32 .. n+32
68
* + Named GPIO inputs "EXP_CPU1_IRQ" 0..n are the expansion interrupts for
69
@@ -XXX,XX +XXX,XX @@ struct ARMSSE {
70
uint32_t exp_numirq;
71
uint32_t sram_addr_width;
72
uint32_t init_svtor;
73
+ uint32_t cpu_mpu_ns[SSE_MAX_CPUS];
74
+ uint32_t cpu_mpu_s[SSE_MAX_CPUS];
75
bool cpu_fpu[SSE_MAX_CPUS];
76
bool cpu_dsp[SSE_MAX_CPUS];
77
};
78
diff --git a/hw/arm/armsse.c b/hw/arm/armsse.c
79
index XXXXXXX..XXXXXXX 100644
80
--- a/hw/arm/armsse.c
81
+++ b/hw/arm/armsse.c
82
@@ -XXX,XX +XXX,XX @@ static Property iotkit_properties[] = {
83
DEFINE_PROP_UINT32("init-svtor", ARMSSE, init_svtor, 0x10000000),
84
DEFINE_PROP_BOOL("CPU0_FPU", ARMSSE, cpu_fpu[0], true),
85
DEFINE_PROP_BOOL("CPU0_DSP", ARMSSE, cpu_dsp[0], true),
86
+ DEFINE_PROP_UINT32("CPU0_MPU_NS", ARMSSE, cpu_mpu_ns[0], 8),
87
+ DEFINE_PROP_UINT32("CPU0_MPU_S", ARMSSE, cpu_mpu_s[0], 8),
88
DEFINE_PROP_END_OF_LIST()
89
};
90
91
@@ -XXX,XX +XXX,XX @@ static Property sse200_properties[] = {
92
DEFINE_PROP_BOOL("CPU0_DSP", ARMSSE, cpu_dsp[0], false),
93
DEFINE_PROP_BOOL("CPU1_FPU", ARMSSE, cpu_fpu[1], true),
94
DEFINE_PROP_BOOL("CPU1_DSP", ARMSSE, cpu_dsp[1], true),
95
+ DEFINE_PROP_UINT32("CPU0_MPU_NS", ARMSSE, cpu_mpu_ns[0], 8),
96
+ DEFINE_PROP_UINT32("CPU0_MPU_S", ARMSSE, cpu_mpu_s[0], 8),
97
+ DEFINE_PROP_UINT32("CPU1_MPU_NS", ARMSSE, cpu_mpu_ns[1], 8),
98
+ DEFINE_PROP_UINT32("CPU1_MPU_S", ARMSSE, cpu_mpu_s[1], 8),
99
DEFINE_PROP_END_OF_LIST()
100
};
101
102
@@ -XXX,XX +XXX,XX @@ static Property sse300_properties[] = {
103
DEFINE_PROP_UINT32("init-svtor", ARMSSE, init_svtor, 0x10000000),
104
DEFINE_PROP_BOOL("CPU0_FPU", ARMSSE, cpu_fpu[0], true),
105
DEFINE_PROP_BOOL("CPU0_DSP", ARMSSE, cpu_dsp[0], true),
106
+ DEFINE_PROP_UINT32("CPU0_MPU_NS", ARMSSE, cpu_mpu_ns[0], 8),
107
+ DEFINE_PROP_UINT32("CPU0_MPU_S", ARMSSE, cpu_mpu_s[0], 8),
108
DEFINE_PROP_END_OF_LIST()
109
};
110
111
@@ -XXX,XX +XXX,XX @@ static void armsse_realize(DeviceState *dev, Error **errp)
112
return;
113
}
114
}
115
+ if (!object_property_set_uint(cpuobj, "mpu-ns-regions",
116
+ s->cpu_mpu_ns[i], errp)) {
117
+ return;
118
+ }
119
+ if (!object_property_set_uint(cpuobj, "mpu-s-regions",
120
+ s->cpu_mpu_s[i], errp)) {
121
+ return;
122
+ }
123
124
if (i > 0) {
125
memory_region_add_subregion_overlap(&s->cpu_container[i], 0,
126
diff --git a/hw/arm/mps2-tz.c b/hw/arm/mps2-tz.c
127
index XXXXXXX..XXXXXXX 100644
128
--- a/hw/arm/mps2-tz.c
129
+++ b/hw/arm/mps2-tz.c
130
@@ -XXX,XX +XXX,XX @@ struct MPS2TZMachineClass {
131
int uart_overflow_irq; /* number of the combined UART overflow IRQ */
132
uint32_t init_svtor; /* init-svtor setting for SSE */
133
uint32_t sram_addr_width; /* SRAM_ADDR_WIDTH setting for SSE */
134
+ uint32_t cpu0_mpu_ns; /* CPU0_MPU_NS setting for SSE */
135
+ uint32_t cpu0_mpu_s; /* CPU0_MPU_S setting for SSE */
136
+ uint32_t cpu1_mpu_ns; /* CPU1_MPU_NS setting for SSE */
137
+ uint32_t cpu1_mpu_s; /* CPU1_MPU_S setting for SSE */
138
const RAMInfo *raminfo;
139
const char *armsse_type;
140
uint32_t boot_ram_size; /* size of ram at address 0; 0 == find in raminfo */
141
@@ -XXX,XX +XXX,XX @@ OBJECT_DECLARE_TYPE(MPS2TZMachineState, MPS2TZMachineClass, MPS2TZ_MACHINE)
142
#define MPS3_DDR_SIZE (2 * GiB)
143
#endif
144
145
+/* For cpu{0,1}_mpu_{ns,s}, means "leave at SSE's default value" */
146
+#define MPU_REGION_DEFAULT UINT32_MAX
147
+
148
static const uint32_t an505_oscclk[] = {
149
40000000,
150
24580000,
151
@@ -XXX,XX +XXX,XX @@ static void mps2tz_common_init(MachineState *machine)
152
OBJECT(system_memory), &error_abort);
153
qdev_prop_set_uint32(iotkitdev, "EXP_NUMIRQ", mmc->numirq);
154
qdev_prop_set_uint32(iotkitdev, "init-svtor", mmc->init_svtor);
155
+ if (mmc->cpu0_mpu_ns != MPU_REGION_DEFAULT) {
156
+ qdev_prop_set_uint32(iotkitdev, "CPU0_MPU_NS", mmc->cpu0_mpu_ns);
157
+ }
158
+ if (mmc->cpu0_mpu_s != MPU_REGION_DEFAULT) {
159
+ qdev_prop_set_uint32(iotkitdev, "CPU0_MPU_S", mmc->cpu0_mpu_s);
160
+ }
161
+ if (object_property_find(OBJECT(iotkitdev), "CPU1_MPU_NS")) {
162
+ if (mmc->cpu1_mpu_ns != MPU_REGION_DEFAULT) {
163
+ qdev_prop_set_uint32(iotkitdev, "CPU1_MPU_NS", mmc->cpu1_mpu_ns);
164
+ }
165
+ if (mmc->cpu1_mpu_s != MPU_REGION_DEFAULT) {
166
+ qdev_prop_set_uint32(iotkitdev, "CPU1_MPU_S", mmc->cpu1_mpu_s);
167
+ }
168
+ }
169
qdev_prop_set_uint32(iotkitdev, "SRAM_ADDR_WIDTH", mmc->sram_addr_width);
170
qdev_connect_clock_in(iotkitdev, "MAINCLK", mms->sysclk);
171
qdev_connect_clock_in(iotkitdev, "S32KCLK", mms->s32kclk);
172
@@ -XXX,XX +XXX,XX @@ static void mps2tz_class_init(ObjectClass *oc, void *data)
29
{
173
{
30
PL061State *s = (PL061State *)opaque;
174
MachineClass *mc = MACHINE_CLASS(oc);
31
175
IDAUInterfaceClass *iic = IDAU_INTERFACE_CLASS(oc);
32
- if (offset < 0x400) {
176
+ MPS2TZMachineClass *mmc = MPS2TZ_MACHINE_CLASS(oc);
33
- return s->data & (offset >> 2);
177
34
- }
178
mc->init = mps2tz_common_init;
35
- if (offset >= s->rsvd_start && offset <= 0xfcc) {
179
mc->reset = mps2_machine_reset;
36
- goto err_out;
180
iic->check = mps2_tz_idau_check;
37
- }
181
+
38
- if (offset >= 0xfd0 && offset < 0x1000) {
182
+ /* Most machines leave these at the SSE defaults */
39
- return s->id[(offset - 0xfd0) >> 2];
183
+ mmc->cpu0_mpu_ns = MPU_REGION_DEFAULT;
40
- }
184
+ mmc->cpu0_mpu_s = MPU_REGION_DEFAULT;
41
switch (offset) {
185
+ mmc->cpu1_mpu_ns = MPU_REGION_DEFAULT;
42
+ case 0x0 ... 0x3ff: /* Data */
186
+ mmc->cpu1_mpu_s = MPU_REGION_DEFAULT;
43
+ return s->data & (offset >> 2);
44
case 0x400: /* Direction */
45
return s->dir;
46
case 0x404: /* Interrupt sense */
47
@@ -XXX,XX +XXX,XX @@ static uint64_t pl061_read(void *opaque, hwaddr offset,
48
case 0x420: /* Alternate function select */
49
return s->afsel;
50
case 0x500: /* 2mA drive */
51
+ if (s->id != pl061_id_luminary) {
52
+ goto bad_offset;
53
+ }
54
return s->dr2r;
55
case 0x504: /* 4mA drive */
56
+ if (s->id != pl061_id_luminary) {
57
+ goto bad_offset;
58
+ }
59
return s->dr4r;
60
case 0x508: /* 8mA drive */
61
+ if (s->id != pl061_id_luminary) {
62
+ goto bad_offset;
63
+ }
64
return s->dr8r;
65
case 0x50c: /* Open drain */
66
+ if (s->id != pl061_id_luminary) {
67
+ goto bad_offset;
68
+ }
69
return s->odr;
70
case 0x510: /* Pull-up */
71
+ if (s->id != pl061_id_luminary) {
72
+ goto bad_offset;
73
+ }
74
return s->pur;
75
case 0x514: /* Pull-down */
76
+ if (s->id != pl061_id_luminary) {
77
+ goto bad_offset;
78
+ }
79
return s->pdr;
80
case 0x518: /* Slew rate control */
81
+ if (s->id != pl061_id_luminary) {
82
+ goto bad_offset;
83
+ }
84
return s->slr;
85
case 0x51c: /* Digital enable */
86
+ if (s->id != pl061_id_luminary) {
87
+ goto bad_offset;
88
+ }
89
return s->den;
90
case 0x520: /* Lock */
91
+ if (s->id != pl061_id_luminary) {
92
+ goto bad_offset;
93
+ }
94
return s->locked;
95
case 0x524: /* Commit */
96
+ if (s->id != pl061_id_luminary) {
97
+ goto bad_offset;
98
+ }
99
return s->cr;
100
case 0x528: /* Analog mode select */
101
+ if (s->id != pl061_id_luminary) {
102
+ goto bad_offset;
103
+ }
104
return s->amsel;
105
+ case 0xfd0 ... 0xfff: /* ID registers */
106
+ return s->id[(offset - 0xfd0) >> 2];
107
default:
108
+ bad_offset:
109
+ qemu_log_mask(LOG_GUEST_ERROR,
110
+ "pl061_read: Bad offset %x\n", (int)offset);
111
break;
112
}
113
-err_out:
114
- qemu_log_mask(LOG_GUEST_ERROR,
115
- "pl061_read: Bad offset %x\n", (int)offset);
116
return 0;
117
}
187
}
118
188
119
@@ -XXX,XX +XXX,XX @@ static void pl061_write(void *opaque, hwaddr offset,
189
static void mps2tz_set_default_ram_info(MPS2TZMachineClass *mmc)
120
PL061State *s = (PL061State *)opaque;
190
@@ -XXX,XX +XXX,XX @@ static void mps3tz_an547_class_init(ObjectClass *oc, void *data)
121
uint8_t mask;
191
mmc->numirq = 96;
122
192
mmc->uart_overflow_irq = 48;
123
- if (offset < 0x400) {
193
mmc->init_svtor = 0x00000000;
124
+ switch (offset) {
194
+ mmc->cpu0_mpu_s = mmc->cpu0_mpu_ns = 16;
125
+ case 0 ... 0x3ff:
195
mmc->sram_addr_width = 21;
126
mask = (offset >> 2) & s->dir;
196
mmc->raminfo = an547_raminfo;
127
s->data = (s->data & ~mask) | (value & mask);
197
mmc->armsse_type = TYPE_SSE300;
128
pl061_update(s);
129
return;
130
- }
131
- if (offset >= s->rsvd_start) {
132
- goto err_out;
133
- }
134
- switch (offset) {
135
case 0x400: /* Direction */
136
s->dir = value & 0xff;
137
break;
138
@@ -XXX,XX +XXX,XX @@ static void pl061_write(void *opaque, hwaddr offset,
139
s->afsel = (s->afsel & ~mask) | (value & mask);
140
break;
141
case 0x500: /* 2mA drive */
142
+ if (s->id != pl061_id_luminary) {
143
+ goto bad_offset;
144
+ }
145
s->dr2r = value & 0xff;
146
break;
147
case 0x504: /* 4mA drive */
148
+ if (s->id != pl061_id_luminary) {
149
+ goto bad_offset;
150
+ }
151
s->dr4r = value & 0xff;
152
break;
153
case 0x508: /* 8mA drive */
154
+ if (s->id != pl061_id_luminary) {
155
+ goto bad_offset;
156
+ }
157
s->dr8r = value & 0xff;
158
break;
159
case 0x50c: /* Open drain */
160
+ if (s->id != pl061_id_luminary) {
161
+ goto bad_offset;
162
+ }
163
s->odr = value & 0xff;
164
break;
165
case 0x510: /* Pull-up */
166
+ if (s->id != pl061_id_luminary) {
167
+ goto bad_offset;
168
+ }
169
s->pur = value & 0xff;
170
break;
171
case 0x514: /* Pull-down */
172
+ if (s->id != pl061_id_luminary) {
173
+ goto bad_offset;
174
+ }
175
s->pdr = value & 0xff;
176
break;
177
case 0x518: /* Slew rate control */
178
+ if (s->id != pl061_id_luminary) {
179
+ goto bad_offset;
180
+ }
181
s->slr = value & 0xff;
182
break;
183
case 0x51c: /* Digital enable */
184
+ if (s->id != pl061_id_luminary) {
185
+ goto bad_offset;
186
+ }
187
s->den = value & 0xff;
188
break;
189
case 0x520: /* Lock */
190
+ if (s->id != pl061_id_luminary) {
191
+ goto bad_offset;
192
+ }
193
s->locked = (value != 0xacce551);
194
break;
195
case 0x524: /* Commit */
196
+ if (s->id != pl061_id_luminary) {
197
+ goto bad_offset;
198
+ }
199
if (!s->locked)
200
s->cr = value & 0xff;
201
break;
202
case 0x528:
203
+ if (s->id != pl061_id_luminary) {
204
+ goto bad_offset;
205
+ }
206
s->amsel = value & 0xff;
207
break;
208
default:
209
- goto err_out;
210
+ bad_offset:
211
+ qemu_log_mask(LOG_GUEST_ERROR,
212
+ "pl061_write: Bad offset %x\n", (int)offset);
213
+ return;
214
}
215
pl061_update(s);
216
return;
217
-err_out:
218
- qemu_log_mask(LOG_GUEST_ERROR,
219
- "pl061_write: Bad offset %x\n", (int)offset);
220
}
221
222
static void pl061_reset(DeviceState *dev)
223
@@ -XXX,XX +XXX,XX @@ static void pl061_luminary_init(Object *obj)
224
PL061State *s = PL061(obj);
225
226
s->id = pl061_id_luminary;
227
- s->rsvd_start = 0x52c;
228
}
229
230
static void pl061_init(Object *obj)
231
@@ -XXX,XX +XXX,XX @@ static void pl061_init(Object *obj)
232
SysBusDevice *sbd = SYS_BUS_DEVICE(obj);
233
234
s->id = pl061_id;
235
- s->rsvd_start = 0x424;
236
237
memory_region_init_io(&s->iomem, obj, &pl061_ops, s, "pl061", 0x1000);
238
sysbus_init_mmio(sbd, &s->iomem);
239
--
198
--
240
2.20.1
199
2.34.1
241
200
242
201
diff view generated by jsdifflib