1
Changes v1->v2: it turns out that the raspi3 support exposes a
1
Here's another arm pullreq; nothing too exciting in here I think.
2
preexisting bug in our register definitions for VMPIDR/VMIDR:
3
https://lists.gnu.org/archive/html/qemu-devel/2018-02/msg04181.html
4
5
So I've dropped the final "enable raspi3 board" patch for the
6
moment. When that VMIDR/VMPIDR patch gets reviewed we can
7
put the raspi3 patch in with it.
8
9
2
10
thanks
3
thanks
11
-- PMM
4
-- PMM
12
5
13
The following changes since commit f003d07337a6d4d02c43429b26a4270459afb51a:
6
The following changes since commit 5fee33d97a7f2e95716417bd164f2f5264acd976:
14
7
15
Merge remote-tracking branch 'remotes/stefanha/tags/block-pull-request' into staging (2018-02-15 15:45:33 +0000)
8
Merge tag 'samuel-thibault' of https://people.debian.org/~sthibault/qemu into staging (2024-04-29 14:34:25 -0700)
16
9
17
are available in the Git repository at:
10
are available in the Git repository at:
18
11
19
git://git.linaro.org/people/pmaydell/qemu-arm.git tags/pull-target-arm-20180215-1
12
https://git.linaro.org/people/pmaydell/qemu-arm.git tags/pull-target-arm-20240430
20
13
21
for you to fetch changes up to bade58166f4466546600d824a2695a00269d10eb:
14
for you to fetch changes up to a0c325c4b05cf7815739d6a84e567b95c8c5be7e:
22
15
23
raspi: Raspberry Pi 3 support (2018-02-15 18:33:46 +0000)
16
tests/qtest : Add testcase for DM163 (2024-04-30 16:05:08 +0100)
24
17
25
----------------------------------------------------------------
18
----------------------------------------------------------------
26
target-arm queue:
19
target-arm queue:
27
* aspeed: code cleanup to use unimplemented_device
20
* hw/core/clock: allow clock_propagate on child clocks
28
* preparatory work for 'raspi3' RaspberryPi 3 machine model
21
* hvf: arm: Remove unused PL1_WRITE_MASK define
29
* more SVE prep work
22
* target/arm: Restrict translation disabled alignment check to VMSA
30
* v8M: add minor missing registers
23
* docs/system/arm/emulation.rst: Add missing implemented features
31
* v7M: fix bug where we weren't migrating v7m.other_sp
24
* target/arm: Enable FEAT_CSV2_3, FEAT_ETS2, FEAT_Spec_FPACC for 'max'
32
* v7M: fix bugs in handling of interrupt registers for
25
* tests/avocado: update sunxi kernel from armbian to 6.6.16
33
external interrupts beyond 32
26
* target/arm: Make new CPUs default to 1GHz generic timer
27
* hw/dmax/xlnx_dpdma: fix handling of address_extension descriptor fields
28
* hw/char/stm32l4x5_usart: Fix memory corruption by adding correct class_size
29
* hw/arm/npcm7xx: Store derivative OTP fuse key in little endian
30
* hw/arm: Add DM163 display to B-L475E-IOT01A board
34
31
35
----------------------------------------------------------------
32
----------------------------------------------------------------
36
Pekka Enberg (2):
33
Alexandra Diupina (1):
37
bcm2836: Make CPU type configurable
34
hw/dmax/xlnx_dpdma: fix handling of address_extension descriptor fields
38
raspi: Raspberry Pi 3 support
39
35
40
Peter Maydell (11):
36
Inès Varhol (5):
41
hw/intc/armv7m_nvic: Don't hardcode M profile ID registers in NVIC
37
hw/display : Add device DM163
42
hw/intc/armv7m_nvic: Fix ICSR PENDNMISET/CLR handling
38
hw/arm : Pass STM32L4x5 SYSCFG gpios to STM32L4x5 SoC
43
hw/intc/armv7m_nvic: Implement M profile cache maintenance ops
39
hw/arm : Create Bl475eMachineState
44
hw/intc/armv7m_nvic: Implement v8M CPPWR register
40
hw/arm : Connect DM163 to B-L475E-IOT01A
45
hw/intc/armv7m_nvic: Implement cache ID registers
41
tests/qtest : Add testcase for DM163
46
hw/intc/armv7m_nvic: Implement SCR
47
target/arm: Implement writing to CONTROL_NS for v8M
48
hw/intc/armv7m_nvic: Fix byte-to-interrupt number conversions
49
target/arm: Add AIRCR to vmstate struct
50
target/arm: Migrate v7m.other_sp
51
target/arm: Implement v8M MSPLIM and PSPLIM registers
52
42
53
Philippe Mathieu-Daudé (2):
43
Peter Maydell (10):
54
hw/arm/aspeed: directly map the serial device to the system address space
44
docs/system/arm/emulation.rst: Add missing implemented features
55
hw/arm/aspeed: simplify using the 'unimplemented device' for aspeed_soc.io
45
target/arm: Enable FEAT_CSV2_3 for -cpu max
46
target/arm: Enable FEAT_ETS2 for -cpu max
47
target/arm: Implement ID_AA64MMFR3_EL1
48
target/arm: Enable FEAT_Spec_FPACC for -cpu max
49
tests/avocado: update sunxi kernel from armbian to 6.6.16
50
target/arm: Refactor default generic timer frequency handling
51
hw/arm/sbsa-ref: Force CPU generic timer to 62.5MHz
52
hw/watchdog/sbsa_gwdt: Make watchdog timer frequency a QOM property
53
target/arm: Default to 1GHz cntfrq for 'max' and new CPUs
56
54
57
Richard Henderson (5):
55
Philippe Mathieu-Daudé (1):
58
target/arm: Remove ARM_CP_64BIT from ZCR_EL registers
56
hw/arm/npcm7xx: Store derivative OTP fuse key in little endian
59
target/arm: Enforce FP access to FPCR/FPSR
60
target/arm: Suppress TB end for FPCR/FPSR
61
target/arm: Enforce access to ZCR_EL at translation
62
target/arm: Handle SVE registers when using clear_vec_high
63
57
64
include/hw/arm/aspeed_soc.h | 1 -
58
Raphael Poggi (1):
65
include/hw/arm/bcm2836.h | 1 +
59
hw/core/clock: allow clock_propagate on child clocks
66
target/arm/cpu.h | 71 ++++++++++++-----
67
target/arm/internals.h | 6 ++
68
hw/arm/aspeed_soc.c | 35 ++-------
69
hw/arm/bcm2836.c | 17 +++--
70
hw/arm/raspi.c | 34 ++++++---
71
hw/intc/armv7m_nvic.c | 98 ++++++++++++++++++------
72
target/arm/cpu.c | 28 +++++++
73
target/arm/helper.c | 84 +++++++++++++++-----
74
target/arm/machine.c | 84 ++++++++++++++++++++
75
target/arm/translate-a64.c | 181 ++++++++++++++++++++------------------------
76
12 files changed, 429 insertions(+), 211 deletions(-)
77
60
61
Richard Henderson (1):
62
target/arm: Restrict translation disabled alignment check to VMSA
63
64
Thomas Huth (1):
65
hw/char/stm32l4x5_usart: Fix memory corruption by adding correct class_size
66
67
Zenghui Yu (1):
68
hvf: arm: Remove PL1_WRITE_MASK
69
70
docs/system/arm/b-l475e-iot01a.rst | 3 +-
71
docs/system/arm/emulation.rst | 42 ++++-
72
include/hw/display/dm163.h | 59 ++++++
73
include/hw/watchdog/sbsa_gwdt.h | 3 +-
74
target/arm/cpu.h | 28 +++
75
target/arm/internals.h | 15 +-
76
hw/arm/b-l475e-iot01a.c | 105 +++++++++--
77
hw/arm/npcm7xx.c | 3 +-
78
hw/arm/sbsa-ref.c | 16 ++
79
hw/arm/stm32l4x5_soc.c | 6 +-
80
hw/char/stm32l4x5_usart.c | 1 +
81
hw/core/clock.c | 1 -
82
hw/core/machine.c | 4 +-
83
hw/display/dm163.c | 349 ++++++++++++++++++++++++++++++++++++
84
hw/dma/xlnx_dpdma.c | 20 +--
85
hw/watchdog/sbsa_gwdt.c | 15 +-
86
target/arm/cpu.c | 42 +++--
87
target/arm/cpu64.c | 2 +
88
target/arm/helper.c | 22 +--
89
target/arm/hvf/hvf.c | 3 +-
90
target/arm/kvm.c | 2 +
91
target/arm/tcg/cpu32.c | 6 +-
92
target/arm/tcg/cpu64.c | 28 ++-
93
target/arm/tcg/hflags.c | 12 +-
94
tests/qtest/dm163-test.c | 194 ++++++++++++++++++++
95
tests/qtest/stm32l4x5_gpio-test.c | 13 +-
96
tests/qtest/stm32l4x5_syscfg-test.c | 17 +-
97
hw/arm/Kconfig | 1 +
98
hw/display/Kconfig | 3 +
99
hw/display/meson.build | 1 +
100
hw/display/trace-events | 14 ++
101
tests/avocado/boot_linux_console.py | 70 ++++----
102
tests/avocado/replay_kernel.py | 8 +-
103
tests/qtest/meson.build | 2 +
104
34 files changed, 987 insertions(+), 123 deletions(-)
105
create mode 100644 include/hw/display/dm163.h
106
create mode 100644 hw/display/dm163.c
107
create mode 100644 tests/qtest/dm163-test.c
108
diff view generated by jsdifflib
New patch
1
From: Raphael Poggi <raphael.poggi@lynxleap.co.uk>
1
2
3
clock_propagate() has an assert that clk->source is NULL, i.e. that
4
you are calling it on a clock which has no source clock. This made
5
sense in the original design where the only way for a clock's
6
frequency to change if it had a source clock was when that source
7
clock changed. However, we subsequently added multiplier/divider
8
support, but didn't look at what that meant for propagation.
9
10
If a clock-management device changes the multiplier or divider value
11
on a clock, it needs to propagate that change down to child clocks,
12
even if the clock has a source clock set. So the assertion is now
13
incorrect.
14
15
Remove the assertion.
16
17
Signed-off-by: Raphael Poggi <raphael.poggi@lynxleap.co.uk>
18
Message-id: 20240419162951.23558-1-raphael.poggi@lynxleap.co.uk
19
Reviewed-by: Peter Maydell <peter.maydell@linaro.org>
20
[PMM: Rewrote the commit message]
21
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
22
---
23
hw/core/clock.c | 1 -
24
1 file changed, 1 deletion(-)
25
26
diff --git a/hw/core/clock.c b/hw/core/clock.c
27
index XXXXXXX..XXXXXXX 100644
28
--- a/hw/core/clock.c
29
+++ b/hw/core/clock.c
30
@@ -XXX,XX +XXX,XX @@ static void clock_propagate_period(Clock *clk, bool call_callbacks)
31
32
void clock_propagate(Clock *clk)
33
{
34
- assert(clk->source == NULL);
35
trace_clock_propagate(CLOCK_PATH(clk));
36
clock_propagate_period(clk, true);
37
}
38
--
39
2.34.1
diff view generated by jsdifflib
1
From: Pekka Enberg <penberg@iki.fi>
1
From: Zenghui Yu <zenghui.yu@linux.dev>
2
2
3
This patch adds Raspberry Pi 3 support to hw/arm/raspi.c. The
3
As it had never been used since the first commit a1477da3ddeb ("hvf: Add
4
differences to Pi 2 are:
4
Apple Silicon support").
5
5
6
- Firmware address
6
Signed-off-by: Zenghui Yu <zenghui.yu@linux.dev>
7
- Board ID
7
Message-id: 20240422092715.71973-1-zenghui.yu@linux.dev
8
- Board revision
9
10
The CPU is different too, but that's going to be configured as part of
11
the machine default CPU when we introduce a new machine type.
12
13
The patch was written from scratch by me but the logic is similar to
14
Zoltán Baldaszti's previous work, which I used as a reference (with
15
permission from the author):
16
17
https://github.com/bztsrc/qemu-raspi3
18
19
Signed-off-by: Pekka Enberg <penberg@iki.fi>
20
[PMM: fixed trailing whitespace on one line]
21
Reviewed-by: Peter Maydell <peter.maydell@linaro.org>
8
Reviewed-by: Peter Maydell <peter.maydell@linaro.org>
22
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
9
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
23
---
10
---
24
hw/arm/raspi.c | 31 +++++++++++++++++++++----------
11
target/arm/hvf/hvf.c | 1 -
25
1 file changed, 21 insertions(+), 10 deletions(-)
12
1 file changed, 1 deletion(-)
26
13
27
diff --git a/hw/arm/raspi.c b/hw/arm/raspi.c
14
diff --git a/target/arm/hvf/hvf.c b/target/arm/hvf/hvf.c
28
index XXXXXXX..XXXXXXX 100644
15
index XXXXXXX..XXXXXXX 100644
29
--- a/hw/arm/raspi.c
16
--- a/target/arm/hvf/hvf.c
30
+++ b/hw/arm/raspi.c
17
+++ b/target/arm/hvf/hvf.c
31
@@ -XXX,XX +XXX,XX @@
18
@@ -XXX,XX +XXX,XX @@ void hvf_arm_init_debug(void)
32
* Rasperry Pi 2 emulation Copyright (c) 2015, Microsoft
19
33
* Written by Andrew Baumann
20
#define HVF_SYSREG(crn, crm, op0, op1, op2) \
34
*
21
ENCODE_AA64_CP_REG(CP_REG_ARM64_SYSREG_CP, crn, crm, op0, op1, op2)
35
+ * Raspberry Pi 3 emulation Copyright (c) 2018 Zoltán Baldaszti
22
-#define PL1_WRITE_MASK 0x4
36
+ * Upstream code cleanup (c) 2018 Pekka Enberg
23
37
+ *
24
#define SYSREG_OP0_SHIFT 20
38
* This code is licensed under the GNU GPLv2 and later.
25
#define SYSREG_OP0_MASK 0x3
39
*/
40
41
@@ -XXX,XX +XXX,XX @@
42
#define SMPBOOT_ADDR 0x300 /* this should leave enough space for ATAGS */
43
#define MVBAR_ADDR 0x400 /* secure vectors */
44
#define BOARDSETUP_ADDR (MVBAR_ADDR + 0x20) /* board setup code */
45
-#define FIRMWARE_ADDR 0x8000 /* Pi loads kernel.img here by default */
46
+#define FIRMWARE_ADDR_2 0x8000 /* Pi 2 loads kernel.img here by default */
47
+#define FIRMWARE_ADDR_3 0x80000 /* Pi 3 loads kernel.img here by default */
48
49
/* Table of Linux board IDs for different Pi versions */
50
-static const int raspi_boardid[] = {[1] = 0xc42, [2] = 0xc43};
51
+static const int raspi_boardid[] = {[1] = 0xc42, [2] = 0xc43, [3] = 0xc44};
52
53
typedef struct RasPiState {
54
BCM2836State soc;
55
@@ -XXX,XX +XXX,XX @@ static void setup_boot(MachineState *machine, int version, size_t ram_size)
56
binfo.secure_board_setup = true;
57
binfo.secure_boot = true;
58
59
- /* Pi2 requires SMP setup */
60
- if (version == 2) {
61
+ /* Pi2 and Pi3 requires SMP setup */
62
+ if (version >= 2) {
63
binfo.smp_loader_start = SMPBOOT_ADDR;
64
binfo.write_secondary_boot = write_smpboot;
65
binfo.secondary_cpu_reset_hook = reset_secondary;
66
@@ -XXX,XX +XXX,XX @@ static void setup_boot(MachineState *machine, int version, size_t ram_size)
67
* the normal Linux boot process
68
*/
69
if (machine->firmware) {
70
+ hwaddr firmware_addr = version == 3 ? FIRMWARE_ADDR_3 : FIRMWARE_ADDR_2;
71
/* load the firmware image (typically kernel.img) */
72
- r = load_image_targphys(machine->firmware, FIRMWARE_ADDR,
73
- ram_size - FIRMWARE_ADDR);
74
+ r = load_image_targphys(machine->firmware, firmware_addr,
75
+ ram_size - firmware_addr);
76
if (r < 0) {
77
error_report("Failed to load firmware from %s", machine->firmware);
78
exit(1);
79
}
80
81
- binfo.entry = FIRMWARE_ADDR;
82
+ binfo.entry = firmware_addr;
83
binfo.firmware_loaded = true;
84
} else {
85
binfo.kernel_filename = machine->kernel_filename;
86
@@ -XXX,XX +XXX,XX @@ static void setup_boot(MachineState *machine, int version, size_t ram_size)
87
arm_load_kernel(ARM_CPU(first_cpu), &binfo);
88
}
89
90
-static void raspi2_init(MachineState *machine)
91
+static void raspi_init(MachineState *machine, int version)
92
{
93
RasPiState *s = g_new0(RasPiState, 1);
94
uint32_t vcram_size;
95
@@ -XXX,XX +XXX,XX @@ static void raspi2_init(MachineState *machine)
96
&error_abort);
97
object_property_set_int(OBJECT(&s->soc), smp_cpus, "enabled-cpus",
98
&error_abort);
99
- object_property_set_int(OBJECT(&s->soc), 0xa21041, "board-rev",
100
+ int board_rev = version == 3 ? 0xa02082 : 0xa21041;
101
+ object_property_set_int(OBJECT(&s->soc), board_rev, "board-rev",
102
&error_abort);
103
object_property_set_bool(OBJECT(&s->soc), true, "realized", &error_abort);
104
105
@@ -XXX,XX +XXX,XX @@ static void raspi2_init(MachineState *machine)
106
107
vcram_size = object_property_get_uint(OBJECT(&s->soc), "vcram-size",
108
&error_abort);
109
- setup_boot(machine, 2, machine->ram_size - vcram_size);
110
+ setup_boot(machine, version, machine->ram_size - vcram_size);
111
+}
112
+
113
+static void raspi2_init(MachineState *machine)
114
+{
115
+ raspi_init(machine, 2);
116
}
117
118
static void raspi2_machine_init(MachineClass *mc)
119
--
26
--
120
2.16.1
27
2.34.1
121
122
diff view generated by jsdifflib
1
From: Richard Henderson <richard.henderson@linaro.org>
1
From: Richard Henderson <richard.henderson@linaro.org>
2
2
3
Nothing in either register affects the TB.
3
For cpus using PMSA, when the MPU is disabled, the default memory
4
type is Normal, Non-cachable. This means that it should not
5
have alignment restrictions enforced.
4
6
7
Cc: qemu-stable@nongnu.org
8
Fixes: 59754f85ed3 ("target/arm: Do memory type alignment check when translation disabled")
9
Reported-by: Clément Chigot <chigot@adacore.com>
5
Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
10
Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
6
Message-id: 20180211205848.4568-4-richard.henderson@linaro.org
11
Reviewed-by: Philippe Mathieu-Daudé <philmd@linaro.org>
7
Reviewed-by: Peter Maydell <peter.maydell@linaro.org>
12
Tested-by: Clément Chigot <chigot@adacore.com>
13
Message-id: 20240422170722.117409-1-richard.henderson@linaro.org
14
[PMM: trivial comment, commit message tweaks]
8
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
15
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
9
---
16
---
10
target/arm/helper.c | 4 ++--
17
target/arm/tcg/hflags.c | 12 ++++++++++--
11
1 file changed, 2 insertions(+), 2 deletions(-)
18
1 file changed, 10 insertions(+), 2 deletions(-)
12
19
13
diff --git a/target/arm/helper.c b/target/arm/helper.c
20
diff --git a/target/arm/tcg/hflags.c b/target/arm/tcg/hflags.c
14
index XXXXXXX..XXXXXXX 100644
21
index XXXXXXX..XXXXXXX 100644
15
--- a/target/arm/helper.c
22
--- a/target/arm/tcg/hflags.c
16
+++ b/target/arm/helper.c
23
+++ b/target/arm/tcg/hflags.c
17
@@ -XXX,XX +XXX,XX @@ static const ARMCPRegInfo v8_cp_reginfo[] = {
24
@@ -XXX,XX +XXX,XX @@ static bool aprofile_require_alignment(CPUARMState *env, int el, uint64_t sctlr)
18
.writefn = aa64_daif_write, .resetfn = arm_cp_reset_ignore },
25
}
19
{ .name = "FPCR", .state = ARM_CP_STATE_AA64,
26
20
.opc0 = 3, .opc1 = 3, .opc2 = 0, .crn = 4, .crm = 4,
27
/*
21
- .access = PL0_RW, .type = ARM_CP_FPU,
28
- * If translation is disabled, then the default memory type is
22
+ .access = PL0_RW, .type = ARM_CP_FPU | ARM_CP_SUPPRESS_TB_END,
29
- * Device(-nGnRnE) instead of Normal, which requires that alignment
23
.readfn = aa64_fpcr_read, .writefn = aa64_fpcr_write },
30
+ * With PMSA, when the MPU is disabled, all memory types in the
24
{ .name = "FPSR", .state = ARM_CP_STATE_AA64,
31
+ * default map are Normal, so don't need aligment enforcing.
25
.opc0 = 3, .opc1 = 3, .opc2 = 1, .crn = 4, .crm = 4,
32
+ */
26
- .access = PL0_RW, .type = ARM_CP_FPU,
33
+ if (arm_feature(env, ARM_FEATURE_PMSA)) {
27
+ .access = PL0_RW, .type = ARM_CP_FPU | ARM_CP_SUPPRESS_TB_END,
34
+ return false;
28
.readfn = aa64_fpsr_read, .writefn = aa64_fpsr_write },
35
+ }
29
{ .name = "DCZID_EL0", .state = ARM_CP_STATE_AA64,
36
+
30
.opc0 = 3, .opc1 = 3, .opc2 = 7, .crn = 0, .crm = 0,
37
+ /*
38
+ * With VMSA, if translation is disabled, then the default memory type
39
+ * is Device(-nGnRnE) instead of Normal, which requires that alignment
40
* be enforced. Since this affects all ram, it is most efficient
41
* to handle this during translation.
42
*/
31
--
43
--
32
2.16.1
44
2.34.1
33
45
34
46
diff view generated by jsdifflib
1
In commit commit 3b2e934463121 we added support for the AIRCR
1
As of version DDI0487K.a of the Arm ARM, some architectural features
2
register holding state, but forgot to add it to the vmstate
2
which previously didn't have official names have been named. Add
3
structs. Since it only holds r/w state if the security extension
3
these to the list of features which QEMU's TCG emulation supports.
4
is implemented, we can just add it to vmstate_m_security.
4
Mostly these are features which we thought of as part of baseline 8.0
5
support. For SVE and SVE2, the names have been brought into line
6
with the FEAT_* naming convention of other extensions, and some
7
sub-components split into separate FEAT_ items. In a few cases (eg
8
FEAT_CCIDX, FEAT_DPB2) the omission from our list was just an oversight.
5
9
6
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
10
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
7
Reviewed-by: Richard Henderson <richard.henderson@linaro.org>
11
Reviewed-by: Richard Henderson <richard.henderson@linaro.org>
8
Message-id: 20180209165810.6668-10-peter.maydell@linaro.org
12
Message-id: 20240418152004.2106516-2-peter.maydell@linaro.org
9
---
13
---
10
target/arm/machine.c | 4 ++++
14
docs/system/arm/emulation.rst | 38 +++++++++++++++++++++++++++++++++--
11
1 file changed, 4 insertions(+)
15
1 file changed, 36 insertions(+), 2 deletions(-)
12
16
13
diff --git a/target/arm/machine.c b/target/arm/machine.c
17
diff --git a/docs/system/arm/emulation.rst b/docs/system/arm/emulation.rst
14
index XXXXXXX..XXXXXXX 100644
18
index XXXXXXX..XXXXXXX 100644
15
--- a/target/arm/machine.c
19
--- a/docs/system/arm/emulation.rst
16
+++ b/target/arm/machine.c
20
+++ b/docs/system/arm/emulation.rst
17
@@ -XXX,XX +XXX,XX @@ static const VMStateDescription vmstate_m_security = {
21
@@ -XXX,XX +XXX,XX @@ Armv8 versions of the A-profile architecture. It also has support for
18
VMSTATE_VALIDATE("SAU_RNR is valid", sau_rnr_vmstate_validate),
22
the following architecture extensions:
19
VMSTATE_UINT32(env.sau.ctrl, ARMCPU),
23
20
VMSTATE_UINT32(env.v7m.scr[M_REG_S], ARMCPU),
24
- FEAT_AA32BF16 (AArch32 BFloat16 instructions)
21
+ /* AIRCR is not secure-only, but our implementation is R/O if the
25
+- FEAT_AA32EL0 (Support for AArch32 at EL0)
22
+ * security extension is unimplemented, so we migrate it here.
26
+- FEAT_AA32EL1 (Support for AArch32 at EL1)
23
+ */
27
+- FEAT_AA32EL2 (Support for AArch32 at EL2)
24
+ VMSTATE_UINT32(env.v7m.aircr, ARMCPU),
28
+- FEAT_AA32EL3 (Support for AArch32 at EL3)
25
VMSTATE_END_OF_LIST()
29
- FEAT_AA32HPD (AArch32 hierarchical permission disables)
26
}
30
- FEAT_AA32I8MM (AArch32 Int8 matrix multiplication instructions)
27
};
31
+- FEAT_AA64EL0 (Support for AArch64 at EL0)
32
+- FEAT_AA64EL1 (Support for AArch64 at EL1)
33
+- FEAT_AA64EL2 (Support for AArch64 at EL2)
34
+- FEAT_AA64EL3 (Support for AArch64 at EL3)
35
+- FEAT_AdvSIMD (Advanced SIMD Extension)
36
- FEAT_AES (AESD and AESE instructions)
37
+- FEAT_Armv9_Crypto (Armv9 Cryptographic Extension)
38
+- FEAT_ASID16 (16 bit ASID)
39
- FEAT_BBM at level 2 (Translation table break-before-make levels)
40
- FEAT_BF16 (AArch64 BFloat16 instructions)
41
- FEAT_BTI (Branch Target Identification)
42
+- FEAT_CCIDX (Extended cache index)
43
- FEAT_CRC32 (CRC32 instructions)
44
+- FEAT_Crypto (Cryptographic Extension)
45
- FEAT_CSV2 (Cache speculation variant 2)
46
- FEAT_CSV2_1p1 (Cache speculation variant 2, version 1.1)
47
- FEAT_CSV2_1p2 (Cache speculation variant 2, version 1.2)
48
@@ -XXX,XX +XXX,XX @@ the following architecture extensions:
49
- FEAT_DGH (Data gathering hint)
50
- FEAT_DIT (Data Independent Timing instructions)
51
- FEAT_DPB (DC CVAP instruction)
52
+- FEAT_DPB2 (DC CVADP instruction)
53
+- FEAT_Debugv8p1 (Debug with VHE)
54
- FEAT_Debugv8p2 (Debug changes for v8.2)
55
- FEAT_Debugv8p4 (Debug changes for v8.4)
56
- FEAT_DotProd (Advanced SIMD dot product instructions)
57
- FEAT_DoubleFault (Double Fault Extension)
58
- FEAT_E0PD (Preventing EL0 access to halves of address maps)
59
- FEAT_ECV (Enhanced Counter Virtualization)
60
+- FEAT_EL0 (Support for execution at EL0)
61
+- FEAT_EL1 (Support for execution at EL1)
62
+- FEAT_EL2 (Support for execution at EL2)
63
+- FEAT_EL3 (Support for execution at EL3)
64
- FEAT_EPAC (Enhanced pointer authentication)
65
- FEAT_ETS (Enhanced Translation Synchronization)
66
- FEAT_EVT (Enhanced Virtualization Traps)
67
+- FEAT_F32MM (Single-precision Matrix Multiplication)
68
+- FEAT_F64MM (Double-precision Matrix Multiplication)
69
- FEAT_FCMA (Floating-point complex number instructions)
70
- FEAT_FGT (Fine-Grained Traps)
71
- FEAT_FHM (Floating-point half-precision multiplication instructions)
72
+- FEAT_FP (Floating Point extensions)
73
- FEAT_FP16 (Half-precision floating-point data processing)
74
- FEAT_FPAC (Faulting on AUT* instructions)
75
- FEAT_FPACCOMBINE (Faulting on combined pointer authentication instructions)
76
@@ -XXX,XX +XXX,XX @@ the following architecture extensions:
77
- FEAT_LSE (Large System Extensions)
78
- FEAT_LSE2 (Large System Extensions v2)
79
- FEAT_LVA (Large Virtual Address space)
80
+- FEAT_MixedEnd (Mixed-endian support)
81
+- FEAT_MixdEndEL0 (Mixed-endian support at EL0)
82
- FEAT_MOPS (Standardization of memory operations)
83
- FEAT_MTE (Memory Tagging Extension)
84
- FEAT_MTE2 (Memory Tagging Extension)
85
- FEAT_MTE3 (MTE Asymmetric Fault Handling)
86
+- FEAT_MTE_ASYM_FAULT (Memory tagging asymmetric faults)
87
- FEAT_NMI (Non-maskable Interrupt)
88
- FEAT_NV (Nested Virtualization)
89
- FEAT_NV2 (Enhanced nested virtualization support)
90
@@ -XXX,XX +XXX,XX @@ the following architecture extensions:
91
- FEAT_PAuth (Pointer authentication)
92
- FEAT_PAuth2 (Enhancements to pointer authentication)
93
- FEAT_PMULL (PMULL, PMULL2 instructions)
94
+- FEAT_PMUv3 (PMU extension version 3)
95
- FEAT_PMUv3p1 (PMU Extensions v3.1)
96
- FEAT_PMUv3p4 (PMU Extensions v3.4)
97
- FEAT_PMUv3p5 (PMU Extensions v3.5)
98
@@ -XXX,XX +XXX,XX @@ the following architecture extensions:
99
- FEAT_SME_FA64 (Full A64 instruction set in Streaming SVE mode)
100
- FEAT_SME_F64F64 (Double-precision floating-point outer product instructions)
101
- FEAT_SME_I16I64 (16-bit to 64-bit integer widening outer product instructions)
102
+- FEAT_SVE (Scalable Vector Extension)
103
+- FEAT_SVE_AES (Scalable Vector AES instructions)
104
+- FEAT_SVE_BitPerm (Scalable Vector Bit Permutes instructions)
105
+- FEAT_SVE_PMULL128 (Scalable Vector PMULL instructions)
106
+- FEAT_SVE_SHA3 (Scalable Vector SHA3 instructions)
107
+- FEAT_SVE_SM4 (Scalable Vector SM4 instructions)
108
+- FEAT_SVE2 (Scalable Vector Extension version 2)
109
- FEAT_SPECRES (Speculation restriction instructions)
110
- FEAT_SSBS (Speculative Store Bypass Safe)
111
+- FEAT_TGran16K (Support for 16KB memory translation granule size at stage 1)
112
+- FEAT_TGran4K (Support for 4KB memory translation granule size at stage 1)
113
+- FEAT_TGran64K (Support for 64KB memory translation granule size at stage 1)
114
- FEAT_TIDCP1 (EL0 use of IMPLEMENTATION DEFINED functionality)
115
- FEAT_TLBIOS (TLB invalidate instructions in Outer Shareable domain)
116
- FEAT_TLBIRANGE (TLB invalidate range instructions)
117
@@ -XXX,XX +XXX,XX @@ the following architecture extensions:
118
- FEAT_VHE (Virtualization Host Extensions)
119
- FEAT_VMID16 (16-bit VMID)
120
- FEAT_XNX (Translation table stage 2 Unprivileged Execute-never)
121
-- SVE (The Scalable Vector Extension)
122
-- SVE2 (The Scalable Vector Extension v2)
123
124
For information on the specifics of these extensions, please refer
125
to the `Armv8-A Arm Architecture Reference Manual
28
--
126
--
29
2.16.1
127
2.34.1
30
31
diff view generated by jsdifflib
1
In commit 50f11062d4c896 we added support for MSR/MRS access
1
FEAT_CSV2_3 adds a mechanism to identify if hardware cannot disclose
2
to the NS banked special registers, but we forgot to implement
2
information about whether branch targets and branch history trained
3
the support for writing to CONTROL_NS. Correct the omission.
3
in one hardware described context can control speculative execution
4
in a different hardware context.
5
6
There is no branch prediction in TCG, so we don't need to do anything
7
to be compliant with this. Upadte the '-cpu max' ID registers to
8
advertise the feature.
4
9
5
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
10
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
6
Reviewed-by: Richard Henderson <richard.henderson@linaro.org>
11
Reviewed-by: Richard Henderson <richard.henderson@linaro.org>
7
Message-id: 20180209165810.6668-8-peter.maydell@linaro.org
12
Reviewed-by: Philippe Mathieu-Daudé <philmd@linaro.org>
13
Message-id: 20240418152004.2106516-3-peter.maydell@linaro.org
8
---
14
---
9
target/arm/helper.c | 10 ++++++++++
15
docs/system/arm/emulation.rst | 1 +
10
1 file changed, 10 insertions(+)
16
target/arm/tcg/cpu64.c | 4 ++--
17
2 files changed, 3 insertions(+), 2 deletions(-)
11
18
12
diff --git a/target/arm/helper.c b/target/arm/helper.c
19
diff --git a/docs/system/arm/emulation.rst b/docs/system/arm/emulation.rst
13
index XXXXXXX..XXXXXXX 100644
20
index XXXXXXX..XXXXXXX 100644
14
--- a/target/arm/helper.c
21
--- a/docs/system/arm/emulation.rst
15
+++ b/target/arm/helper.c
22
+++ b/docs/system/arm/emulation.rst
16
@@ -XXX,XX +XXX,XX @@ void HELPER(v7m_msr)(CPUARMState *env, uint32_t maskreg, uint32_t val)
23
@@ -XXX,XX +XXX,XX @@ the following architecture extensions:
17
}
24
- FEAT_CSV2_1p1 (Cache speculation variant 2, version 1.1)
18
env->v7m.faultmask[M_REG_NS] = val & 1;
25
- FEAT_CSV2_1p2 (Cache speculation variant 2, version 1.2)
19
return;
26
- FEAT_CSV2_2 (Cache speculation variant 2, version 2)
20
+ case 0x94: /* CONTROL_NS */
27
+- FEAT_CSV2_3 (Cache speculation variant 2, version 3)
21
+ if (!env->v7m.secure) {
28
- FEAT_CSV3 (Cache speculation variant 3)
22
+ return;
29
- FEAT_DGH (Data gathering hint)
23
+ }
30
- FEAT_DIT (Data Independent Timing instructions)
24
+ write_v7m_control_spsel_for_secstate(env,
31
diff --git a/target/arm/tcg/cpu64.c b/target/arm/tcg/cpu64.c
25
+ val & R_V7M_CONTROL_SPSEL_MASK,
32
index XXXXXXX..XXXXXXX 100644
26
+ M_REG_NS);
33
--- a/target/arm/tcg/cpu64.c
27
+ env->v7m.control[M_REG_NS] &= ~R_V7M_CONTROL_NPRIV_MASK;
34
+++ b/target/arm/tcg/cpu64.c
28
+ env->v7m.control[M_REG_NS] |= val & R_V7M_CONTROL_NPRIV_MASK;
35
@@ -XXX,XX +XXX,XX @@ void aarch64_max_tcg_initfn(Object *obj)
29
+ return;
36
t = FIELD_DP64(t, ID_AA64PFR0, SVE, 1);
30
case 0x98: /* SP_NS */
37
t = FIELD_DP64(t, ID_AA64PFR0, SEL2, 1); /* FEAT_SEL2 */
31
{
38
t = FIELD_DP64(t, ID_AA64PFR0, DIT, 1); /* FEAT_DIT */
32
/* This gives the non-secure SP selected based on whether we're
39
- t = FIELD_DP64(t, ID_AA64PFR0, CSV2, 2); /* FEAT_CSV2_2 */
40
+ t = FIELD_DP64(t, ID_AA64PFR0, CSV2, 3); /* FEAT_CSV2_3 */
41
t = FIELD_DP64(t, ID_AA64PFR0, CSV3, 1); /* FEAT_CSV3 */
42
cpu->isar.id_aa64pfr0 = t;
43
44
@@ -XXX,XX +XXX,XX @@ void aarch64_max_tcg_initfn(Object *obj)
45
t = FIELD_DP64(t, ID_AA64PFR1, MTE, 3); /* FEAT_MTE3 */
46
t = FIELD_DP64(t, ID_AA64PFR1, RAS_FRAC, 0); /* FEAT_RASv1p1 + FEAT_DoubleFault */
47
t = FIELD_DP64(t, ID_AA64PFR1, SME, 1); /* FEAT_SME */
48
- t = FIELD_DP64(t, ID_AA64PFR1, CSV2_FRAC, 0); /* FEAT_CSV2_2 */
49
+ t = FIELD_DP64(t, ID_AA64PFR1, CSV2_FRAC, 0); /* FEAT_CSV2_3 */
50
t = FIELD_DP64(t, ID_AA64PFR1, NMI, 1); /* FEAT_NMI */
51
cpu->isar.id_aa64pfr1 = t;
52
33
--
53
--
34
2.16.1
54
2.34.1
35
55
36
56
diff view generated by jsdifflib
1
The PENDNMISET/CLR bits in the ICSR should be RAZ/WI from
1
FEAT_ETS2 is a tighter set of guarantees about memory ordering
2
NonSecure state if the AIRCR.BFHFNMINS bit is zero. We had
2
involving translation table walks than the old FEAT_ETS; FEAT_ETS has
3
misimplemented this as making the bits RAZ/WI from both
3
been retired from the Arm ARM and the old ID_AA64MMFR1.ETS == 1
4
Secure and NonSecure states. Fix this bug by checking
4
now gives no greater guarantees than ETS == 0.
5
attrs.secure so that Secure code can pend and unpend NMIs.
5
6
FEAT_ETS2 requires:
7
* the virtual address of a load or store that appears in program
8
order after a DSB cannot be translated until after the DSB
9
completes (section B2.10.9)
10
* TLB maintenance operations that only affect translations without
11
execute permission are guaranteed complete after a DSB
12
(R_BLDZX)
13
* if a memory access RW2 is ordered-before memory access RW2,
14
then RW1 is also ordered-before any translation table walk
15
generated by RW2 that generates a Translation, Address size
16
or Access flag fault (R_NNFPF, I_CLGHP)
17
18
As with FEAT_ETS, QEMU is already compliant, because we do not
19
reorder translation table walk memory accesses relative to other
20
memory accesses, and we always guarantee to have finished TLB
21
maintenance as soon as the TLB op is done.
22
23
Update the documentation to list FEAT_ETS2 instead of the
24
no-longer-existent FEAT_ETS, and update the 'max' CPU ID registers.
6
25
7
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
26
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
8
Reviewed-by: Richard Henderson <richard.henderson@linaro.org>
27
Reviewed-by: Richard Henderson <richard.henderson@linaro.org>
9
Message-id: 20180209165810.6668-3-peter.maydell@linaro.org
28
Reviewed-by: Philippe Mathieu-Daudé <philmd@linaro.org>
29
Message-id: 20240418152004.2106516-4-peter.maydell@linaro.org
10
---
30
---
11
hw/intc/armv7m_nvic.c | 6 +++---
31
docs/system/arm/emulation.rst | 2 +-
12
1 file changed, 3 insertions(+), 3 deletions(-)
32
target/arm/tcg/cpu32.c | 2 +-
33
target/arm/tcg/cpu64.c | 2 +-
34
3 files changed, 3 insertions(+), 3 deletions(-)
13
35
14
diff --git a/hw/intc/armv7m_nvic.c b/hw/intc/armv7m_nvic.c
36
diff --git a/docs/system/arm/emulation.rst b/docs/system/arm/emulation.rst
15
index XXXXXXX..XXXXXXX 100644
37
index XXXXXXX..XXXXXXX 100644
16
--- a/hw/intc/armv7m_nvic.c
38
--- a/docs/system/arm/emulation.rst
17
+++ b/hw/intc/armv7m_nvic.c
39
+++ b/docs/system/arm/emulation.rst
18
@@ -XXX,XX +XXX,XX @@ static uint32_t nvic_readl(NVICState *s, uint32_t offset, MemTxAttrs attrs)
40
@@ -XXX,XX +XXX,XX @@ the following architecture extensions:
19
}
41
- FEAT_EL2 (Support for execution at EL2)
20
}
42
- FEAT_EL3 (Support for execution at EL3)
21
/* NMIPENDSET */
43
- FEAT_EPAC (Enhanced pointer authentication)
22
- if ((cpu->env.v7m.aircr & R_V7M_AIRCR_BFHFNMINS_MASK) &&
44
-- FEAT_ETS (Enhanced Translation Synchronization)
23
- s->vectors[ARMV7M_EXCP_NMI].pending) {
45
+- FEAT_ETS2 (Enhanced Translation Synchronization)
24
+ if ((attrs.secure || (cpu->env.v7m.aircr & R_V7M_AIRCR_BFHFNMINS_MASK))
46
- FEAT_EVT (Enhanced Virtualization Traps)
25
+ && s->vectors[ARMV7M_EXCP_NMI].pending) {
47
- FEAT_F32MM (Single-precision Matrix Multiplication)
26
val |= (1 << 31);
48
- FEAT_F64MM (Double-precision Matrix Multiplication)
27
}
49
diff --git a/target/arm/tcg/cpu32.c b/target/arm/tcg/cpu32.c
28
/* ISRPREEMPT: RES0 when halting debug not implemented */
50
index XXXXXXX..XXXXXXX 100644
29
@@ -XXX,XX +XXX,XX @@ static void nvic_writel(NVICState *s, uint32_t offset, uint32_t value,
51
--- a/target/arm/tcg/cpu32.c
30
break;
52
+++ b/target/arm/tcg/cpu32.c
31
}
53
@@ -XXX,XX +XXX,XX @@ void aa32_max_features(ARMCPU *cpu)
32
case 0xd04: /* Interrupt Control State (ICSR) */
54
cpu->isar.id_mmfr4 = t;
33
- if (cpu->env.v7m.aircr & R_V7M_AIRCR_BFHFNMINS_MASK) {
55
34
+ if (attrs.secure || cpu->env.v7m.aircr & R_V7M_AIRCR_BFHFNMINS_MASK) {
56
t = cpu->isar.id_mmfr5;
35
if (value & (1 << 31)) {
57
- t = FIELD_DP32(t, ID_MMFR5, ETS, 1); /* FEAT_ETS */
36
armv7m_nvic_set_pending(s, ARMV7M_EXCP_NMI, false);
58
+ t = FIELD_DP32(t, ID_MMFR5, ETS, 2); /* FEAT_ETS2 */
37
} else if (value & (1 << 30) &&
59
cpu->isar.id_mmfr5 = t;
60
61
t = cpu->isar.id_pfr0;
62
diff --git a/target/arm/tcg/cpu64.c b/target/arm/tcg/cpu64.c
63
index XXXXXXX..XXXXXXX 100644
64
--- a/target/arm/tcg/cpu64.c
65
+++ b/target/arm/tcg/cpu64.c
66
@@ -XXX,XX +XXX,XX @@ void aarch64_max_tcg_initfn(Object *obj)
67
t = FIELD_DP64(t, ID_AA64MMFR1, LO, 1); /* FEAT_LOR */
68
t = FIELD_DP64(t, ID_AA64MMFR1, PAN, 3); /* FEAT_PAN3 */
69
t = FIELD_DP64(t, ID_AA64MMFR1, XNX, 1); /* FEAT_XNX */
70
- t = FIELD_DP64(t, ID_AA64MMFR1, ETS, 1); /* FEAT_ETS */
71
+ t = FIELD_DP64(t, ID_AA64MMFR1, ETS, 2); /* FEAT_ETS2 */
72
t = FIELD_DP64(t, ID_AA64MMFR1, HCX, 1); /* FEAT_HCX */
73
t = FIELD_DP64(t, ID_AA64MMFR1, TIDCP1, 1); /* FEAT_TIDCP1 */
74
cpu->isar.id_aa64mmfr1 = t;
38
--
75
--
39
2.16.1
76
2.34.1
40
77
41
78
diff view generated by jsdifflib
1
The v8M architecture includes hardware support for enforcing
1
Newer versions of the Arm ARM (e.g. rev K.a) now define fields for
2
stack pointer limits. We don't implement this behaviour yet,
2
ID_AA64MMFR3_EL1. Implement this register, so that we can set the
3
but provide the MSPLIM and PSPLIM stack pointer limit registers
3
fields if we need to. There's no behaviour change here since we
4
as reads-as-written, so that when we do implement the checks
4
don't currently set the register value to non-zero.
5
in future this won't break guest migration.
6
5
7
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
6
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
8
Reviewed-by: Richard Henderson <richard.henderson@linaro.org>
7
Reviewed-by: Richard Henderson <richard.henderson@linaro.org>
9
Message-id: 20180209165810.6668-12-peter.maydell@linaro.org
8
Reviewed-by: Philippe Mathieu-Daudé <philmd@linaro.org>
9
Message-id: 20240418152004.2106516-5-peter.maydell@linaro.org
10
---
10
---
11
target/arm/cpu.h | 2 ++
11
target/arm/cpu.h | 17 +++++++++++++++++
12
target/arm/helper.c | 46 ++++++++++++++++++++++++++++++++++++++++++++++
12
target/arm/helper.c | 6 ++++--
13
target/arm/machine.c | 21 +++++++++++++++++++++
13
target/arm/hvf/hvf.c | 2 ++
14
3 files changed, 69 insertions(+)
14
target/arm/kvm.c | 2 ++
15
4 files changed, 25 insertions(+), 2 deletions(-)
15
16
16
diff --git a/target/arm/cpu.h b/target/arm/cpu.h
17
diff --git a/target/arm/cpu.h b/target/arm/cpu.h
17
index XXXXXXX..XXXXXXX 100644
18
index XXXXXXX..XXXXXXX 100644
18
--- a/target/arm/cpu.h
19
--- a/target/arm/cpu.h
19
+++ b/target/arm/cpu.h
20
+++ b/target/arm/cpu.h
20
@@ -XXX,XX +XXX,XX @@ typedef struct CPUARMState {
21
@@ -XXX,XX +XXX,XX @@ struct ArchCPU {
21
uint32_t secure; /* Is CPU in Secure state? (not guest visible) */
22
uint64_t id_aa64mmfr0;
22
uint32_t csselr[M_REG_NUM_BANKS];
23
uint64_t id_aa64mmfr1;
23
uint32_t scr[M_REG_NUM_BANKS];
24
uint64_t id_aa64mmfr2;
24
+ uint32_t msplim[M_REG_NUM_BANKS];
25
+ uint64_t id_aa64mmfr3;
25
+ uint32_t psplim[M_REG_NUM_BANKS];
26
uint64_t id_aa64dfr0;
26
} v7m;
27
uint64_t id_aa64dfr1;
27
28
uint64_t id_aa64zfr0;
28
/* Information associated with an exception about to be taken:
29
@@ -XXX,XX +XXX,XX @@ FIELD(ID_AA64MMFR2, BBM, 52, 4)
30
FIELD(ID_AA64MMFR2, EVT, 56, 4)
31
FIELD(ID_AA64MMFR2, E0PD, 60, 4)
32
33
+FIELD(ID_AA64MMFR3, TCRX, 0, 4)
34
+FIELD(ID_AA64MMFR3, SCTLRX, 4, 4)
35
+FIELD(ID_AA64MMFR3, S1PIE, 8, 4)
36
+FIELD(ID_AA64MMFR3, S2PIE, 12, 4)
37
+FIELD(ID_AA64MMFR3, S1POE, 16, 4)
38
+FIELD(ID_AA64MMFR3, S2POE, 20, 4)
39
+FIELD(ID_AA64MMFR3, AIE, 24, 4)
40
+FIELD(ID_AA64MMFR3, MEC, 28, 4)
41
+FIELD(ID_AA64MMFR3, D128, 32, 4)
42
+FIELD(ID_AA64MMFR3, D128_2, 36, 4)
43
+FIELD(ID_AA64MMFR3, SNERR, 40, 4)
44
+FIELD(ID_AA64MMFR3, ANERR, 44, 4)
45
+FIELD(ID_AA64MMFR3, SDERR, 52, 4)
46
+FIELD(ID_AA64MMFR3, ADERR, 56, 4)
47
+FIELD(ID_AA64MMFR3, SPEC_FPACC, 60, 4)
48
+
49
FIELD(ID_AA64DFR0, DEBUGVER, 0, 4)
50
FIELD(ID_AA64DFR0, TRACEVER, 4, 4)
51
FIELD(ID_AA64DFR0, PMUVER, 8, 4)
29
diff --git a/target/arm/helper.c b/target/arm/helper.c
52
diff --git a/target/arm/helper.c b/target/arm/helper.c
30
index XXXXXXX..XXXXXXX 100644
53
index XXXXXXX..XXXXXXX 100644
31
--- a/target/arm/helper.c
54
--- a/target/arm/helper.c
32
+++ b/target/arm/helper.c
55
+++ b/target/arm/helper.c
33
@@ -XXX,XX +XXX,XX @@ uint32_t HELPER(v7m_mrs)(CPUARMState *env, uint32_t reg)
56
@@ -XXX,XX +XXX,XX @@ void register_cp_regs_for_features(ARMCPU *cpu)
34
return 0;
57
.access = PL1_R, .type = ARM_CP_CONST,
35
}
58
.accessfn = access_aa64_tid3,
36
return env->v7m.other_ss_psp;
59
.resetvalue = cpu->isar.id_aa64mmfr2 },
37
+ case 0x8a: /* MSPLIM_NS */
60
- { .name = "ID_AA64MMFR3_EL1_RESERVED", .state = ARM_CP_STATE_AA64,
38
+ if (!env->v7m.secure) {
61
+ { .name = "ID_AA64MMFR3_EL1", .state = ARM_CP_STATE_AA64,
39
+ return 0;
62
.opc0 = 3, .opc1 = 0, .crn = 0, .crm = 7, .opc2 = 3,
40
+ }
63
.access = PL1_R, .type = ARM_CP_CONST,
41
+ return env->v7m.msplim[M_REG_NS];
64
.accessfn = access_aa64_tid3,
42
+ case 0x8b: /* PSPLIM_NS */
65
- .resetvalue = 0 },
43
+ if (!env->v7m.secure) {
66
+ .resetvalue = cpu->isar.id_aa64mmfr3 },
44
+ return 0;
67
{ .name = "ID_AA64MMFR4_EL1_RESERVED", .state = ARM_CP_STATE_AA64,
45
+ }
68
.opc0 = 3, .opc1 = 0, .crn = 0, .crm = 7, .opc2 = 4,
46
+ return env->v7m.psplim[M_REG_NS];
69
.access = PL1_R, .type = ARM_CP_CONST,
47
case 0x90: /* PRIMASK_NS */
70
@@ -XXX,XX +XXX,XX @@ void register_cp_regs_for_features(ARMCPU *cpu)
48
if (!env->v7m.secure) {
71
.exported_bits = R_ID_AA64MMFR1_AFP_MASK },
49
return 0;
72
{ .name = "ID_AA64MMFR2_EL1",
50
@@ -XXX,XX +XXX,XX @@ uint32_t HELPER(v7m_mrs)(CPUARMState *env, uint32_t reg)
73
.exported_bits = R_ID_AA64MMFR2_AT_MASK },
51
return v7m_using_psp(env) ? env->v7m.other_sp : env->regs[13];
74
+ { .name = "ID_AA64MMFR3_EL1",
52
case 9: /* PSP */
75
+ .exported_bits = 0 },
53
return v7m_using_psp(env) ? env->regs[13] : env->v7m.other_sp;
76
{ .name = "ID_AA64MMFR*_EL1_RESERVED",
54
+ case 10: /* MSPLIM */
77
.is_glob = true },
55
+ if (!arm_feature(env, ARM_FEATURE_V8)) {
78
{ .name = "ID_AA64DFR0_EL1",
56
+ goto bad_reg;
79
diff --git a/target/arm/hvf/hvf.c b/target/arm/hvf/hvf.c
57
+ }
58
+ return env->v7m.msplim[env->v7m.secure];
59
+ case 11: /* PSPLIM */
60
+ if (!arm_feature(env, ARM_FEATURE_V8)) {
61
+ goto bad_reg;
62
+ }
63
+ return env->v7m.psplim[env->v7m.secure];
64
case 16: /* PRIMASK */
65
return env->v7m.primask[env->v7m.secure];
66
case 17: /* BASEPRI */
67
@@ -XXX,XX +XXX,XX @@ uint32_t HELPER(v7m_mrs)(CPUARMState *env, uint32_t reg)
68
case 19: /* FAULTMASK */
69
return env->v7m.faultmask[env->v7m.secure];
70
default:
71
+ bad_reg:
72
qemu_log_mask(LOG_GUEST_ERROR, "Attempt to read unknown special"
73
" register %d\n", reg);
74
return 0;
75
@@ -XXX,XX +XXX,XX @@ void HELPER(v7m_msr)(CPUARMState *env, uint32_t maskreg, uint32_t val)
76
}
77
env->v7m.other_ss_psp = val;
78
return;
79
+ case 0x8a: /* MSPLIM_NS */
80
+ if (!env->v7m.secure) {
81
+ return;
82
+ }
83
+ env->v7m.msplim[M_REG_NS] = val & ~7;
84
+ return;
85
+ case 0x8b: /* PSPLIM_NS */
86
+ if (!env->v7m.secure) {
87
+ return;
88
+ }
89
+ env->v7m.psplim[M_REG_NS] = val & ~7;
90
+ return;
91
case 0x90: /* PRIMASK_NS */
92
if (!env->v7m.secure) {
93
return;
94
@@ -XXX,XX +XXX,XX @@ void HELPER(v7m_msr)(CPUARMState *env, uint32_t maskreg, uint32_t val)
95
env->v7m.other_sp = val;
96
}
97
break;
98
+ case 10: /* MSPLIM */
99
+ if (!arm_feature(env, ARM_FEATURE_V8)) {
100
+ goto bad_reg;
101
+ }
102
+ env->v7m.msplim[env->v7m.secure] = val & ~7;
103
+ break;
104
+ case 11: /* PSPLIM */
105
+ if (!arm_feature(env, ARM_FEATURE_V8)) {
106
+ goto bad_reg;
107
+ }
108
+ env->v7m.psplim[env->v7m.secure] = val & ~7;
109
+ break;
110
case 16: /* PRIMASK */
111
env->v7m.primask[env->v7m.secure] = val & 1;
112
break;
113
@@ -XXX,XX +XXX,XX @@ void HELPER(v7m_msr)(CPUARMState *env, uint32_t maskreg, uint32_t val)
114
env->v7m.control[env->v7m.secure] |= val & R_V7M_CONTROL_NPRIV_MASK;
115
break;
116
default:
117
+ bad_reg:
118
qemu_log_mask(LOG_GUEST_ERROR, "Attempt to write unknown special"
119
" register %d\n", reg);
120
return;
121
diff --git a/target/arm/machine.c b/target/arm/machine.c
122
index XXXXXXX..XXXXXXX 100644
80
index XXXXXXX..XXXXXXX 100644
123
--- a/target/arm/machine.c
81
--- a/target/arm/hvf/hvf.c
124
+++ b/target/arm/machine.c
82
+++ b/target/arm/hvf/hvf.c
125
@@ -XXX,XX +XXX,XX @@ static const VMStateDescription vmstate_m_other_sp = {
83
@@ -XXX,XX +XXX,XX @@ static struct hvf_sreg_match hvf_sreg_match[] = {
126
}
84
#endif
127
};
85
{ HV_SYS_REG_ID_AA64MMFR1_EL1, HVF_SYSREG(0, 7, 3, 0, 1) },
128
86
{ HV_SYS_REG_ID_AA64MMFR2_EL1, HVF_SYSREG(0, 7, 3, 0, 2) },
129
+static bool m_v8m_needed(void *opaque)
87
+ /* Add ID_AA64MMFR3_EL1 here when HVF supports it */
130
+{
88
131
+ ARMCPU *cpu = opaque;
89
{ HV_SYS_REG_MDSCR_EL1, HVF_SYSREG(0, 2, 2, 0, 2) },
132
+ CPUARMState *env = &cpu->env;
90
{ HV_SYS_REG_SCTLR_EL1, HVF_SYSREG(1, 0, 3, 0, 0) },
133
+
91
@@ -XXX,XX +XXX,XX @@ static bool hvf_arm_get_host_cpu_features(ARMHostCPUFeatures *ahcf)
134
+ return arm_feature(env, ARM_FEATURE_M) && arm_feature(env, ARM_FEATURE_V8);
92
{ HV_SYS_REG_ID_AA64MMFR0_EL1, &host_isar.id_aa64mmfr0 },
135
+}
93
{ HV_SYS_REG_ID_AA64MMFR1_EL1, &host_isar.id_aa64mmfr1 },
136
+
94
{ HV_SYS_REG_ID_AA64MMFR2_EL1, &host_isar.id_aa64mmfr2 },
137
+static const VMStateDescription vmstate_m_v8m = {
95
+ /* Add ID_AA64MMFR3_EL1 here when HVF supports it */
138
+ .name = "cpu/m/v8m",
96
};
139
+ .version_id = 1,
97
hv_vcpu_t fd;
140
+ .minimum_version_id = 1,
98
hv_return_t r = HV_SUCCESS;
141
+ .needed = m_v8m_needed,
99
diff --git a/target/arm/kvm.c b/target/arm/kvm.c
142
+ .fields = (VMStateField[]) {
100
index XXXXXXX..XXXXXXX 100644
143
+ VMSTATE_UINT32_ARRAY(env.v7m.msplim, ARMCPU, M_REG_NUM_BANKS),
101
--- a/target/arm/kvm.c
144
+ VMSTATE_UINT32_ARRAY(env.v7m.psplim, ARMCPU, M_REG_NUM_BANKS),
102
+++ b/target/arm/kvm.c
145
+ VMSTATE_END_OF_LIST()
103
@@ -XXX,XX +XXX,XX @@ static bool kvm_arm_get_host_cpu_features(ARMHostCPUFeatures *ahcf)
146
+ }
104
ARM64_SYS_REG(3, 0, 0, 7, 1));
147
+};
105
err |= read_sys_reg64(fdarray[2], &ahcf->isar.id_aa64mmfr2,
148
+
106
ARM64_SYS_REG(3, 0, 0, 7, 2));
149
static const VMStateDescription vmstate_m = {
107
+ err |= read_sys_reg64(fdarray[2], &ahcf->isar.id_aa64mmfr3,
150
.name = "cpu/m",
108
+ ARM64_SYS_REG(3, 0, 0, 7, 3));
151
.version_id = 4,
109
152
@@ -XXX,XX +XXX,XX @@ static const VMStateDescription vmstate_m = {
110
/*
153
&vmstate_m_csselr,
111
* Note that if AArch32 support is not present in the host,
154
&vmstate_m_scr,
155
&vmstate_m_other_sp,
156
+ &vmstate_m_v8m,
157
NULL
158
}
159
};
160
--
112
--
161
2.16.1
113
2.34.1
162
114
163
115
diff view generated by jsdifflib
1
The Coprocessor Power Control Register (CPPWR) is new in v8M.
1
FEAT_Spec_FPACC is a feature describing speculative behaviour in the
2
It allows software to control whether coprocessors are allowed
2
event of a PAC authontication failure when FEAT_FPACCOMBINE is
3
to power down and lose their state. QEMU doesn't have any
3
implemented. FEAT_Spec_FPACC means that the speculative use of
4
notion of power control, so we choose the IMPDEF option of
4
pointers processed by a PAC Authentication is not materially
5
making the whole register RAZ/WI (indicating that no coprocessors
5
different in terms of the impact on cached microarchitectural state
6
can ever power down and lose state).
6
(caches, TLBs, etc) between passing and failing of the PAC
7
Authentication.
8
9
QEMU doesn't do speculative execution, so we can advertise
10
this feature.
7
11
8
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
12
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
9
Reviewed-by: Richard Henderson <richard.henderson@linaro.org>
13
Reviewed-by: Richard Henderson <richard.henderson@linaro.org>
10
Message-id: 20180209165810.6668-5-peter.maydell@linaro.org
14
Reviewed-by: Philippe Mathieu-Daudé <philmd@linaro.org>
15
Message-id: 20240418152004.2106516-6-peter.maydell@linaro.org
11
---
16
---
12
hw/intc/armv7m_nvic.c | 14 ++++++++++++++
17
docs/system/arm/emulation.rst | 1 +
13
1 file changed, 14 insertions(+)
18
target/arm/tcg/cpu64.c | 4 ++++
19
2 files changed, 5 insertions(+)
14
20
15
diff --git a/hw/intc/armv7m_nvic.c b/hw/intc/armv7m_nvic.c
21
diff --git a/docs/system/arm/emulation.rst b/docs/system/arm/emulation.rst
16
index XXXXXXX..XXXXXXX 100644
22
index XXXXXXX..XXXXXXX 100644
17
--- a/hw/intc/armv7m_nvic.c
23
--- a/docs/system/arm/emulation.rst
18
+++ b/hw/intc/armv7m_nvic.c
24
+++ b/docs/system/arm/emulation.rst
19
@@ -XXX,XX +XXX,XX @@ static uint32_t nvic_readl(NVICState *s, uint32_t offset, MemTxAttrs attrs)
25
@@ -XXX,XX +XXX,XX @@ the following architecture extensions:
20
switch (offset) {
26
- FEAT_FP16 (Half-precision floating-point data processing)
21
case 4: /* Interrupt Control Type. */
27
- FEAT_FPAC (Faulting on AUT* instructions)
22
return ((s->num_irq - NVIC_FIRST_IRQ) / 32) - 1;
28
- FEAT_FPACCOMBINE (Faulting on combined pointer authentication instructions)
23
+ case 0xc: /* CPPWR */
29
+- FEAT_FPACC_SPEC (Speculative behavior of combined pointer authentication instructions)
24
+ if (!arm_feature(&cpu->env, ARM_FEATURE_V8)) {
30
- FEAT_FRINTTS (Floating-point to integer instructions)
25
+ goto bad_offset;
31
- FEAT_FlagM (Flag manipulation instructions v2)
26
+ }
32
- FEAT_FlagM2 (Enhancements to flag manipulation instructions)
27
+ /* We make the IMPDEF choice that nothing can ever go into a
33
diff --git a/target/arm/tcg/cpu64.c b/target/arm/tcg/cpu64.c
28
+ * non-retentive power state, which allows us to RAZ/WI this.
34
index XXXXXXX..XXXXXXX 100644
29
+ */
35
--- a/target/arm/tcg/cpu64.c
30
+ return 0;
36
+++ b/target/arm/tcg/cpu64.c
31
case 0x380 ... 0x3bf: /* NVIC_ITNS<n> */
37
@@ -XXX,XX +XXX,XX @@ void aarch64_max_tcg_initfn(Object *obj)
32
{
38
t = FIELD_DP64(t, ID_AA64MMFR2, E0PD, 1); /* FEAT_E0PD */
33
int startvec = 8 * (offset - 0x380) + NVIC_FIRST_IRQ;
39
cpu->isar.id_aa64mmfr2 = t;
34
@@ -XXX,XX +XXX,XX @@ static void nvic_writel(NVICState *s, uint32_t offset, uint32_t value,
40
35
ARMCPU *cpu = s->cpu;
41
+ t = cpu->isar.id_aa64mmfr3;
36
42
+ t = FIELD_DP64(t, ID_AA64MMFR3, SPEC_FPACC, 1); /* FEAT_FPACC_SPEC */
37
switch (offset) {
43
+ cpu->isar.id_aa64mmfr3 = t;
38
+ case 0xc: /* CPPWR */
44
+
39
+ if (!arm_feature(&cpu->env, ARM_FEATURE_V8)) {
45
t = cpu->isar.id_aa64zfr0;
40
+ goto bad_offset;
46
t = FIELD_DP64(t, ID_AA64ZFR0, SVEVER, 1);
41
+ }
47
t = FIELD_DP64(t, ID_AA64ZFR0, AES, 2); /* FEAT_SVE_PMULL128 */
42
+ /* Make the IMPDEF choice to RAZ/WI this. */
43
+ break;
44
case 0x380 ... 0x3bf: /* NVIC_ITNS<n> */
45
{
46
int startvec = 8 * (offset - 0x380) + NVIC_FIRST_IRQ;
47
--
48
--
48
2.16.1
49
2.34.1
49
50
50
51
diff view generated by jsdifflib
1
In many of the NVIC registers relating to interrupts, we
1
The Linux kernel 5.10.16 binary for sunxi has been removed from
2
have to convert from a byte offset within a register set
2
apt.armbian.com. This means that the avocado tests for these machines
3
into the number of the first interrupt which is affected.
3
will be skipped (status CANCEL) if the old binary isn't present in
4
We were getting this wrong for:
4
the avocado cache.
5
* reads of NVIC_ISPR<n>, NVIC_ISER<n>, NVIC_ICPR<n>, NVIC_ICER<n>,
6
NVIC_IABR<n> -- in all these cases we were missing the "* 8"
7
needed to convert from the byte offset to the interrupt number
8
(since all these registers use one bit per interrupt)
9
* writes of NVIC_IPR<n> had the opposite problem of a spurious
10
"* 8" (since these registers use one byte per interrupt)
11
5
6
Update to 6.6.16, in the same way we did in commit e384db41d8661
7
when we moved to 5.10.16 in 2021.
8
9
Cc: qemu-stable@nongnu.org
10
Resolves: https://gitlab.com/qemu-project/qemu/-/issues/2284
12
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
11
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
13
Reviewed-by: Philippe Mathieu-Daudé <f4bug@amsat.org>
12
Reviewed-by: Strahinja Jankovic <strahinja.p.jankovic@gmail.com>
14
Message-id: 20180209165810.6668-9-peter.maydell@linaro.org
13
Reviewed-by: Niek Linnenbank <nieklinnenbank@gmail.com>
14
Tested-by: Niek Linnenbank <nieklinnenbank@gmail.com>
15
Message-id: 20240415151845.1564201-1-peter.maydell@linaro.org
15
---
16
---
16
hw/intc/armv7m_nvic.c | 8 ++++----
17
tests/avocado/boot_linux_console.py | 70 ++++++++++++++---------------
17
1 file changed, 4 insertions(+), 4 deletions(-)
18
tests/avocado/replay_kernel.py | 8 ++--
19
2 files changed, 39 insertions(+), 39 deletions(-)
18
20
19
diff --git a/hw/intc/armv7m_nvic.c b/hw/intc/armv7m_nvic.c
21
diff --git a/tests/avocado/boot_linux_console.py b/tests/avocado/boot_linux_console.py
20
index XXXXXXX..XXXXXXX 100644
22
index XXXXXXX..XXXXXXX 100644
21
--- a/hw/intc/armv7m_nvic.c
23
--- a/tests/avocado/boot_linux_console.py
22
+++ b/hw/intc/armv7m_nvic.c
24
+++ b/tests/avocado/boot_linux_console.py
23
@@ -XXX,XX +XXX,XX @@ static MemTxResult nvic_sysreg_read(void *opaque, hwaddr addr,
25
@@ -XXX,XX +XXX,XX @@ def test_arm_cubieboard_initrd(self):
24
/* fall through */
26
:avocado: tags=accel:tcg
25
case 0x180 ... 0x1bf: /* NVIC Clear enable */
27
"""
26
val = 0;
28
deb_url = ('https://apt.armbian.com/pool/main/l/'
27
- startvec = offset - 0x180 + NVIC_FIRST_IRQ; /* vector # */
29
- 'linux-5.10.16-sunxi/linux-image-current-sunxi_21.02.2_armhf.deb')
28
+ startvec = 8 * (offset - 0x180) + NVIC_FIRST_IRQ; /* vector # */
30
- deb_hash = '9fa84beda245cabf0b4fa84cf6eaa7738ead1da0'
29
31
+ 'linux-6.6.16/linux-image-current-sunxi_24.2.1_armhf__6.6.16-Seb3e-D6b4a-P2359-Ce96bHfe66-HK01ba-V014b-B067e-R448a.deb')
30
for (i = 0, end = size * 8; i < end && startvec + i < s->num_irq; i++) {
32
+ deb_hash = 'f7c3c8c5432f765445dc6e7eab02f3bbe668256b'
31
if (s->vectors[startvec + i].enabled &&
33
deb_path = self.fetch_asset(deb_url, asset_hash=deb_hash)
32
@@ -XXX,XX +XXX,XX @@ static MemTxResult nvic_sysreg_read(void *opaque, hwaddr addr,
34
kernel_path = self.extract_from_deb(deb_path,
33
/* fall through */
35
- '/boot/vmlinuz-5.10.16-sunxi')
34
case 0x280 ... 0x2bf: /* NVIC Clear pend */
36
- dtb_path = '/usr/lib/linux-image-current-sunxi/sun4i-a10-cubieboard.dtb'
35
val = 0;
37
+ '/boot/vmlinuz-6.6.16-current-sunxi')
36
- startvec = offset - 0x280 + NVIC_FIRST_IRQ; /* vector # */
38
+ dtb_path = '/usr/lib/linux-image-6.6.16-current-sunxi/sun4i-a10-cubieboard.dtb'
37
+ startvec = 8 * (offset - 0x280) + NVIC_FIRST_IRQ; /* vector # */
39
dtb_path = self.extract_from_deb(deb_path, dtb_path)
38
for (i = 0, end = size * 8; i < end && startvec + i < s->num_irq; i++) {
40
initrd_url = ('https://github.com/groeck/linux-build-test/raw/'
39
if (s->vectors[startvec + i].pending &&
41
'2eb0a73b5d5a28df3170c546ddaaa9757e1e0848/rootfs/'
40
(attrs.secure || s->itns[startvec + i])) {
42
@@ -XXX,XX +XXX,XX @@ def test_arm_cubieboard_sata(self):
41
@@ -XXX,XX +XXX,XX @@ static MemTxResult nvic_sysreg_read(void *opaque, hwaddr addr,
43
:avocado: tags=accel:tcg
42
break;
44
"""
43
case 0x300 ... 0x33f: /* NVIC Active */
45
deb_url = ('https://apt.armbian.com/pool/main/l/'
44
val = 0;
46
- 'linux-5.10.16-sunxi/linux-image-current-sunxi_21.02.2_armhf.deb')
45
- startvec = offset - 0x300 + NVIC_FIRST_IRQ; /* vector # */
47
- deb_hash = '9fa84beda245cabf0b4fa84cf6eaa7738ead1da0'
46
+ startvec = 8 * (offset - 0x300) + NVIC_FIRST_IRQ; /* vector # */
48
+ 'linux-6.6.16/linux-image-current-sunxi_24.2.1_armhf__6.6.16-Seb3e-D6b4a-P2359-Ce96bHfe66-HK01ba-V014b-B067e-R448a.deb')
47
49
+ deb_hash = 'f7c3c8c5432f765445dc6e7eab02f3bbe668256b'
48
for (i = 0, end = size * 8; i < end && startvec + i < s->num_irq; i++) {
50
deb_path = self.fetch_asset(deb_url, asset_hash=deb_hash)
49
if (s->vectors[startvec + i].active &&
51
kernel_path = self.extract_from_deb(deb_path,
50
@@ -XXX,XX +XXX,XX @@ static MemTxResult nvic_sysreg_write(void *opaque, hwaddr addr,
52
- '/boot/vmlinuz-5.10.16-sunxi')
51
case 0x300 ... 0x33f: /* NVIC Active */
53
- dtb_path = '/usr/lib/linux-image-current-sunxi/sun4i-a10-cubieboard.dtb'
52
return MEMTX_OK; /* R/O */
54
+ '/boot/vmlinuz-6.6.16-current-sunxi')
53
case 0x400 ... 0x5ef: /* NVIC Priority */
55
+ dtb_path = '/usr/lib/linux-image-6.6.16-current-sunxi/sun4i-a10-cubieboard.dtb'
54
- startvec = 8 * (offset - 0x400) + NVIC_FIRST_IRQ; /* vector # */
56
dtb_path = self.extract_from_deb(deb_path, dtb_path)
55
+ startvec = (offset - 0x400) + NVIC_FIRST_IRQ; /* vector # */
57
rootfs_url = ('https://github.com/groeck/linux-build-test/raw/'
56
58
'2eb0a73b5d5a28df3170c546ddaaa9757e1e0848/rootfs/'
57
for (i = 0; i < size && startvec + i < s->num_irq; i++) {
59
@@ -XXX,XX +XXX,XX @@ def test_arm_bpim2u(self):
58
if (attrs.secure || s->itns[startvec + i]) {
60
:avocado: tags=machine:bpim2u
61
:avocado: tags=accel:tcg
62
"""
63
- deb_url = ('https://apt.armbian.com/pool/main/l/linux-5.10.16-sunxi/'
64
- 'linux-image-current-sunxi_21.02.2_armhf.deb')
65
- deb_hash = '9fa84beda245cabf0b4fa84cf6eaa7738ead1da0'
66
+ deb_url = ('https://apt.armbian.com/pool/main/l/'
67
+ 'linux-6.6.16/linux-image-current-sunxi_24.2.1_armhf__6.6.16-Seb3e-D6b4a-P2359-Ce96bHfe66-HK01ba-V014b-B067e-R448a.deb')
68
+ deb_hash = 'f7c3c8c5432f765445dc6e7eab02f3bbe668256b'
69
deb_path = self.fetch_asset(deb_url, asset_hash=deb_hash)
70
kernel_path = self.extract_from_deb(deb_path,
71
- '/boot/vmlinuz-5.10.16-sunxi')
72
- dtb_path = ('/usr/lib/linux-image-current-sunxi/'
73
+ '/boot/vmlinuz-6.6.16-current-sunxi')
74
+ dtb_path = ('/usr/lib/linux-image-6.6.16-current-sunxi/'
75
'sun8i-r40-bananapi-m2-ultra.dtb')
76
dtb_path = self.extract_from_deb(deb_path, dtb_path)
77
78
@@ -XXX,XX +XXX,XX @@ def test_arm_bpim2u_initrd(self):
79
:avocado: tags=accel:tcg
80
:avocado: tags=machine:bpim2u
81
"""
82
- deb_url = ('https://apt.armbian.com/pool/main/l/linux-5.10.16-sunxi/'
83
- 'linux-image-current-sunxi_21.02.2_armhf.deb')
84
- deb_hash = '9fa84beda245cabf0b4fa84cf6eaa7738ead1da0'
85
+ deb_url = ('https://apt.armbian.com/pool/main/l/'
86
+ 'linux-6.6.16/linux-image-current-sunxi_24.2.1_armhf__6.6.16-Seb3e-D6b4a-P2359-Ce96bHfe66-HK01ba-V014b-B067e-R448a.deb')
87
+ deb_hash = 'f7c3c8c5432f765445dc6e7eab02f3bbe668256b'
88
deb_path = self.fetch_asset(deb_url, asset_hash=deb_hash)
89
kernel_path = self.extract_from_deb(deb_path,
90
- '/boot/vmlinuz-5.10.16-sunxi')
91
- dtb_path = ('/usr/lib/linux-image-current-sunxi/'
92
+ '/boot/vmlinuz-6.6.16-current-sunxi')
93
+ dtb_path = ('/usr/lib/linux-image-6.6.16-current-sunxi/'
94
'sun8i-r40-bananapi-m2-ultra.dtb')
95
dtb_path = self.extract_from_deb(deb_path, dtb_path)
96
initrd_url = ('https://github.com/groeck/linux-build-test/raw/'
97
@@ -XXX,XX +XXX,XX @@ def test_arm_bpim2u_gmac(self):
98
"""
99
self.require_netdev('user')
100
101
- deb_url = ('https://apt.armbian.com/pool/main/l/linux-5.10.16-sunxi/'
102
- 'linux-image-current-sunxi_21.02.2_armhf.deb')
103
- deb_hash = '9fa84beda245cabf0b4fa84cf6eaa7738ead1da0'
104
+ deb_url = ('https://apt.armbian.com/pool/main/l/'
105
+ 'linux-6.6.16/linux-image-current-sunxi_24.2.1_armhf__6.6.16-Seb3e-D6b4a-P2359-Ce96bHfe66-HK01ba-V014b-B067e-R448a.deb')
106
+ deb_hash = 'f7c3c8c5432f765445dc6e7eab02f3bbe668256b'
107
deb_path = self.fetch_asset(deb_url, asset_hash=deb_hash)
108
kernel_path = self.extract_from_deb(deb_path,
109
- '/boot/vmlinuz-5.10.16-sunxi')
110
- dtb_path = ('/usr/lib/linux-image-current-sunxi/'
111
+ '/boot/vmlinuz-6.6.16-current-sunxi')
112
+ dtb_path = ('/usr/lib/linux-image-6.6.16-current-sunxi/'
113
'sun8i-r40-bananapi-m2-ultra.dtb')
114
dtb_path = self.extract_from_deb(deb_path, dtb_path)
115
rootfs_url = ('http://storage.kernelci.org/images/rootfs/buildroot/'
116
@@ -XXX,XX +XXX,XX @@ def test_arm_orangepi(self):
117
:avocado: tags=accel:tcg
118
"""
119
deb_url = ('https://apt.armbian.com/pool/main/l/'
120
- 'linux-5.10.16-sunxi/linux-image-current-sunxi_21.02.2_armhf.deb')
121
- deb_hash = '9fa84beda245cabf0b4fa84cf6eaa7738ead1da0'
122
+ 'linux-6.6.16/linux-image-current-sunxi_24.2.1_armhf__6.6.16-Seb3e-D6b4a-P2359-Ce96bHfe66-HK01ba-V014b-B067e-R448a.deb')
123
+ deb_hash = 'f7c3c8c5432f765445dc6e7eab02f3bbe668256b'
124
deb_path = self.fetch_asset(deb_url, asset_hash=deb_hash)
125
kernel_path = self.extract_from_deb(deb_path,
126
- '/boot/vmlinuz-5.10.16-sunxi')
127
- dtb_path = '/usr/lib/linux-image-current-sunxi/sun8i-h3-orangepi-pc.dtb'
128
+ '/boot/vmlinuz-6.6.16-current-sunxi')
129
+ dtb_path = '/usr/lib/linux-image-6.6.16-current-sunxi/sun8i-h3-orangepi-pc.dtb'
130
dtb_path = self.extract_from_deb(deb_path, dtb_path)
131
132
self.vm.set_console()
133
@@ -XXX,XX +XXX,XX @@ def test_arm_orangepi_initrd(self):
134
:avocado: tags=machine:orangepi-pc
135
"""
136
deb_url = ('https://apt.armbian.com/pool/main/l/'
137
- 'linux-5.10.16-sunxi/linux-image-current-sunxi_21.02.2_armhf.deb')
138
- deb_hash = '9fa84beda245cabf0b4fa84cf6eaa7738ead1da0'
139
+ 'linux-6.6.16/linux-image-current-sunxi_24.2.1_armhf__6.6.16-Seb3e-D6b4a-P2359-Ce96bHfe66-HK01ba-V014b-B067e-R448a.deb')
140
+ deb_hash = 'f7c3c8c5432f765445dc6e7eab02f3bbe668256b'
141
deb_path = self.fetch_asset(deb_url, asset_hash=deb_hash)
142
kernel_path = self.extract_from_deb(deb_path,
143
- '/boot/vmlinuz-5.10.16-sunxi')
144
- dtb_path = '/usr/lib/linux-image-current-sunxi/sun8i-h3-orangepi-pc.dtb'
145
+ '/boot/vmlinuz-6.6.16-current-sunxi')
146
+ dtb_path = '/usr/lib/linux-image-6.6.16-current-sunxi/sun8i-h3-orangepi-pc.dtb'
147
dtb_path = self.extract_from_deb(deb_path, dtb_path)
148
initrd_url = ('https://github.com/groeck/linux-build-test/raw/'
149
'2eb0a73b5d5a28df3170c546ddaaa9757e1e0848/rootfs/'
150
@@ -XXX,XX +XXX,XX @@ def test_arm_orangepi_sd(self):
151
self.require_netdev('user')
152
153
deb_url = ('https://apt.armbian.com/pool/main/l/'
154
- 'linux-5.10.16-sunxi/linux-image-current-sunxi_21.02.2_armhf.deb')
155
- deb_hash = '9fa84beda245cabf0b4fa84cf6eaa7738ead1da0'
156
+ 'linux-6.6.16/linux-image-current-sunxi_24.2.1_armhf__6.6.16-Seb3e-D6b4a-P2359-Ce96bHfe66-HK01ba-V014b-B067e-R448a.deb')
157
+ deb_hash = 'f7c3c8c5432f765445dc6e7eab02f3bbe668256b'
158
deb_path = self.fetch_asset(deb_url, asset_hash=deb_hash)
159
kernel_path = self.extract_from_deb(deb_path,
160
- '/boot/vmlinuz-5.10.16-sunxi')
161
- dtb_path = '/usr/lib/linux-image-current-sunxi/sun8i-h3-orangepi-pc.dtb'
162
+ '/boot/vmlinuz-6.6.16-current-sunxi')
163
+ dtb_path = '/usr/lib/linux-image-6.6.16-current-sunxi/sun8i-h3-orangepi-pc.dtb'
164
dtb_path = self.extract_from_deb(deb_path, dtb_path)
165
rootfs_url = ('http://storage.kernelci.org/images/rootfs/buildroot/'
166
'buildroot-baseline/20221116.0/armel/rootfs.ext2.xz')
167
diff --git a/tests/avocado/replay_kernel.py b/tests/avocado/replay_kernel.py
168
index XXXXXXX..XXXXXXX 100644
169
--- a/tests/avocado/replay_kernel.py
170
+++ b/tests/avocado/replay_kernel.py
171
@@ -XXX,XX +XXX,XX @@ def test_arm_cubieboard_initrd(self):
172
:avocado: tags=machine:cubieboard
173
"""
174
deb_url = ('https://apt.armbian.com/pool/main/l/'
175
- 'linux-5.10.16-sunxi/linux-image-current-sunxi_21.02.2_armhf.deb')
176
- deb_hash = '9fa84beda245cabf0b4fa84cf6eaa7738ead1da0'
177
+ 'linux-6.6.16/linux-image-current-sunxi_24.2.1_armhf__6.6.16-Seb3e-D6b4a-P2359-Ce96bHfe66-HK01ba-V014b-B067e-R448a.deb')
178
+ deb_hash = 'f7c3c8c5432f765445dc6e7eab02f3bbe668256b'
179
deb_path = self.fetch_asset(deb_url, asset_hash=deb_hash)
180
kernel_path = self.extract_from_deb(deb_path,
181
- '/boot/vmlinuz-5.10.16-sunxi')
182
- dtb_path = '/usr/lib/linux-image-current-sunxi/sun4i-a10-cubieboard.dtb'
183
+ '/boot/vmlinuz-6.6.16-current-sunxi')
184
+ dtb_path = '/usr/lib/linux-image-6.6.16-current-sunxi/sun4i-a10-cubieboard.dtb'
185
dtb_path = self.extract_from_deb(deb_path, dtb_path)
186
initrd_url = ('https://github.com/groeck/linux-build-test/raw/'
187
'2eb0a73b5d5a28df3170c546ddaaa9757e1e0848/rootfs/'
59
--
188
--
60
2.16.1
189
2.34.1
61
62
diff view generated by jsdifflib
1
From: Richard Henderson <richard.henderson@linaro.org>
1
The generic timer frequency is settable by board code via a QOM
2
property "cntfrq", but otherwise defaults to 62.5MHz. The way this
3
is done includes some complication resulting from how this was
4
originally a fixed value with no QOM property. Clean it up:
2
5
3
This also makes sure that we get the correct ordering of
6
* always set cpu->gt_cntfrq_hz to some sensible value, whether
4
SVE vs FP exceptions.
7
the CPU has the generic timer or not, and whether it's system
8
or user-only emulation
9
* this means we can always use gt_cntfrq_hz, and never need
10
the old GTIMER_SCALE define
11
* set the default value in exactly one place, in the realize fn
5
12
6
Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
13
The aim here is to pave the way for handling the ARMv8.6 requirement
7
Message-id: 20180211205848.4568-5-richard.henderson@linaro.org
14
that the generic timer frequency is always 1GHz. We're going to do
8
Reviewed-by: Peter Maydell <peter.maydell@linaro.org>
15
that by having old CPU types keep their legacy-in-QEMU behaviour and
16
having the default for any new CPU types be a 1GHz rather han 62.5MHz
17
cntfrq, so we want the point where the default is decided to be in
18
one place, and in code, not in a DEFINE_PROP_UINT64() initializer.
19
20
This commit should have no behavioural changes.
21
9
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
22
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
23
Reviewed-by: Philippe Mathieu-Daudé <philmd@linaro.org>
24
Reviewed-by: Richard Henderson <richard.henderson@linaro.org>
25
Message-id: 20240426122913.3427983-2-peter.maydell@linaro.org
10
---
26
---
11
target/arm/cpu.h | 3 ++-
27
target/arm/internals.h | 7 ++++---
12
target/arm/internals.h | 6 ++++++
28
target/arm/cpu.c | 31 +++++++++++++++++--------------
13
target/arm/helper.c | 22 ++++------------------
29
target/arm/helper.c | 16 ++++++++--------
14
target/arm/translate-a64.c | 16 ++++++++++++++++
30
3 files changed, 29 insertions(+), 25 deletions(-)
15
4 files changed, 28 insertions(+), 19 deletions(-)
16
31
17
diff --git a/target/arm/cpu.h b/target/arm/cpu.h
18
index XXXXXXX..XXXXXXX 100644
19
--- a/target/arm/cpu.h
20
+++ b/target/arm/cpu.h
21
@@ -XXX,XX +XXX,XX @@ static inline uint64_t cpreg_to_kvm_id(uint32_t cpregid)
22
#define ARM_CP_DC_ZVA (ARM_CP_SPECIAL | 0x0500)
23
#define ARM_LAST_SPECIAL ARM_CP_DC_ZVA
24
#define ARM_CP_FPU 0x1000
25
+#define ARM_CP_SVE 0x2000
26
/* Used only as a terminator for ARMCPRegInfo lists */
27
#define ARM_CP_SENTINEL 0xffff
28
/* Mask of only the flag bits in a type field */
29
-#define ARM_CP_FLAG_MASK 0x10ff
30
+#define ARM_CP_FLAG_MASK 0x30ff
31
32
/* Valid values for ARMCPRegInfo state field, indicating which of
33
* the AArch32 and AArch64 execution states this register is visible in.
34
diff --git a/target/arm/internals.h b/target/arm/internals.h
32
diff --git a/target/arm/internals.h b/target/arm/internals.h
35
index XXXXXXX..XXXXXXX 100644
33
index XXXXXXX..XXXXXXX 100644
36
--- a/target/arm/internals.h
34
--- a/target/arm/internals.h
37
+++ b/target/arm/internals.h
35
+++ b/target/arm/internals.h
38
@@ -XXX,XX +XXX,XX @@ enum arm_exception_class {
36
@@ -XXX,XX +XXX,XX @@ static inline bool excp_is_internal(int excp)
39
EC_AA64_HVC = 0x16,
37
|| excp == EXCP_SEMIHOST;
40
EC_AA64_SMC = 0x17,
41
EC_SYSTEMREGISTERTRAP = 0x18,
42
+ EC_SVEACCESSTRAP = 0x19,
43
EC_INSNABORT = 0x20,
44
EC_INSNABORT_SAME_EL = 0x21,
45
EC_PCALIGNMENT = 0x22,
46
@@ -XXX,XX +XXX,XX @@ static inline uint32_t syn_fp_access_trap(int cv, int cond, bool is_16bit)
47
| (cv << 24) | (cond << 20);
48
}
38
}
49
39
50
+static inline uint32_t syn_sve_access_trap(void)
40
-/* Scale factor for generic timers, ie number of ns per tick.
51
+{
41
- * This gives a 62.5MHz timer.
52
+ return EC_SVEACCESSTRAP << ARM_EL_EC_SHIFT;
42
+/*
53
+}
43
+ * Default frequency for the generic timer, in Hz.
44
+ * This is 62.5MHz, which gives a 16 ns tick period.
45
*/
46
-#define GTIMER_SCALE 16
47
+#define GTIMER_DEFAULT_HZ 62500000
48
49
/* Bit definitions for the v7M CONTROL register */
50
FIELD(V7M_CONTROL, NPRIV, 0, 1)
51
diff --git a/target/arm/cpu.c b/target/arm/cpu.c
52
index XXXXXXX..XXXXXXX 100644
53
--- a/target/arm/cpu.c
54
+++ b/target/arm/cpu.c
55
@@ -XXX,XX +XXX,XX @@ static void arm_cpu_initfn(Object *obj)
56
}
57
}
58
59
+/*
60
+ * 0 means "unset, use the default value". That default might vary depending
61
+ * on the CPU type, and is set in the realize fn.
62
+ */
63
static Property arm_cpu_gt_cntfrq_property =
64
- DEFINE_PROP_UINT64("cntfrq", ARMCPU, gt_cntfrq_hz,
65
- NANOSECONDS_PER_SECOND / GTIMER_SCALE);
66
+ DEFINE_PROP_UINT64("cntfrq", ARMCPU, gt_cntfrq_hz, 0);
67
68
static Property arm_cpu_reset_cbar_property =
69
DEFINE_PROP_UINT64("reset-cbar", ARMCPU, reset_cbar, 0);
70
@@ -XXX,XX +XXX,XX @@ static void arm_cpu_realizefn(DeviceState *dev, Error **errp)
71
return;
72
}
73
74
+ if (!cpu->gt_cntfrq_hz) {
75
+ /*
76
+ * 0 means "the board didn't set a value, use the default".
77
+ * The default value of the generic timer frequency (as seen in
78
+ * CNTFRQ_EL0) is 62.5MHz, which corresponds to a period of 16ns.
79
+ * This is what you get (a) for a CONFIG_USER_ONLY CPU (b) if the
80
+ * board doesn't set it.
81
+ */
82
+ cpu->gt_cntfrq_hz = GTIMER_DEFAULT_HZ;
83
+ }
54
+
84
+
55
static inline uint32_t syn_insn_abort(int same_el, int ea, int s1ptw, int fsc)
85
#ifndef CONFIG_USER_ONLY
56
{
86
/* The NVIC and M-profile CPU are two halves of a single piece of
57
return (EC_INSNABORT << ARM_EL_EC_SHIFT) | (same_el << ARM_EL_EC_SHIFT)
87
* hardware; trying to use one without the other is a command line
88
@@ -XXX,XX +XXX,XX @@ static void arm_cpu_realizefn(DeviceState *dev, Error **errp)
89
}
90
91
{
92
- uint64_t scale;
93
-
94
- if (arm_feature(env, ARM_FEATURE_GENERIC_TIMER)) {
95
- if (!cpu->gt_cntfrq_hz) {
96
- error_setg(errp, "Invalid CNTFRQ: %"PRId64"Hz",
97
- cpu->gt_cntfrq_hz);
98
- return;
99
- }
100
- scale = gt_cntfrq_period_ns(cpu);
101
- } else {
102
- scale = GTIMER_SCALE;
103
- }
104
+ uint64_t scale = gt_cntfrq_period_ns(cpu);
105
106
cpu->gt_timer[GTIMER_PHYS] = timer_new(QEMU_CLOCK_VIRTUAL, scale,
107
arm_gt_ptimer_cb, cpu);
58
diff --git a/target/arm/helper.c b/target/arm/helper.c
108
diff --git a/target/arm/helper.c b/target/arm/helper.c
59
index XXXXXXX..XXXXXXX 100644
109
index XXXXXXX..XXXXXXX 100644
60
--- a/target/arm/helper.c
110
--- a/target/arm/helper.c
61
+++ b/target/arm/helper.c
111
+++ b/target/arm/helper.c
62
@@ -XXX,XX +XXX,XX @@ static int sve_exception_el(CPUARMState *env)
112
@@ -XXX,XX +XXX,XX @@ static const ARMCPRegInfo v6k_cp_reginfo[] = {
63
return 0;
113
.resetvalue = 0 },
114
};
115
116
+static void arm_gt_cntfrq_reset(CPUARMState *env, const ARMCPRegInfo *opaque)
117
+{
118
+ ARMCPU *cpu = env_archcpu(env);
119
+
120
+ cpu->env.cp15.c14_cntfrq = cpu->gt_cntfrq_hz;
121
+}
122
+
123
#ifndef CONFIG_USER_ONLY
124
125
static CPAccessResult gt_cntfrq_access(CPUARMState *env, const ARMCPRegInfo *ri,
126
@@ -XXX,XX +XXX,XX @@ void arm_gt_hvtimer_cb(void *opaque)
127
gt_recalc_timer(cpu, GTIMER_HYPVIRT);
64
}
128
}
65
129
66
-static CPAccessResult zcr_access(CPUARMState *env, const ARMCPRegInfo *ri,
130
-static void arm_gt_cntfrq_reset(CPUARMState *env, const ARMCPRegInfo *opaque)
67
- bool isread)
68
-{
131
-{
69
- switch (sve_exception_el(env)) {
132
- ARMCPU *cpu = env_archcpu(env);
70
- case 3:
133
-
71
- return CP_ACCESS_TRAP_EL3;
134
- cpu->env.cp15.c14_cntfrq = cpu->gt_cntfrq_hz;
72
- case 2:
73
- return CP_ACCESS_TRAP_EL2;
74
- case 1:
75
- return CP_ACCESS_TRAP;
76
- }
77
- return CP_ACCESS_OK;
78
-}
135
-}
79
-
136
-
80
static void zcr_write(CPUARMState *env, const ARMCPRegInfo *ri,
137
static const ARMCPRegInfo generic_timer_cp_reginfo[] = {
81
uint64_t value)
138
/*
82
{
139
* Note that CNTFRQ is purely reads-as-written for the benefit
83
@@ -XXX,XX +XXX,XX @@ static void zcr_write(CPUARMState *env, const ARMCPRegInfo *ri,
140
@@ -XXX,XX +XXX,XX @@ static const ARMCPRegInfo generic_timer_cp_reginfo[] = {
84
static const ARMCPRegInfo zcr_el1_reginfo = {
141
.opc0 = 3, .opc1 = 3, .crn = 14, .crm = 0, .opc2 = 0,
85
.name = "ZCR_EL1", .state = ARM_CP_STATE_AA64,
142
.type = ARM_CP_CONST, .access = PL0_R /* no PL1_RW in linux-user */,
86
.opc0 = 3, .opc1 = 0, .crn = 1, .crm = 2, .opc2 = 0,
143
.fieldoffset = offsetof(CPUARMState, cp15.c14_cntfrq),
87
- .access = PL1_RW, .accessfn = zcr_access,
144
- .resetvalue = NANOSECONDS_PER_SECOND / GTIMER_SCALE,
88
+ .access = PL1_RW, .type = ARM_CP_SVE | ARM_CP_FPU,
145
+ .resetfn = arm_gt_cntfrq_reset,
89
.fieldoffset = offsetof(CPUARMState, vfp.zcr_el[1]),
146
},
90
.writefn = zcr_write, .raw_writefn = raw_write
147
{ .name = "CNTVCT_EL0", .state = ARM_CP_STATE_AA64,
91
};
148
.opc0 = 3, .opc1 = 3, .crn = 14, .crm = 0, .opc2 = 2,
92
@@ -XXX,XX +XXX,XX @@ static const ARMCPRegInfo zcr_el1_reginfo = {
93
static const ARMCPRegInfo zcr_el2_reginfo = {
94
.name = "ZCR_EL2", .state = ARM_CP_STATE_AA64,
95
.opc0 = 3, .opc1 = 4, .crn = 1, .crm = 2, .opc2 = 0,
96
- .access = PL2_RW, .accessfn = zcr_access,
97
+ .access = PL2_RW, .type = ARM_CP_SVE | ARM_CP_FPU,
98
.fieldoffset = offsetof(CPUARMState, vfp.zcr_el[2]),
99
.writefn = zcr_write, .raw_writefn = raw_write
100
};
101
@@ -XXX,XX +XXX,XX @@ static const ARMCPRegInfo zcr_el2_reginfo = {
102
static const ARMCPRegInfo zcr_no_el2_reginfo = {
103
.name = "ZCR_EL2", .state = ARM_CP_STATE_AA64,
104
.opc0 = 3, .opc1 = 4, .crn = 1, .crm = 2, .opc2 = 0,
105
- .access = PL2_RW,
106
+ .access = PL2_RW, .type = ARM_CP_SVE | ARM_CP_FPU,
107
.readfn = arm_cp_read_zero, .writefn = arm_cp_write_ignore
108
};
109
110
static const ARMCPRegInfo zcr_el3_reginfo = {
111
.name = "ZCR_EL3", .state = ARM_CP_STATE_AA64,
112
.opc0 = 3, .opc1 = 6, .crn = 1, .crm = 2, .opc2 = 0,
113
- .access = PL3_RW, .accessfn = zcr_access,
114
+ .access = PL3_RW, .type = ARM_CP_SVE | ARM_CP_FPU,
115
.fieldoffset = offsetof(CPUARMState, vfp.zcr_el[3]),
116
.writefn = zcr_write, .raw_writefn = raw_write
117
};
118
diff --git a/target/arm/translate-a64.c b/target/arm/translate-a64.c
119
index XXXXXXX..XXXXXXX 100644
120
--- a/target/arm/translate-a64.c
121
+++ b/target/arm/translate-a64.c
122
@@ -XXX,XX +XXX,XX @@ static inline bool fp_access_check(DisasContext *s)
123
return false;
124
}
125
126
+/* Check that SVE access is enabled. If it is, return true.
127
+ * If not, emit code to generate an appropriate exception and return false.
128
+ */
129
+static inline bool sve_access_check(DisasContext *s)
130
+{
131
+ if (s->sve_excp_el) {
132
+ gen_exception_insn(s, 4, EXCP_UDEF, syn_sve_access_trap(),
133
+ s->sve_excp_el);
134
+ return false;
135
+ }
136
+ return true;
137
+}
138
+
139
/*
140
* This utility function is for doing register extension with an
141
* optional shift. You will likely want to pass a temporary for the
142
@@ -XXX,XX +XXX,XX @@ static void handle_sys(DisasContext *s, uint32_t insn, bool isread,
143
default:
144
break;
145
}
146
+ if ((ri->type & ARM_CP_SVE) && !sve_access_check(s)) {
147
+ return;
148
+ }
149
if ((ri->type & ARM_CP_FPU) && !fp_access_check(s)) {
150
return;
151
}
152
--
149
--
153
2.16.1
150
2.34.1
154
151
155
152
diff view generated by jsdifflib
1
For M profile cores, cache maintenance operations are done by
1
Currently QEMU CPUs always run with a generic timer counter frequency
2
writing to special registers in the system register space.
2
of 62.5MHz, but ARMv8.6 CPUs will run at 1GHz. For older versions of
3
For QEMU, cache operations are always NOPs, since we don't
3
the TF-A firmware that sbsa-ref runs, the frequency of the generic
4
implement the cache. Implementing these explicitly avoids
4
timer is hardcoded into the firmware, and so if the CPU actually has
5
a spurious LOG_GUEST_ERROR when the guest uses them.
5
a different frequency then timers in the guest will be set
6
incorrectly.
7
8
The default frequency used by the 'max' CPU is about to change, so
9
make the sbsa-ref board force the CPU frequency to the value which
10
the firmware expects.
11
12
Newer versions of TF-A will read the frequency from the CPU's
13
CNTFRQ_EL0 register:
14
https://github.com/ARM-software/arm-trusted-firmware/commit/4c77fac98dac0bebc63798aae9101ac865b87148
15
so in the longer term we could make this board use the 1GHz
16
frequency. We will need to make sure we update the binaries used
17
by our avocado test
18
Aarch64SbsarefMachine.test_sbsaref_alpine_linux_max_pauth_impdef
19
before we can do that.
6
20
7
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
21
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
8
Reviewed-by: Richard Henderson <richard.henderson@linaro.org>
22
Reviewed-by: Philippe Mathieu-Daudé <philmd@linaro.org>
9
Message-id: 20180209165810.6668-4-peter.maydell@linaro.org
23
Reviewed-by: Marcin Juszkiewicz <marcin.juszkiewicz@linaro.org>
24
Message-id: 20240426122913.3427983-3-peter.maydell@linaro.org
10
---
25
---
11
hw/intc/armv7m_nvic.c | 12 ++++++++++++
26
hw/arm/sbsa-ref.c | 15 +++++++++++++++
12
1 file changed, 12 insertions(+)
27
1 file changed, 15 insertions(+)
13
28
14
diff --git a/hw/intc/armv7m_nvic.c b/hw/intc/armv7m_nvic.c
29
diff --git a/hw/arm/sbsa-ref.c b/hw/arm/sbsa-ref.c
15
index XXXXXXX..XXXXXXX 100644
30
index XXXXXXX..XXXXXXX 100644
16
--- a/hw/intc/armv7m_nvic.c
31
--- a/hw/arm/sbsa-ref.c
17
+++ b/hw/intc/armv7m_nvic.c
32
+++ b/hw/arm/sbsa-ref.c
18
@@ -XXX,XX +XXX,XX @@ static void nvic_writel(NVICState *s, uint32_t offset, uint32_t value,
33
@@ -XXX,XX +XXX,XX @@
34
#define NUM_SMMU_IRQS 4
35
#define NUM_SATA_PORTS 6
36
37
+/*
38
+ * Generic timer frequency in Hz (which drives both the CPU generic timers
39
+ * and the SBSA watchdog-timer). Older versions of the TF-A firmware
40
+ * typically used with sbsa-ref (including the binaries in our Avocado test
41
+ * Aarch64SbsarefMachine.test_sbsaref_alpine_linux_max_pauth_impdef
42
+ * assume it is this value.
43
+ *
44
+ * TODO: this value is not architecturally correct for an Armv8.6 or
45
+ * better CPU, so we should move to 1GHz once the TF-A fix above has
46
+ * made it into a release and into our Avocado test.
47
+ */
48
+#define SBSA_GTIMER_HZ 62500000
49
+
50
enum {
51
SBSA_FLASH,
52
SBSA_MEM,
53
@@ -XXX,XX +XXX,XX @@ static void sbsa_ref_init(MachineState *machine)
54
&error_abort);
19
}
55
}
20
break;
56
21
}
57
+ object_property_set_int(cpuobj, "cntfrq", SBSA_GTIMER_HZ, &error_abort);
22
+ case 0xf50: /* ICIALLU */
58
+
23
+ case 0xf58: /* ICIMVAU */
59
object_property_set_link(cpuobj, "memory", OBJECT(sysmem),
24
+ case 0xf5c: /* DCIMVAC */
60
&error_abort);
25
+ case 0xf60: /* DCISW */
61
26
+ case 0xf64: /* DCCMVAU */
27
+ case 0xf68: /* DCCMVAC */
28
+ case 0xf6c: /* DCCSW */
29
+ case 0xf70: /* DCCIMVAC */
30
+ case 0xf74: /* DCCISW */
31
+ case 0xf78: /* BPIALL */
32
+ /* Cache and branch predictor maintenance: for QEMU these always NOP */
33
+ break;
34
default:
35
bad_offset:
36
qemu_log_mask(LOG_GUEST_ERROR,
37
--
62
--
38
2.16.1
63
2.34.1
39
64
40
65
diff view generated by jsdifflib
1
Instead of hardcoding the values of M profile ID registers in the
1
Currently the sbsa_gdwt watchdog device hardcodes its frequency at
2
NVIC, use the fields in the CPU struct. This will allow us to
2
62.5MHz. In real hardware, this watchdog is supposed to be driven
3
give different M profile CPU types different ID register values.
3
from the system counter, which also drives the CPU generic timers.
4
Newer CPU types (in particular from Armv8.6) should have a CPU
5
generic timer frequency of 1GHz, so we can't leave the watchdog
6
on the old QEMU default of 62.5GHz.
4
7
5
This commit includes the addition of the missing ID_ISAR5,
8
Make the frequency a QOM property so it can be set by the board,
6
which exists as RES0 in both v7M and v8M.
9
and have our only board that uses this device set that frequency
7
10
to the same value it sets the CPU frequency.
8
(The values of the ID registers might be wrong for the M4 --
9
this commit leaves the behaviour there unchanged.)
10
11
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: Philippe Mathieu-Daudé <philmd@linaro.org>
13
Reviewed-by: Richard Henderson <richard.henderson@linaro.org>
14
Message-id: 20240426122913.3427983-4-peter.maydell@linaro.org
14
Message-id: 20180209165810.6668-2-peter.maydell@linaro.org
15
---
15
---
16
hw/intc/armv7m_nvic.c | 30 ++++++++++++++++--------------
16
include/hw/watchdog/sbsa_gwdt.h | 3 +--
17
target/arm/cpu.c | 28 ++++++++++++++++++++++++++++
17
hw/arm/sbsa-ref.c | 1 +
18
2 files changed, 44 insertions(+), 14 deletions(-)
18
hw/watchdog/sbsa_gwdt.c | 15 ++++++++++++++-
19
3 files changed, 16 insertions(+), 3 deletions(-)
19
20
20
diff --git a/hw/intc/armv7m_nvic.c b/hw/intc/armv7m_nvic.c
21
diff --git a/include/hw/watchdog/sbsa_gwdt.h b/include/hw/watchdog/sbsa_gwdt.h
21
index XXXXXXX..XXXXXXX 100644
22
index XXXXXXX..XXXXXXX 100644
22
--- a/hw/intc/armv7m_nvic.c
23
--- a/include/hw/watchdog/sbsa_gwdt.h
23
+++ b/hw/intc/armv7m_nvic.c
24
+++ b/include/hw/watchdog/sbsa_gwdt.h
24
@@ -XXX,XX +XXX,XX @@ static uint32_t nvic_readl(NVICState *s, uint32_t offset, MemTxAttrs attrs)
25
@@ -XXX,XX +XXX,XX @@
25
"Aux Fault status registers unimplemented\n");
26
#define SBSA_GWDT_RMMIO_SIZE 0x1000
26
return 0;
27
#define SBSA_GWDT_CMMIO_SIZE 0x1000
27
case 0xd40: /* PFR0. */
28
28
- return 0x00000030;
29
-#define SBSA_TIMER_FREQ 62500000 /* Hz */
29
- case 0xd44: /* PRF1. */
30
-
30
- return 0x00000200;
31
typedef struct SBSA_GWDTState {
31
+ return cpu->id_pfr0;
32
/* <private> */
32
+ case 0xd44: /* PFR1. */
33
SysBusDevice parent_obj;
33
+ return cpu->id_pfr1;
34
@@ -XXX,XX +XXX,XX @@ typedef struct SBSA_GWDTState {
34
case 0xd48: /* DFR0. */
35
qemu_irq irq;
35
- return 0x00100000;
36
36
+ return cpu->id_dfr0;
37
QEMUTimer *timer;
37
case 0xd4c: /* AFR0. */
38
+ uint64_t freq;
38
- return 0x00000000;
39
39
+ return cpu->id_afr0;
40
uint32_t id;
40
case 0xd50: /* MMFR0. */
41
uint32_t wcs;
41
- return 0x00000030;
42
diff --git a/hw/arm/sbsa-ref.c b/hw/arm/sbsa-ref.c
42
+ return cpu->id_mmfr0;
43
case 0xd54: /* MMFR1. */
44
- return 0x00000000;
45
+ return cpu->id_mmfr1;
46
case 0xd58: /* MMFR2. */
47
- return 0x00000000;
48
+ return cpu->id_mmfr2;
49
case 0xd5c: /* MMFR3. */
50
- return 0x00000000;
51
+ return cpu->id_mmfr3;
52
case 0xd60: /* ISAR0. */
53
- return 0x01141110;
54
+ return cpu->id_isar0;
55
case 0xd64: /* ISAR1. */
56
- return 0x02111000;
57
+ return cpu->id_isar1;
58
case 0xd68: /* ISAR2. */
59
- return 0x21112231;
60
+ return cpu->id_isar2;
61
case 0xd6c: /* ISAR3. */
62
- return 0x01111110;
63
+ return cpu->id_isar3;
64
case 0xd70: /* ISAR4. */
65
- return 0x01310102;
66
+ return cpu->id_isar4;
67
+ case 0xd74: /* ISAR5. */
68
+ return cpu->id_isar5;
69
/* TODO: Implement debug registers. */
70
case 0xd90: /* MPU_TYPE */
71
/* Unified MPU; if the MPU is not present this value is zero */
72
diff --git a/target/arm/cpu.c b/target/arm/cpu.c
73
index XXXXXXX..XXXXXXX 100644
43
index XXXXXXX..XXXXXXX 100644
74
--- a/target/arm/cpu.c
44
--- a/hw/arm/sbsa-ref.c
75
+++ b/target/arm/cpu.c
45
+++ b/hw/arm/sbsa-ref.c
76
@@ -XXX,XX +XXX,XX @@ static void cortex_m3_initfn(Object *obj)
46
@@ -XXX,XX +XXX,XX @@ static void create_wdt(const SBSAMachineState *sms)
77
set_feature(&cpu->env, ARM_FEATURE_M);
47
SysBusDevice *s = SYS_BUS_DEVICE(dev);
78
cpu->midr = 0x410fc231;
48
int irq = sbsa_ref_irqmap[SBSA_GWDT_WS0];
79
cpu->pmsav7_dregion = 8;
49
80
+ cpu->id_pfr0 = 0x00000030;
50
+ qdev_prop_set_uint64(dev, "clock-frequency", SBSA_GTIMER_HZ);
81
+ cpu->id_pfr1 = 0x00000200;
51
sysbus_realize_and_unref(s, &error_fatal);
82
+ cpu->id_dfr0 = 0x00100000;
52
sysbus_mmio_map(s, 0, rbase);
83
+ cpu->id_afr0 = 0x00000000;
53
sysbus_mmio_map(s, 1, cbase);
84
+ cpu->id_mmfr0 = 0x00000030;
54
diff --git a/hw/watchdog/sbsa_gwdt.c b/hw/watchdog/sbsa_gwdt.c
85
+ cpu->id_mmfr1 = 0x00000000;
55
index XXXXXXX..XXXXXXX 100644
86
+ cpu->id_mmfr2 = 0x00000000;
56
--- a/hw/watchdog/sbsa_gwdt.c
87
+ cpu->id_mmfr3 = 0x00000000;
57
+++ b/hw/watchdog/sbsa_gwdt.c
88
+ cpu->id_isar0 = 0x01141110;
58
@@ -XXX,XX +XXX,XX @@
89
+ cpu->id_isar1 = 0x02111000;
59
#include "qemu/osdep.h"
90
+ cpu->id_isar2 = 0x21112231;
60
#include "sysemu/reset.h"
91
+ cpu->id_isar3 = 0x01111110;
61
#include "sysemu/watchdog.h"
92
+ cpu->id_isar4 = 0x01310102;
62
+#include "hw/qdev-properties.h"
93
+ cpu->id_isar5 = 0x00000000;
63
#include "hw/watchdog/sbsa_gwdt.h"
64
#include "qemu/timer.h"
65
#include "migration/vmstate.h"
66
@@ -XXX,XX +XXX,XX @@ static void sbsa_gwdt_update_timer(SBSA_GWDTState *s, WdtRefreshType rtype)
67
timeout = s->woru;
68
timeout <<= 32;
69
timeout |= s->worl;
70
- timeout = muldiv64(timeout, NANOSECONDS_PER_SECOND, SBSA_TIMER_FREQ);
71
+ timeout = muldiv64(timeout, NANOSECONDS_PER_SECOND, s->freq);
72
timeout += qemu_clock_get_ns(QEMU_CLOCK_VIRTUAL);
73
74
if ((rtype == EXPLICIT_REFRESH) || ((rtype == TIMEOUT_REFRESH) &&
75
@@ -XXX,XX +XXX,XX @@ static void wdt_sbsa_gwdt_realize(DeviceState *dev, Error **errp)
76
dev);
94
}
77
}
95
78
96
static void cortex_m4_initfn(Object *obj)
79
+static Property wdt_sbsa_gwdt_props[] = {
97
@@ -XXX,XX +XXX,XX @@ static void cortex_m4_initfn(Object *obj)
80
+ /*
98
set_feature(&cpu->env, ARM_FEATURE_THUMB_DSP);
81
+ * Timer frequency in Hz. This must match the frequency used by
99
cpu->midr = 0x410fc240; /* r0p0 */
82
+ * the CPU's generic timer. Default 62.5Hz matches QEMU's legacy
100
cpu->pmsav7_dregion = 8;
83
+ * CPU timer frequency default.
101
+ cpu->id_pfr0 = 0x00000030;
84
+ */
102
+ cpu->id_pfr1 = 0x00000200;
85
+ DEFINE_PROP_UINT64("clock-frequency", struct SBSA_GWDTState, freq,
103
+ cpu->id_dfr0 = 0x00100000;
86
+ 62500000),
104
+ cpu->id_afr0 = 0x00000000;
87
+ DEFINE_PROP_END_OF_LIST(),
105
+ cpu->id_mmfr0 = 0x00000030;
88
+};
106
+ cpu->id_mmfr1 = 0x00000000;
89
+
107
+ cpu->id_mmfr2 = 0x00000000;
90
static void wdt_sbsa_gwdt_class_init(ObjectClass *klass, void *data)
108
+ cpu->id_mmfr3 = 0x00000000;
91
{
109
+ cpu->id_isar0 = 0x01141110;
92
DeviceClass *dc = DEVICE_CLASS(klass);
110
+ cpu->id_isar1 = 0x02111000;
93
@@ -XXX,XX +XXX,XX @@ static void wdt_sbsa_gwdt_class_init(ObjectClass *klass, void *data)
111
+ cpu->id_isar2 = 0x21112231;
94
set_bit(DEVICE_CATEGORY_WATCHDOG, dc->categories);
112
+ cpu->id_isar3 = 0x01111110;
95
dc->vmsd = &vmstate_sbsa_gwdt;
113
+ cpu->id_isar4 = 0x01310102;
96
dc->desc = "SBSA-compliant generic watchdog device";
114
+ cpu->id_isar5 = 0x00000000;
97
+ device_class_set_props(dc, wdt_sbsa_gwdt_props);
115
}
98
}
116
99
117
static void arm_v7m_class_init(ObjectClass *oc, void *data)
100
static const TypeInfo wdt_sbsa_gwdt_info = {
118
--
101
--
119
2.16.1
102
2.34.1
120
103
121
104
diff view generated by jsdifflib
1
We were previously making the system control register (SCR)
1
In previous versions of the Arm architecture, the frequency of the
2
just RAZ/WI. Although we don't implement the functionality
2
generic timers as reported in CNTFRQ_EL0 could be any IMPDEF value,
3
this register controls, we should at least provide the state,
3
and for QEMU we picked 62.5MHz, giving a timer tick period of 16ns.
4
including the banked state for v8M.
4
In Armv8.6, the architecture standardized this frequency to 1GHz.
5
6
Because there is no ID register feature field that indicates whether
7
a CPU is v8.6 or that it ought to have this counter frequency, we
8
implement this by changing our default CNTFRQ value for all CPUs,
9
with exceptions for backwards compatibility:
10
11
* CPU types which we already implement will retain the old
12
default value. None of these are v8.6 CPUs, so this is
13
architecturally OK.
14
* CPUs used in versioned machine types with a version of 9.0
15
or earlier will retain the old default value.
16
17
The upshot is that the only CPU type that changes is 'max'; but any
18
new type we add in future (whether v8.6 or not) will also get the new
19
1GHz default.
20
21
It remains the case that the machine model can override the default
22
value via the 'cntfrq' QOM property (regardless of the CPU type).
5
23
6
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
24
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
7
Reviewed-by: Richard Henderson <richard.henderson@linaro.org>
25
Reviewed-by: Richard Henderson <richard.henderson@linaro.org>
8
Message-id: 20180209165810.6668-7-peter.maydell@linaro.org
26
Reviewed-by: Philippe Mathieu-Daudé <philmd@linaro.org>
27
Message-id: 20240426122913.3427983-5-peter.maydell@linaro.org
9
---
28
---
10
target/arm/cpu.h | 7 +++++++
29
target/arm/cpu.h | 11 +++++++++++
11
hw/intc/armv7m_nvic.c | 12 ++++++++----
30
target/arm/internals.h | 12 ++++++++++--
12
target/arm/machine.c | 12 ++++++++++++
31
hw/core/machine.c | 4 +++-
13
3 files changed, 27 insertions(+), 4 deletions(-)
32
target/arm/cpu.c | 23 +++++++++++++++++------
33
target/arm/cpu64.c | 2 ++
34
target/arm/tcg/cpu32.c | 4 ++++
35
target/arm/tcg/cpu64.c | 18 ++++++++++++++++++
36
7 files changed, 65 insertions(+), 9 deletions(-)
14
37
15
diff --git a/target/arm/cpu.h b/target/arm/cpu.h
38
diff --git a/target/arm/cpu.h b/target/arm/cpu.h
16
index XXXXXXX..XXXXXXX 100644
39
index XXXXXXX..XXXXXXX 100644
17
--- a/target/arm/cpu.h
40
--- a/target/arm/cpu.h
18
+++ b/target/arm/cpu.h
41
+++ b/target/arm/cpu.h
19
@@ -XXX,XX +XXX,XX @@ typedef struct CPUARMState {
42
@@ -XXX,XX +XXX,XX @@ struct ArchCPU {
20
uint32_t aircr; /* only holds r/w state if security extn implemented */
43
*/
21
uint32_t secure; /* Is CPU in Secure state? (not guest visible) */
44
bool host_cpu_probe_failed;
22
uint32_t csselr[M_REG_NUM_BANKS];
45
23
+ uint32_t scr[M_REG_NUM_BANKS];
46
+ /* QOM property to indicate we should use the back-compat CNTFRQ default */
24
} v7m;
47
+ bool backcompat_cntfrq;
25
26
/* Information associated with an exception about to be taken:
27
@@ -XXX,XX +XXX,XX @@ FIELD(V7M_CCR, STKALIGN, 9, 1)
28
FIELD(V7M_CCR, DC, 16, 1)
29
FIELD(V7M_CCR, IC, 17, 1)
30
31
+/* V7M SCR bits */
32
+FIELD(V7M_SCR, SLEEPONEXIT, 1, 1)
33
+FIELD(V7M_SCR, SLEEPDEEP, 2, 1)
34
+FIELD(V7M_SCR, SLEEPDEEPS, 3, 1)
35
+FIELD(V7M_SCR, SEVONPEND, 4, 1)
36
+
48
+
37
/* V7M AIRCR bits */
49
/* Specify the number of cores in this CPU cluster. Used for the L2CTLR
38
FIELD(V7M_AIRCR, VECTRESET, 0, 1)
50
* register.
39
FIELD(V7M_AIRCR, VECTCLRACTIVE, 1, 1)
51
*/
40
diff --git a/hw/intc/armv7m_nvic.c b/hw/intc/armv7m_nvic.c
52
@@ -XXX,XX +XXX,XX @@ enum arm_features {
41
index XXXXXXX..XXXXXXX 100644
53
ARM_FEATURE_M_SECURITY, /* M profile Security Extension */
42
--- a/hw/intc/armv7m_nvic.c
54
ARM_FEATURE_M_MAIN, /* M profile Main Extension */
43
+++ b/hw/intc/armv7m_nvic.c
55
ARM_FEATURE_V8_1M, /* M profile extras only in v8.1M and later */
44
@@ -XXX,XX +XXX,XX @@ static uint32_t nvic_readl(NVICState *s, uint32_t offset, MemTxAttrs attrs)
56
+ /*
45
}
57
+ * ARM_FEATURE_BACKCOMPAT_CNTFRQ makes the CPU default cntfrq be 62.5MHz
46
return val;
58
+ * if the board doesn't set a value, instead of 1GHz. It is for backwards
47
case 0xd10: /* System Control. */
59
+ * compatibility and used only with CPU definitions that were already
48
- /* TODO: Implement SLEEPONEXIT. */
60
+ * in QEMU before we changed the default. It should not be set on any
49
- return 0;
61
+ * CPU types added in future.
50
+ return cpu->env.v7m.scr[attrs.secure];
62
+ */
51
case 0xd14: /* Configuration Control. */
63
+ ARM_FEATURE_BACKCOMPAT_CNTFRQ, /* 62.5MHz timer default */
52
/* The BFHFNMIGN bit is the only non-banked bit; we
64
};
53
* keep it in the non-secure copy of the register.
65
54
@@ -XXX,XX +XXX,XX @@ static void nvic_writel(NVICState *s, uint32_t offset, uint32_t value,
66
static inline int arm_feature(CPUARMState *env, int feature)
55
}
67
diff --git a/target/arm/internals.h b/target/arm/internals.h
56
break;
68
index XXXXXXX..XXXXXXX 100644
57
case 0xd10: /* System Control. */
69
--- a/target/arm/internals.h
58
- /* TODO: Implement control registers. */
70
+++ b/target/arm/internals.h
59
- qemu_log_mask(LOG_UNIMP, "NVIC: SCR unimplemented\n");
71
@@ -XXX,XX +XXX,XX @@ static inline bool excp_is_internal(int excp)
60
+ /* We don't implement deep-sleep so these bits are RAZ/WI.
72
61
+ * The other bits in the register are banked.
73
/*
62
+ * QEMU's implementation ignores SEVONPEND and SLEEPONEXIT, which
74
* Default frequency for the generic timer, in Hz.
63
+ * is architecturally permitted.
75
- * This is 62.5MHz, which gives a 16 ns tick period.
64
+ */
76
+ * ARMv8.6 and later CPUs architecturally must use a 1GHz timer; before
65
+ value &= ~(R_V7M_SCR_SLEEPDEEP_MASK | R_V7M_SCR_SLEEPDEEPS_MASK);
77
+ * that it was an IMPDEF choice, and QEMU initially picked 62.5MHz,
66
+ cpu->env.v7m.scr[attrs.secure] = value;
78
+ * which gives a 16ns tick period.
67
break;
79
+ *
68
case 0xd14: /* Configuration Control. */
80
+ * We will use the back-compat value:
69
/* Enforce RAZ/WI on reserved and must-RAZ/WI bits */
81
+ * - for QEMU CPU types added before we standardized on 1GHz
70
diff --git a/target/arm/machine.c b/target/arm/machine.c
82
+ * - for versioned machine types with a version of 9.0 or earlier
71
index XXXXXXX..XXXXXXX 100644
83
+ * In any case, the machine model may override via the cntfrq property.
72
--- a/target/arm/machine.c
84
*/
73
+++ b/target/arm/machine.c
85
-#define GTIMER_DEFAULT_HZ 62500000
74
@@ -XXX,XX +XXX,XX @@ static const VMStateDescription vmstate_m_csselr = {
86
+#define GTIMER_DEFAULT_HZ 1000000000
87
+#define GTIMER_BACKCOMPAT_HZ 62500000
88
89
/* Bit definitions for the v7M CONTROL register */
90
FIELD(V7M_CONTROL, NPRIV, 0, 1)
91
diff --git a/hw/core/machine.c b/hw/core/machine.c
92
index XXXXXXX..XXXXXXX 100644
93
--- a/hw/core/machine.c
94
+++ b/hw/core/machine.c
95
@@ -XXX,XX +XXX,XX @@
96
#include "hw/virtio/virtio-iommu.h"
97
#include "audio/audio.h"
98
99
-GlobalProperty hw_compat_9_0[] = {};
100
+GlobalProperty hw_compat_9_0[] = {
101
+ {"arm-cpu", "backcompat-cntfrq", "true" },
102
+};
103
const size_t hw_compat_9_0_len = G_N_ELEMENTS(hw_compat_9_0);
104
105
GlobalProperty hw_compat_8_2[] = {
106
diff --git a/target/arm/cpu.c b/target/arm/cpu.c
107
index XXXXXXX..XXXXXXX 100644
108
--- a/target/arm/cpu.c
109
+++ b/target/arm/cpu.c
110
@@ -XXX,XX +XXX,XX @@ static void arm_cpu_realizefn(DeviceState *dev, Error **errp)
111
112
if (!cpu->gt_cntfrq_hz) {
113
/*
114
- * 0 means "the board didn't set a value, use the default".
115
- * The default value of the generic timer frequency (as seen in
116
- * CNTFRQ_EL0) is 62.5MHz, which corresponds to a period of 16ns.
117
- * This is what you get (a) for a CONFIG_USER_ONLY CPU (b) if the
118
- * board doesn't set it.
119
+ * 0 means "the board didn't set a value, use the default". (We also
120
+ * get here for the CONFIG_USER_ONLY case.)
121
+ * ARMv8.6 and later CPUs architecturally must use a 1GHz timer; before
122
+ * that it was an IMPDEF choice, and QEMU initially picked 62.5MHz,
123
+ * which gives a 16ns tick period.
124
+ *
125
+ * We will use the back-compat value:
126
+ * - for QEMU CPU types added before we standardized on 1GHz
127
+ * - for versioned machine types with a version of 9.0 or earlier
128
*/
129
- cpu->gt_cntfrq_hz = GTIMER_DEFAULT_HZ;
130
+ if (arm_feature(env, ARM_FEATURE_BACKCOMPAT_CNTFRQ) ||
131
+ cpu->backcompat_cntfrq) {
132
+ cpu->gt_cntfrq_hz = GTIMER_BACKCOMPAT_HZ;
133
+ } else {
134
+ cpu->gt_cntfrq_hz = GTIMER_DEFAULT_HZ;
135
+ }
75
}
136
}
137
138
#ifndef CONFIG_USER_ONLY
139
@@ -XXX,XX +XXX,XX @@ static Property arm_cpu_properties[] = {
140
mp_affinity, ARM64_AFFINITY_INVALID),
141
DEFINE_PROP_INT32("node-id", ARMCPU, node_id, CPU_UNSET_NUMA_NODE_ID),
142
DEFINE_PROP_INT32("core-count", ARMCPU, core_count, -1),
143
+ /* True to default to the backward-compat old CNTFRQ rather than 1Ghz */
144
+ DEFINE_PROP_BOOL("backcompat-cntfrq", ARMCPU, backcompat_cntfrq, false),
145
DEFINE_PROP_END_OF_LIST()
76
};
146
};
77
147
78
+static const VMStateDescription vmstate_m_scr = {
148
diff --git a/target/arm/cpu64.c b/target/arm/cpu64.c
79
+ .name = "cpu/m/scr",
149
index XXXXXXX..XXXXXXX 100644
80
+ .version_id = 1,
150
--- a/target/arm/cpu64.c
81
+ .minimum_version_id = 1,
151
+++ b/target/arm/cpu64.c
82
+ .fields = (VMStateField[]) {
152
@@ -XXX,XX +XXX,XX @@ static void aarch64_a57_initfn(Object *obj)
83
+ VMSTATE_UINT32(env.v7m.scr[M_REG_NS], ARMCPU),
153
set_feature(&cpu->env, ARM_FEATURE_V8);
84
+ VMSTATE_END_OF_LIST()
154
set_feature(&cpu->env, ARM_FEATURE_NEON);
85
+ }
155
set_feature(&cpu->env, ARM_FEATURE_GENERIC_TIMER);
86
+};
156
+ set_feature(&cpu->env, ARM_FEATURE_BACKCOMPAT_CNTFRQ);
157
set_feature(&cpu->env, ARM_FEATURE_AARCH64);
158
set_feature(&cpu->env, ARM_FEATURE_CBAR_RO);
159
set_feature(&cpu->env, ARM_FEATURE_EL2);
160
@@ -XXX,XX +XXX,XX @@ static void aarch64_a53_initfn(Object *obj)
161
set_feature(&cpu->env, ARM_FEATURE_V8);
162
set_feature(&cpu->env, ARM_FEATURE_NEON);
163
set_feature(&cpu->env, ARM_FEATURE_GENERIC_TIMER);
164
+ set_feature(&cpu->env, ARM_FEATURE_BACKCOMPAT_CNTFRQ);
165
set_feature(&cpu->env, ARM_FEATURE_AARCH64);
166
set_feature(&cpu->env, ARM_FEATURE_CBAR_RO);
167
set_feature(&cpu->env, ARM_FEATURE_EL2);
168
diff --git a/target/arm/tcg/cpu32.c b/target/arm/tcg/cpu32.c
169
index XXXXXXX..XXXXXXX 100644
170
--- a/target/arm/tcg/cpu32.c
171
+++ b/target/arm/tcg/cpu32.c
172
@@ -XXX,XX +XXX,XX @@ static void cortex_a7_initfn(Object *obj)
173
set_feature(&cpu->env, ARM_FEATURE_NEON);
174
set_feature(&cpu->env, ARM_FEATURE_THUMB2EE);
175
set_feature(&cpu->env, ARM_FEATURE_GENERIC_TIMER);
176
+ set_feature(&cpu->env, ARM_FEATURE_BACKCOMPAT_CNTFRQ);
177
set_feature(&cpu->env, ARM_FEATURE_DUMMY_C15_REGS);
178
set_feature(&cpu->env, ARM_FEATURE_CBAR_RO);
179
set_feature(&cpu->env, ARM_FEATURE_EL2);
180
@@ -XXX,XX +XXX,XX @@ static void cortex_a15_initfn(Object *obj)
181
set_feature(&cpu->env, ARM_FEATURE_NEON);
182
set_feature(&cpu->env, ARM_FEATURE_THUMB2EE);
183
set_feature(&cpu->env, ARM_FEATURE_GENERIC_TIMER);
184
+ set_feature(&cpu->env, ARM_FEATURE_BACKCOMPAT_CNTFRQ);
185
set_feature(&cpu->env, ARM_FEATURE_DUMMY_C15_REGS);
186
set_feature(&cpu->env, ARM_FEATURE_CBAR_RO);
187
set_feature(&cpu->env, ARM_FEATURE_EL2);
188
@@ -XXX,XX +XXX,XX @@ static void cortex_r52_initfn(Object *obj)
189
set_feature(&cpu->env, ARM_FEATURE_PMSA);
190
set_feature(&cpu->env, ARM_FEATURE_NEON);
191
set_feature(&cpu->env, ARM_FEATURE_GENERIC_TIMER);
192
+ set_feature(&cpu->env, ARM_FEATURE_BACKCOMPAT_CNTFRQ);
193
set_feature(&cpu->env, ARM_FEATURE_CBAR_RO);
194
set_feature(&cpu->env, ARM_FEATURE_AUXCR);
195
cpu->midr = 0x411fd133; /* r1p3 */
196
@@ -XXX,XX +XXX,XX @@ static void arm_max_initfn(Object *obj)
197
set_feature(&cpu->env, ARM_FEATURE_V8);
198
set_feature(&cpu->env, ARM_FEATURE_NEON);
199
set_feature(&cpu->env, ARM_FEATURE_GENERIC_TIMER);
200
+ set_feature(&cpu->env, ARM_FEATURE_BACKCOMPAT_CNTFRQ);
201
set_feature(&cpu->env, ARM_FEATURE_CBAR_RO);
202
set_feature(&cpu->env, ARM_FEATURE_EL2);
203
set_feature(&cpu->env, ARM_FEATURE_EL3);
204
diff --git a/target/arm/tcg/cpu64.c b/target/arm/tcg/cpu64.c
205
index XXXXXXX..XXXXXXX 100644
206
--- a/target/arm/tcg/cpu64.c
207
+++ b/target/arm/tcg/cpu64.c
208
@@ -XXX,XX +XXX,XX @@ static void aarch64_a35_initfn(Object *obj)
209
set_feature(&cpu->env, ARM_FEATURE_V8);
210
set_feature(&cpu->env, ARM_FEATURE_NEON);
211
set_feature(&cpu->env, ARM_FEATURE_GENERIC_TIMER);
212
+ set_feature(&cpu->env, ARM_FEATURE_BACKCOMPAT_CNTFRQ);
213
set_feature(&cpu->env, ARM_FEATURE_AARCH64);
214
set_feature(&cpu->env, ARM_FEATURE_CBAR_RO);
215
set_feature(&cpu->env, ARM_FEATURE_EL2);
216
@@ -XXX,XX +XXX,XX @@ static void aarch64_a55_initfn(Object *obj)
217
set_feature(&cpu->env, ARM_FEATURE_V8);
218
set_feature(&cpu->env, ARM_FEATURE_NEON);
219
set_feature(&cpu->env, ARM_FEATURE_GENERIC_TIMER);
220
+ set_feature(&cpu->env, ARM_FEATURE_BACKCOMPAT_CNTFRQ);
221
set_feature(&cpu->env, ARM_FEATURE_AARCH64);
222
set_feature(&cpu->env, ARM_FEATURE_CBAR_RO);
223
set_feature(&cpu->env, ARM_FEATURE_EL2);
224
@@ -XXX,XX +XXX,XX @@ static void aarch64_a72_initfn(Object *obj)
225
set_feature(&cpu->env, ARM_FEATURE_V8);
226
set_feature(&cpu->env, ARM_FEATURE_NEON);
227
set_feature(&cpu->env, ARM_FEATURE_GENERIC_TIMER);
228
+ set_feature(&cpu->env, ARM_FEATURE_BACKCOMPAT_CNTFRQ);
229
set_feature(&cpu->env, ARM_FEATURE_AARCH64);
230
set_feature(&cpu->env, ARM_FEATURE_CBAR_RO);
231
set_feature(&cpu->env, ARM_FEATURE_EL2);
232
@@ -XXX,XX +XXX,XX @@ static void aarch64_a76_initfn(Object *obj)
233
set_feature(&cpu->env, ARM_FEATURE_V8);
234
set_feature(&cpu->env, ARM_FEATURE_NEON);
235
set_feature(&cpu->env, ARM_FEATURE_GENERIC_TIMER);
236
+ set_feature(&cpu->env, ARM_FEATURE_BACKCOMPAT_CNTFRQ);
237
set_feature(&cpu->env, ARM_FEATURE_AARCH64);
238
set_feature(&cpu->env, ARM_FEATURE_CBAR_RO);
239
set_feature(&cpu->env, ARM_FEATURE_EL2);
240
@@ -XXX,XX +XXX,XX @@ static void aarch64_a64fx_initfn(Object *obj)
241
set_feature(&cpu->env, ARM_FEATURE_V8);
242
set_feature(&cpu->env, ARM_FEATURE_NEON);
243
set_feature(&cpu->env, ARM_FEATURE_GENERIC_TIMER);
244
+ set_feature(&cpu->env, ARM_FEATURE_BACKCOMPAT_CNTFRQ);
245
set_feature(&cpu->env, ARM_FEATURE_AARCH64);
246
set_feature(&cpu->env, ARM_FEATURE_EL2);
247
set_feature(&cpu->env, ARM_FEATURE_EL3);
248
@@ -XXX,XX +XXX,XX @@ static void aarch64_neoverse_n1_initfn(Object *obj)
249
set_feature(&cpu->env, ARM_FEATURE_V8);
250
set_feature(&cpu->env, ARM_FEATURE_NEON);
251
set_feature(&cpu->env, ARM_FEATURE_GENERIC_TIMER);
252
+ set_feature(&cpu->env, ARM_FEATURE_BACKCOMPAT_CNTFRQ);
253
set_feature(&cpu->env, ARM_FEATURE_AARCH64);
254
set_feature(&cpu->env, ARM_FEATURE_CBAR_RO);
255
set_feature(&cpu->env, ARM_FEATURE_EL2);
256
@@ -XXX,XX +XXX,XX @@ static void aarch64_neoverse_v1_initfn(Object *obj)
257
set_feature(&cpu->env, ARM_FEATURE_V8);
258
set_feature(&cpu->env, ARM_FEATURE_NEON);
259
set_feature(&cpu->env, ARM_FEATURE_GENERIC_TIMER);
260
+ set_feature(&cpu->env, ARM_FEATURE_BACKCOMPAT_CNTFRQ);
261
set_feature(&cpu->env, ARM_FEATURE_AARCH64);
262
set_feature(&cpu->env, ARM_FEATURE_CBAR_RO);
263
set_feature(&cpu->env, ARM_FEATURE_EL2);
264
@@ -XXX,XX +XXX,XX @@ static void aarch64_a710_initfn(Object *obj)
265
set_feature(&cpu->env, ARM_FEATURE_V8);
266
set_feature(&cpu->env, ARM_FEATURE_NEON);
267
set_feature(&cpu->env, ARM_FEATURE_GENERIC_TIMER);
268
+ set_feature(&cpu->env, ARM_FEATURE_BACKCOMPAT_CNTFRQ);
269
set_feature(&cpu->env, ARM_FEATURE_AARCH64);
270
set_feature(&cpu->env, ARM_FEATURE_CBAR_RO);
271
set_feature(&cpu->env, ARM_FEATURE_EL2);
272
@@ -XXX,XX +XXX,XX @@ static void aarch64_neoverse_n2_initfn(Object *obj)
273
set_feature(&cpu->env, ARM_FEATURE_V8);
274
set_feature(&cpu->env, ARM_FEATURE_NEON);
275
set_feature(&cpu->env, ARM_FEATURE_GENERIC_TIMER);
276
+ set_feature(&cpu->env, ARM_FEATURE_BACKCOMPAT_CNTFRQ);
277
set_feature(&cpu->env, ARM_FEATURE_AARCH64);
278
set_feature(&cpu->env, ARM_FEATURE_CBAR_RO);
279
set_feature(&cpu->env, ARM_FEATURE_EL2);
280
@@ -XXX,XX +XXX,XX @@ void aarch64_max_tcg_initfn(Object *obj)
281
uint64_t t;
282
uint32_t u;
283
284
+ /*
285
+ * Unset ARM_FEATURE_BACKCOMPAT_CNTFRQ, which we would otherwise default
286
+ * to because we started with aarch64_a57_initfn(). A 'max' CPU might
287
+ * be a v8.6-or-later one, in which case the cntfrq must be 1GHz; and
288
+ * because it is our "may change" CPU type we are OK with it not being
289
+ * backwards-compatible with how it worked in old QEMU.
290
+ */
291
+ unset_feature(&cpu->env, ARM_FEATURE_BACKCOMPAT_CNTFRQ);
87
+
292
+
88
static const VMStateDescription vmstate_m = {
293
/*
89
.name = "cpu/m",
294
* Reset MIDR so the guest doesn't mistake our 'max' CPU type for a real
90
.version_id = 4,
295
* one and try to apply errata workarounds or use impdef features we
91
@@ -XXX,XX +XXX,XX @@ static const VMStateDescription vmstate_m = {
92
.subsections = (const VMStateDescription*[]) {
93
&vmstate_m_faultmask_primask,
94
&vmstate_m_csselr,
95
+ &vmstate_m_scr,
96
NULL
97
}
98
};
99
@@ -XXX,XX +XXX,XX @@ static const VMStateDescription vmstate_m_security = {
100
VMSTATE_UINT32(env.sau.rnr, ARMCPU),
101
VMSTATE_VALIDATE("SAU_RNR is valid", sau_rnr_vmstate_validate),
102
VMSTATE_UINT32(env.sau.ctrl, ARMCPU),
103
+ VMSTATE_UINT32(env.v7m.scr[M_REG_S], ARMCPU),
104
VMSTATE_END_OF_LIST()
105
}
106
};
107
--
296
--
108
2.16.1
297
2.34.1
109
298
110
299
diff view generated by jsdifflib
1
From: Pekka Enberg <penberg@iki.fi>
1
From: Alexandra Diupina <adiupina@astralinux.ru>
2
2
3
This patch adds a "cpu-type" property to BCM2836 SoC in preparation for
3
The DMA descriptor structures for this device have
4
reusing the code for the Raspberry Pi 3, which has a different processor
4
a set of "address extension" fields which extend the 32
5
model.
5
bit source addresses with an extra 16 bits to give a
6
48 bit address:
7
https://docs.amd.com/r/en-US/ug1085-zynq-ultrascale-trm/ADDR_EXT-Field
6
8
7
Signed-off-by: Pekka Enberg <penberg@iki.fi>
9
However, we misimplemented this address extension in several ways:
10
* we only extracted 12 bits of the extension fields, not 16
11
* we didn't shift the extension field up far enough
12
* we accidentally did the shift as 32-bit arithmetic, which
13
meant that we would have an overflow instead of setting
14
bits [47:32] of the resulting 64-bit address
15
16
Add a type cast and use extract64() instead of extract32()
17
to avoid integer overflow on addition. Fix bit fields
18
extraction according to documentation.
19
20
Found by Linux Verification Center (linuxtesting.org) with SVACE.
21
22
Cc: qemu-stable@nongnu.org
23
Fixes: d3c6369a96 ("introduce xlnx-dpdma")
24
Signed-off-by: Alexandra Diupina <adiupina@astralinux.ru>
25
Message-id: 20240428181131.23801-1-adiupina@astralinux.ru
26
[PMM: adjusted commit message]
8
Reviewed-by: Peter Maydell <peter.maydell@linaro.org>
27
Reviewed-by: Peter Maydell <peter.maydell@linaro.org>
9
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
28
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
10
---
29
---
11
include/hw/arm/bcm2836.h | 1 +
30
hw/dma/xlnx_dpdma.c | 20 ++++++++++----------
12
hw/arm/bcm2836.c | 17 +++++++++--------
31
1 file changed, 10 insertions(+), 10 deletions(-)
13
hw/arm/raspi.c | 3 +++
14
3 files changed, 13 insertions(+), 8 deletions(-)
15
32
16
diff --git a/include/hw/arm/bcm2836.h b/include/hw/arm/bcm2836.h
33
diff --git a/hw/dma/xlnx_dpdma.c b/hw/dma/xlnx_dpdma.c
17
index XXXXXXX..XXXXXXX 100644
34
index XXXXXXX..XXXXXXX 100644
18
--- a/include/hw/arm/bcm2836.h
35
--- a/hw/dma/xlnx_dpdma.c
19
+++ b/include/hw/arm/bcm2836.h
36
+++ b/hw/dma/xlnx_dpdma.c
20
@@ -XXX,XX +XXX,XX @@ typedef struct BCM2836State {
37
@@ -XXX,XX +XXX,XX @@ static uint64_t xlnx_dpdma_desc_get_source_address(DPDMADescriptor *desc,
21
DeviceState parent_obj;
38
22
/*< public >*/
39
switch (frag) {
23
40
case 0:
24
+ char *cpu_type;
41
- addr = desc->source_address
25
uint32_t enabled_cpus;
42
- + (extract32(desc->address_extension, 16, 12) << 20);
26
43
+ addr = (uint64_t)desc->source_address
27
ARMCPU cpus[BCM2836_NCPUS];
44
+ + (extract64(desc->address_extension, 16, 16) << 32);
28
diff --git a/hw/arm/bcm2836.c b/hw/arm/bcm2836.c
45
break;
29
index XXXXXXX..XXXXXXX 100644
46
case 1:
30
--- a/hw/arm/bcm2836.c
47
- addr = desc->source_address2
31
+++ b/hw/arm/bcm2836.c
48
- + (extract32(desc->address_extension_23, 0, 12) << 8);
32
@@ -XXX,XX +XXX,XX @@
49
+ addr = (uint64_t)desc->source_address2
33
static void bcm2836_init(Object *obj)
50
+ + (extract64(desc->address_extension_23, 0, 16) << 32);
34
{
51
break;
35
BCM2836State *s = BCM2836(obj);
52
case 2:
36
- int n;
53
- addr = desc->source_address3
37
-
54
- + (extract32(desc->address_extension_23, 16, 12) << 20);
38
- for (n = 0; n < BCM2836_NCPUS; n++) {
55
+ addr = (uint64_t)desc->source_address3
39
- object_initialize(&s->cpus[n], sizeof(s->cpus[n]),
56
+ + (extract64(desc->address_extension_23, 16, 16) << 32);
40
- "cortex-a15-" TYPE_ARM_CPU);
57
break;
41
- object_property_add_child(obj, "cpu[*]", OBJECT(&s->cpus[n]),
58
case 3:
42
- &error_abort);
59
- addr = desc->source_address4
43
- }
60
- + (extract32(desc->address_extension_45, 0, 12) << 8);
44
61
+ addr = (uint64_t)desc->source_address4
45
object_initialize(&s->control, sizeof(s->control), TYPE_BCM2836_CONTROL);
62
+ + (extract64(desc->address_extension_45, 0, 16) << 32);
46
object_property_add_child(obj, "control", OBJECT(&s->control), NULL);
63
break;
47
@@ -XXX,XX +XXX,XX @@ static void bcm2836_realize(DeviceState *dev, Error **errp)
64
case 4:
48
65
- addr = desc->source_address5
49
/* common peripherals from bcm2835 */
66
- + (extract32(desc->address_extension_45, 16, 12) << 20);
50
67
+ addr = (uint64_t)desc->source_address5
51
+ obj = OBJECT(dev);
68
+ + (extract64(desc->address_extension_45, 16, 16) << 32);
52
+ for (n = 0; n < BCM2836_NCPUS; n++) {
69
break;
53
+ object_initialize(&s->cpus[n], sizeof(s->cpus[n]),
70
default:
54
+ s->cpu_type);
71
addr = 0;
55
+ object_property_add_child(obj, "cpu[*]", OBJECT(&s->cpus[n]),
56
+ &error_abort);
57
+ }
58
+
59
obj = object_property_get_link(OBJECT(dev), "ram", &err);
60
if (obj == NULL) {
61
error_setg(errp, "%s: required ram link not found: %s",
62
@@ -XXX,XX +XXX,XX @@ static void bcm2836_realize(DeviceState *dev, Error **errp)
63
}
64
65
static Property bcm2836_props[] = {
66
+ DEFINE_PROP_STRING("cpu-type", BCM2836State, cpu_type),
67
DEFINE_PROP_UINT32("enabled-cpus", BCM2836State, enabled_cpus, BCM2836_NCPUS),
68
DEFINE_PROP_END_OF_LIST()
69
};
70
diff --git a/hw/arm/raspi.c b/hw/arm/raspi.c
71
index XXXXXXX..XXXXXXX 100644
72
--- a/hw/arm/raspi.c
73
+++ b/hw/arm/raspi.c
74
@@ -XXX,XX +XXX,XX @@ static void raspi2_init(MachineState *machine)
75
/* Setup the SOC */
76
object_property_add_const_link(OBJECT(&s->soc), "ram", OBJECT(&s->ram),
77
&error_abort);
78
+ object_property_set_str(OBJECT(&s->soc), machine->cpu_type, "cpu-type",
79
+ &error_abort);
80
object_property_set_int(OBJECT(&s->soc), smp_cpus, "enabled-cpus",
81
&error_abort);
82
object_property_set_int(OBJECT(&s->soc), 0xa21041, "board-rev",
83
@@ -XXX,XX +XXX,XX @@ static void raspi2_machine_init(MachineClass *mc)
84
mc->no_parallel = 1;
85
mc->no_floppy = 1;
86
mc->no_cdrom = 1;
87
+ mc->default_cpu_type = ARM_CPU_TYPE_NAME("cortex-a15");
88
mc->max_cpus = BCM2836_NCPUS;
89
mc->min_cpus = BCM2836_NCPUS;
90
mc->default_cpus = BCM2836_NCPUS;
91
--
72
--
92
2.16.1
73
2.34.1
93
94
diff view generated by jsdifflib
1
From: Philippe Mathieu-Daudé <f4bug@amsat.org>
1
From: Thomas Huth <thuth@redhat.com>
2
2
3
(qemu) info mtree
3
"make check-qtest-aarch64" recently started failing on FreeBSD builds,
4
address-space: cpu-memory-0
4
and valgrind on Linux also detected that there is something fishy with
5
0000000000000000-ffffffffffffffff (prio 0, i/o): system
5
the new stm32l4x5-usart: The code forgot to set the correct class_size
6
0000000000000000-0000000007ffffff (prio 0, rom): aspeed.boot_rom
6
here, so the various class_init functions in this file wrote beyond
7
- 000000001e600000-000000001e7fffff (prio -1, i/o): aspeed_soc.io
7
the allocated buffer when setting the subc->type field.
8
+ 000000001e600000-000000001e7fffff (prio -1000, i/o): aspeed_soc.io
9
000000001e620000-000000001e6200ff (prio 0, i/o): aspeed.smc.ast2500-fmc
10
000000001e630000-000000001e6300ff (prio 0, i/o): aspeed.smc.ast2500-spi1
11
000000001e631000-000000001e6310ff (prio 0, i/o): aspeed.smc.ast2500-spi2
12
8
13
Signed-off-by: Philippe Mathieu-Daudé <f4bug@amsat.org>
9
Fixes: 4fb37aea7e ("hw/char: Implement STM32L4x5 USART skeleton")
14
Reviewed-by: Cédric Le Goater <clg@kaod.org>
10
Signed-off-by: Thomas Huth <thuth@redhat.com>
15
Reviewed-by: Andrew Jeffery <andrew@aj.id.au>
11
Reviewed-by: Philippe Mathieu-Daudé <philmd@linaro.org>
16
Message-id: 20180209085755.30414-3-f4bug@amsat.org
12
Message-id: 20240429075908.36302-1-thuth@redhat.com
17
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
13
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
18
---
14
---
19
include/hw/arm/aspeed_soc.h | 1 -
15
hw/char/stm32l4x5_usart.c | 1 +
20
hw/arm/aspeed_soc.c | 32 +++-----------------------------
16
1 file changed, 1 insertion(+)
21
2 files changed, 3 insertions(+), 30 deletions(-)
22
17
23
diff --git a/include/hw/arm/aspeed_soc.h b/include/hw/arm/aspeed_soc.h
18
diff --git a/hw/char/stm32l4x5_usart.c b/hw/char/stm32l4x5_usart.c
24
index XXXXXXX..XXXXXXX 100644
19
index XXXXXXX..XXXXXXX 100644
25
--- a/include/hw/arm/aspeed_soc.h
20
--- a/hw/char/stm32l4x5_usart.c
26
+++ b/include/hw/arm/aspeed_soc.h
21
+++ b/hw/char/stm32l4x5_usart.c
27
@@ -XXX,XX +XXX,XX @@ typedef struct AspeedSoCState {
22
@@ -XXX,XX +XXX,XX @@ static const TypeInfo stm32l4x5_usart_types[] = {
28
23
.parent = TYPE_SYS_BUS_DEVICE,
29
/*< public >*/
24
.instance_size = sizeof(Stm32l4x5UsartBaseState),
30
ARMCPU cpu;
25
.instance_init = stm32l4x5_usart_base_init,
31
- MemoryRegion iomem;
26
+ .class_size = sizeof(Stm32l4x5UsartBaseClass),
32
MemoryRegion sram;
27
.class_init = stm32l4x5_usart_base_class_init,
33
AspeedVICState vic;
28
.abstract = true,
34
AspeedTimerCtrlState timerctrl;
29
}, {
35
diff --git a/hw/arm/aspeed_soc.c b/hw/arm/aspeed_soc.c
36
index XXXXXXX..XXXXXXX 100644
37
--- a/hw/arm/aspeed_soc.c
38
+++ b/hw/arm/aspeed_soc.c
39
@@ -XXX,XX +XXX,XX @@
40
#include "qemu-common.h"
41
#include "cpu.h"
42
#include "exec/address-spaces.h"
43
+#include "hw/misc/unimp.h"
44
#include "hw/arm/aspeed_soc.h"
45
#include "hw/char/serial.h"
46
#include "qemu/log.h"
47
@@ -XXX,XX +XXX,XX @@ static const AspeedSoCInfo aspeed_socs[] = {
48
},
49
};
50
51
-/*
52
- * IO handlers: simply catch any reads/writes to IO addresses that aren't
53
- * handled by a device mapping.
54
- */
55
-
56
-static uint64_t aspeed_soc_io_read(void *p, hwaddr offset, unsigned size)
57
-{
58
- qemu_log_mask(LOG_UNIMP, "%s: 0x%" HWADDR_PRIx " [%u]\n",
59
- __func__, offset, size);
60
- return 0;
61
-}
62
-
63
-static void aspeed_soc_io_write(void *opaque, hwaddr offset, uint64_t value,
64
- unsigned size)
65
-{
66
- qemu_log_mask(LOG_UNIMP, "%s: 0x%" HWADDR_PRIx " <- 0x%" PRIx64 " [%u]\n",
67
- __func__, offset, value, size);
68
-}
69
-
70
-static const MemoryRegionOps aspeed_soc_io_ops = {
71
- .read = aspeed_soc_io_read,
72
- .write = aspeed_soc_io_write,
73
- .endianness = DEVICE_LITTLE_ENDIAN,
74
-};
75
-
76
static void aspeed_soc_init(Object *obj)
77
{
78
AspeedSoCState *s = ASPEED_SOC(obj);
79
@@ -XXX,XX +XXX,XX @@ static void aspeed_soc_realize(DeviceState *dev, Error **errp)
80
Error *err = NULL, *local_err = NULL;
81
82
/* IO space */
83
- memory_region_init_io(&s->iomem, NULL, &aspeed_soc_io_ops, NULL,
84
- "aspeed_soc.io", ASPEED_SOC_IOMEM_SIZE);
85
- memory_region_add_subregion_overlap(get_system_memory(),
86
- ASPEED_SOC_IOMEM_BASE, &s->iomem, -1);
87
+ create_unimplemented_device("aspeed_soc.io",
88
+ ASPEED_SOC_IOMEM_BASE, ASPEED_SOC_IOMEM_SIZE);
89
90
/* CPU */
91
object_property_set_bool(OBJECT(&s->cpu), true, "realized", &err);
92
--
30
--
93
2.16.1
31
2.34.1
94
32
95
33
diff view generated by jsdifflib
1
From: Richard Henderson <richard.henderson@linaro.org>
1
From: Philippe Mathieu-Daudé <philmd@linaro.org>
2
2
3
Because they are ARM_CP_STATE_AA64, ARM_CP_64BIT is implied.
3
Use little endian for derivative OTP fuse key.
4
4
5
Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
5
Cc: qemu-stable@nongnu.org
6
Message-id: 20180211205848.4568-2-richard.henderson@linaro.org
6
Fixes: c752bb079b ("hw/nvram: NPCM7xx OTP device model")
7
Suggested-by: Avi Fishman <Avi.Fishman@nuvoton.com>
8
Signed-off-by: Philippe Mathieu-Daudé <philmd@linaro.org>
9
Message-id: 20240422125813.1403-1-philmd@linaro.org
7
Reviewed-by: Peter Maydell <peter.maydell@linaro.org>
10
Reviewed-by: Peter Maydell <peter.maydell@linaro.org>
8
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
11
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
9
---
12
---
10
target/arm/helper.c | 8 ++++----
13
hw/arm/npcm7xx.c | 3 ++-
11
1 file changed, 4 insertions(+), 4 deletions(-)
14
1 file changed, 2 insertions(+), 1 deletion(-)
12
15
13
diff --git a/target/arm/helper.c b/target/arm/helper.c
16
diff --git a/hw/arm/npcm7xx.c b/hw/arm/npcm7xx.c
14
index XXXXXXX..XXXXXXX 100644
17
index XXXXXXX..XXXXXXX 100644
15
--- a/target/arm/helper.c
18
--- a/hw/arm/npcm7xx.c
16
+++ b/target/arm/helper.c
19
+++ b/hw/arm/npcm7xx.c
17
@@ -XXX,XX +XXX,XX @@ static void zcr_write(CPUARMState *env, const ARMCPRegInfo *ri,
20
@@ -XXX,XX +XXX,XX @@
18
static const ARMCPRegInfo zcr_el1_reginfo = {
21
#include "hw/qdev-clock.h"
19
.name = "ZCR_EL1", .state = ARM_CP_STATE_AA64,
22
#include "hw/qdev-properties.h"
20
.opc0 = 3, .opc1 = 0, .crn = 1, .crm = 2, .opc2 = 0,
23
#include "qapi/error.h"
21
- .access = PL1_RW, .accessfn = zcr_access, .type = ARM_CP_64BIT,
24
+#include "qemu/bswap.h"
22
+ .access = PL1_RW, .accessfn = zcr_access,
25
#include "qemu/units.h"
23
.fieldoffset = offsetof(CPUARMState, vfp.zcr_el[1]),
26
#include "sysemu/sysemu.h"
24
.writefn = zcr_write, .raw_writefn = raw_write
27
#include "target/arm/cpu-qom.h"
25
};
28
@@ -XXX,XX +XXX,XX @@ static void npcm7xx_init_fuses(NPCM7xxState *s)
26
@@ -XXX,XX +XXX,XX @@ static const ARMCPRegInfo zcr_el1_reginfo = {
29
* The initial mask of disabled modules indicates the chip derivative (e.g.
27
static const ARMCPRegInfo zcr_el2_reginfo = {
30
* NPCM750 or NPCM730).
28
.name = "ZCR_EL2", .state = ARM_CP_STATE_AA64,
31
*/
29
.opc0 = 3, .opc1 = 4, .crn = 1, .crm = 2, .opc2 = 0,
32
- value = tswap32(nc->disabled_modules);
30
- .access = PL2_RW, .accessfn = zcr_access, .type = ARM_CP_64BIT,
33
+ value = cpu_to_le32(nc->disabled_modules);
31
+ .access = PL2_RW, .accessfn = zcr_access,
34
npcm7xx_otp_array_write(&s->fuse_array, &value, NPCM7XX_FUSE_DERIVATIVE,
32
.fieldoffset = offsetof(CPUARMState, vfp.zcr_el[2]),
35
sizeof(value));
33
.writefn = zcr_write, .raw_writefn = raw_write
36
}
34
};
35
@@ -XXX,XX +XXX,XX @@ static const ARMCPRegInfo zcr_el2_reginfo = {
36
static const ARMCPRegInfo zcr_no_el2_reginfo = {
37
.name = "ZCR_EL2", .state = ARM_CP_STATE_AA64,
38
.opc0 = 3, .opc1 = 4, .crn = 1, .crm = 2, .opc2 = 0,
39
- .access = PL2_RW, .type = ARM_CP_64BIT,
40
+ .access = PL2_RW,
41
.readfn = arm_cp_read_zero, .writefn = arm_cp_write_ignore
42
};
43
44
static const ARMCPRegInfo zcr_el3_reginfo = {
45
.name = "ZCR_EL3", .state = ARM_CP_STATE_AA64,
46
.opc0 = 3, .opc1 = 6, .crn = 1, .crm = 2, .opc2 = 0,
47
- .access = PL3_RW, .accessfn = zcr_access, .type = ARM_CP_64BIT,
48
+ .access = PL3_RW, .accessfn = zcr_access,
49
.fieldoffset = offsetof(CPUARMState, vfp.zcr_el[3]),
50
.writefn = zcr_write, .raw_writefn = raw_write
51
};
52
--
37
--
53
2.16.1
38
2.34.1
54
39
55
40
diff view generated by jsdifflib
1
In commit abc24d86cc0364f we accidentally broke migration of
1
From: Inès Varhol <ines.varhol@telecom-paris.fr>
2
the stack pointer value for the mode (process, handler) the CPU
3
is not currently running as. (The commit correctly removed the
4
no-longer-used v7m.current_sp flag from the VMState but also
5
deleted the still very much in use v7m.other_sp SP value field.)
6
2
7
Add a subsection to migrate it again. (We don't need to care
3
This device implements the IM120417002 colors shield v1.1 for Arduino
8
about trying to retain compatibility with pre-abc24d86cc0364f
4
(which relies on the DM163 8x3-channel led driving logic) and features
9
versions of QEMU, because that commit bumped the version_id
5
a simple display of an 8x8 RGB matrix. The columns of the matrix are
10
and we've since bumped it again a couple of times.)
6
driven by the DM163 and the rows are driven externally.
11
7
8
Acked-by: Alistair Francis <alistair.francis@wdc.com>
9
Signed-off-by: Arnaud Minier <arnaud.minier@telecom-paris.fr>
10
Signed-off-by: Inès Varhol <ines.varhol@telecom-paris.fr>
11
Reviewed-by: Philippe Mathieu-Daudé <philmd@linaro.org>
12
Message-id: 20240424200929.240921-2-ines.varhol@telecom-paris.fr
13
[PMM: updated to new reset hold method prototype]
12
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
14
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
13
Reviewed-by: Richard Henderson <richard.henderson@linaro.org>
14
Message-id: 20180209165810.6668-11-peter.maydell@linaro.org
15
---
15
---
16
target/arm/machine.c | 11 +++++++++++
16
docs/system/arm/b-l475e-iot01a.rst | 3 +-
17
1 file changed, 11 insertions(+)
17
include/hw/display/dm163.h | 59 +++++
18
hw/display/dm163.c | 349 +++++++++++++++++++++++++++++
19
hw/display/Kconfig | 3 +
20
hw/display/meson.build | 1 +
21
hw/display/trace-events | 14 ++
22
6 files changed, 428 insertions(+), 1 deletion(-)
23
create mode 100644 include/hw/display/dm163.h
24
create mode 100644 hw/display/dm163.c
18
25
19
diff --git a/target/arm/machine.c b/target/arm/machine.c
26
diff --git a/docs/system/arm/b-l475e-iot01a.rst b/docs/system/arm/b-l475e-iot01a.rst
20
index XXXXXXX..XXXXXXX 100644
27
index XXXXXXX..XXXXXXX 100644
21
--- a/target/arm/machine.c
28
--- a/docs/system/arm/b-l475e-iot01a.rst
22
+++ b/target/arm/machine.c
29
+++ b/docs/system/arm/b-l475e-iot01a.rst
23
@@ -XXX,XX +XXX,XX @@ static const VMStateDescription vmstate_m_scr = {
30
@@ -XXX,XX +XXX,XX @@ USART, I2C, SPI, CAN and USB OTG, as well as a variety of sensors.
24
}
31
Supported devices
25
};
32
"""""""""""""""""
26
33
27
+static const VMStateDescription vmstate_m_other_sp = {
34
-Currently B-L475E-IOT01A machine's only supports the following devices:
28
+ .name = "cpu/m/other-sp",
35
+Currently B-L475E-IOT01A machines support the following devices:
36
37
- Cortex-M4F based STM32L4x5 SoC
38
- STM32L4x5 EXTI (Extended interrupts and events controller)
39
@@ -XXX,XX +XXX,XX @@ Currently B-L475E-IOT01A machine's only supports the following devices:
40
- STM32L4x5 RCC (Reset and clock control)
41
- STM32L4x5 GPIOs (General-purpose I/Os)
42
- STM32L4x5 USARTs, UARTs and LPUART (Serial ports)
43
+- optional 8x8 led display (based on DM163 driver)
44
45
Missing devices
46
"""""""""""""""
47
diff --git a/include/hw/display/dm163.h b/include/hw/display/dm163.h
48
new file mode 100644
49
index XXXXXXX..XXXXXXX
50
--- /dev/null
51
+++ b/include/hw/display/dm163.h
52
@@ -XXX,XX +XXX,XX @@
53
+/*
54
+ * QEMU DM163 8x3-channel constant current led driver
55
+ * driving columns of associated 8x8 RGB matrix.
56
+ *
57
+ * Copyright (C) 2024 Samuel Tardieu <sam@rfc1149.net>
58
+ * Copyright (C) 2024 Arnaud Minier <arnaud.minier@telecom-paris.fr>
59
+ * Copyright (C) 2024 Inès Varhol <ines.varhol@telecom-paris.fr>
60
+ *
61
+ * SPDX-License-Identifier: GPL-2.0-or-later
62
+ */
63
+
64
+#ifndef HW_DISPLAY_DM163_H
65
+#define HW_DISPLAY_DM163_H
66
+
67
+#include "qom/object.h"
68
+#include "hw/qdev-core.h"
69
+
70
+#define TYPE_DM163 "dm163"
71
+OBJECT_DECLARE_SIMPLE_TYPE(DM163State, DM163);
72
+
73
+#define RGB_MATRIX_NUM_ROWS 8
74
+#define RGB_MATRIX_NUM_COLS 8
75
+#define DM163_NUM_LEDS (RGB_MATRIX_NUM_COLS * 3)
76
+/* The last row is filled with 0 (turned off row) */
77
+#define COLOR_BUFFER_SIZE (RGB_MATRIX_NUM_ROWS + 1)
78
+
79
+typedef struct DM163State {
80
+ DeviceState parent_obj;
81
+
82
+ /* DM163 driver */
83
+ uint64_t bank0_shift_register[3];
84
+ uint64_t bank1_shift_register[3];
85
+ uint16_t latched_outputs[DM163_NUM_LEDS];
86
+ uint16_t outputs[DM163_NUM_LEDS];
87
+ qemu_irq sout;
88
+
89
+ uint8_t sin;
90
+ uint8_t dck;
91
+ uint8_t rst_b;
92
+ uint8_t lat_b;
93
+ uint8_t selbk;
94
+ uint8_t en_b;
95
+
96
+ /* IM120417002 colors shield */
97
+ uint8_t activated_rows;
98
+
99
+ /* 8x8 RGB matrix */
100
+ QemuConsole *console;
101
+ uint8_t redraw;
102
+ /* Rows currently being displayed on the matrix. */
103
+ /* The last row is filled with 0 (turned off row) */
104
+ uint32_t buffer[COLOR_BUFFER_SIZE][RGB_MATRIX_NUM_COLS];
105
+ uint8_t last_buffer_idx;
106
+ uint8_t buffer_idx_of_row[RGB_MATRIX_NUM_ROWS];
107
+ /* Used to simulate retinal persistence of rows */
108
+ uint8_t row_persistence_delay[RGB_MATRIX_NUM_ROWS];
109
+} DM163State;
110
+
111
+#endif /* HW_DISPLAY_DM163_H */
112
diff --git a/hw/display/dm163.c b/hw/display/dm163.c
113
new file mode 100644
114
index XXXXXXX..XXXXXXX
115
--- /dev/null
116
+++ b/hw/display/dm163.c
117
@@ -XXX,XX +XXX,XX @@
118
+/*
119
+ * QEMU DM163 8x3-channel constant current led driver
120
+ * driving columns of associated 8x8 RGB matrix.
121
+ *
122
+ * Copyright (C) 2024 Samuel Tardieu <sam@rfc1149.net>
123
+ * Copyright (C) 2024 Arnaud Minier <arnaud.minier@telecom-paris.fr>
124
+ * Copyright (C) 2024 Inès Varhol <ines.varhol@telecom-paris.fr>
125
+ *
126
+ * SPDX-License-Identifier: GPL-2.0-or-later
127
+ */
128
+
129
+/*
130
+ * The reference used for the DM163 is the following :
131
+ * http://www.siti.com.tw/product/spec/LED/DM163.pdf
132
+ */
133
+
134
+#include "qemu/osdep.h"
135
+#include "qapi/error.h"
136
+#include "migration/vmstate.h"
137
+#include "hw/irq.h"
138
+#include "hw/qdev-properties.h"
139
+#include "hw/display/dm163.h"
140
+#include "ui/console.h"
141
+#include "trace.h"
142
+
143
+#define LED_SQUARE_SIZE 100
144
+/* Number of frames a row stays visible after being turned off. */
145
+#define ROW_PERSISTENCE 3
146
+#define TURNED_OFF_ROW (COLOR_BUFFER_SIZE - 1)
147
+
148
+static const VMStateDescription vmstate_dm163 = {
149
+ .name = TYPE_DM163,
29
+ .version_id = 1,
150
+ .version_id = 1,
30
+ .minimum_version_id = 1,
151
+ .minimum_version_id = 1,
31
+ .fields = (VMStateField[]) {
152
+ .fields = (const VMStateField[]) {
32
+ VMSTATE_UINT32(env.v7m.other_sp, ARMCPU),
153
+ VMSTATE_UINT64_ARRAY(bank0_shift_register, DM163State, 3),
154
+ VMSTATE_UINT64_ARRAY(bank1_shift_register, DM163State, 3),
155
+ VMSTATE_UINT16_ARRAY(latched_outputs, DM163State, DM163_NUM_LEDS),
156
+ VMSTATE_UINT16_ARRAY(outputs, DM163State, DM163_NUM_LEDS),
157
+ VMSTATE_UINT8(dck, DM163State),
158
+ VMSTATE_UINT8(en_b, DM163State),
159
+ VMSTATE_UINT8(lat_b, DM163State),
160
+ VMSTATE_UINT8(rst_b, DM163State),
161
+ VMSTATE_UINT8(selbk, DM163State),
162
+ VMSTATE_UINT8(sin, DM163State),
163
+ VMSTATE_UINT8(activated_rows, DM163State),
164
+ VMSTATE_UINT32_2DARRAY(buffer, DM163State, COLOR_BUFFER_SIZE,
165
+ RGB_MATRIX_NUM_COLS),
166
+ VMSTATE_UINT8(last_buffer_idx, DM163State),
167
+ VMSTATE_UINT8_ARRAY(buffer_idx_of_row, DM163State, RGB_MATRIX_NUM_ROWS),
168
+ VMSTATE_UINT8_ARRAY(row_persistence_delay, DM163State,
169
+ RGB_MATRIX_NUM_ROWS),
33
+ VMSTATE_END_OF_LIST()
170
+ VMSTATE_END_OF_LIST()
34
+ }
171
+ }
35
+};
172
+};
36
+
173
+
37
static const VMStateDescription vmstate_m = {
174
+static void dm163_reset_hold(Object *obj, ResetType type)
38
.name = "cpu/m",
175
+{
39
.version_id = 4,
176
+ DM163State *s = DM163(obj);
40
@@ -XXX,XX +XXX,XX @@ static const VMStateDescription vmstate_m = {
177
+
41
&vmstate_m_faultmask_primask,
178
+ s->sin = 0;
42
&vmstate_m_csselr,
179
+ s->dck = 0;
43
&vmstate_m_scr,
180
+ s->rst_b = 0;
44
+ &vmstate_m_other_sp,
181
+ /* Ensuring the first falling edge of lat_b isn't missed */
45
NULL
182
+ s->lat_b = 1;
46
}
183
+ s->selbk = 0;
47
};
184
+ s->en_b = 0;
185
+ /* Reset stops the PWM, not the shift and latched registers. */
186
+ memset(s->outputs, 0, sizeof(s->outputs));
187
+
188
+ s->activated_rows = 0;
189
+ s->redraw = 0;
190
+ trace_dm163_redraw(s->redraw);
191
+ for (unsigned i = 0; i < COLOR_BUFFER_SIZE; i++) {
192
+ memset(s->buffer[i], 0, sizeof(s->buffer[0]));
193
+ }
194
+ s->last_buffer_idx = 0;
195
+ memset(s->buffer_idx_of_row, TURNED_OFF_ROW, sizeof(s->buffer_idx_of_row));
196
+ memset(s->row_persistence_delay, 0, sizeof(s->row_persistence_delay));
197
+}
198
+
199
+static void dm163_dck_gpio_handler(void *opaque, int line, int new_state)
200
+{
201
+ DM163State *s = opaque;
202
+
203
+ if (new_state && !s->dck) {
204
+ /*
205
+ * On raising dck, sample selbk to get the bank to use, and
206
+ * sample sin for the bit to enter into the bank shift buffer.
207
+ */
208
+ uint64_t *sb =
209
+ s->selbk ? s->bank1_shift_register : s->bank0_shift_register;
210
+ /* Output the outgoing bit on sout */
211
+ const bool sout = (s->selbk ? sb[2] & MAKE_64BIT_MASK(63, 1) :
212
+ sb[2] & MAKE_64BIT_MASK(15, 1)) != 0;
213
+ qemu_set_irq(s->sout, sout);
214
+ /* Enter sin into the shift buffer */
215
+ sb[2] = (sb[2] << 1) | ((sb[1] >> 63) & 1);
216
+ sb[1] = (sb[1] << 1) | ((sb[0] >> 63) & 1);
217
+ sb[0] = (sb[0] << 1) | s->sin;
218
+ }
219
+
220
+ s->dck = new_state;
221
+ trace_dm163_dck(new_state);
222
+}
223
+
224
+static void dm163_propagate_outputs(DM163State *s)
225
+{
226
+ s->last_buffer_idx = (s->last_buffer_idx + 1) % RGB_MATRIX_NUM_ROWS;
227
+ /* Values are output when reset is high and enable is low. */
228
+ if (s->rst_b && !s->en_b) {
229
+ memcpy(s->outputs, s->latched_outputs, sizeof(s->outputs));
230
+ } else {
231
+ memset(s->outputs, 0, sizeof(s->outputs));
232
+ }
233
+ for (unsigned x = 0; x < RGB_MATRIX_NUM_COLS; x++) {
234
+ /* Grouping the 3 RGB channels in a pixel value */
235
+ const uint16_t b = extract16(s->outputs[3 * x + 0], 6, 8);
236
+ const uint16_t g = extract16(s->outputs[3 * x + 1], 6, 8);
237
+ const uint16_t r = extract16(s->outputs[3 * x + 2], 6, 8);
238
+ uint32_t rgba = 0;
239
+
240
+ trace_dm163_channels(3 * x + 2, r);
241
+ trace_dm163_channels(3 * x + 1, g);
242
+ trace_dm163_channels(3 * x + 0, b);
243
+
244
+ rgba = deposit32(rgba, 0, 8, r);
245
+ rgba = deposit32(rgba, 8, 8, g);
246
+ rgba = deposit32(rgba, 16, 8, b);
247
+
248
+ /* Led values are sent from the last one to the first one */
249
+ s->buffer[s->last_buffer_idx][RGB_MATRIX_NUM_COLS - x - 1] = rgba;
250
+ }
251
+ for (unsigned row = 0; row < RGB_MATRIX_NUM_ROWS; row++) {
252
+ if (s->activated_rows & (1 << row)) {
253
+ s->buffer_idx_of_row[row] = s->last_buffer_idx;
254
+ s->redraw |= (1 << row);
255
+ trace_dm163_redraw(s->redraw);
256
+ }
257
+ }
258
+}
259
+
260
+static void dm163_en_b_gpio_handler(void *opaque, int line, int new_state)
261
+{
262
+ DM163State *s = opaque;
263
+
264
+ s->en_b = new_state;
265
+ dm163_propagate_outputs(s);
266
+ trace_dm163_en_b(new_state);
267
+}
268
+
269
+static uint8_t dm163_bank0(const DM163State *s, uint8_t led)
270
+{
271
+ /*
272
+ * Bank 0 uses 6 bits per led, so a value may be stored accross
273
+ * two uint64_t entries.
274
+ */
275
+ const uint8_t low_bit = 6 * led;
276
+ const uint8_t low_word = low_bit / 64;
277
+ const uint8_t high_word = (low_bit + 5) / 64;
278
+ const uint8_t low_shift = low_bit % 64;
279
+
280
+ if (low_word == high_word) {
281
+ /* Simple case: the value belongs to one entry. */
282
+ return extract64(s->bank0_shift_register[low_word], low_shift, 6);
283
+ }
284
+
285
+ const uint8_t nb_bits_in_low_word = 64 - low_shift;
286
+ const uint8_t nb_bits_in_high_word = 6 - nb_bits_in_low_word;
287
+
288
+ const uint64_t bits_in_low_word = \
289
+ extract64(s->bank0_shift_register[low_word], low_shift,
290
+ nb_bits_in_low_word);
291
+ const uint64_t bits_in_high_word = \
292
+ extract64(s->bank0_shift_register[high_word], 0,
293
+ nb_bits_in_high_word);
294
+ uint8_t val = 0;
295
+
296
+ val = deposit32(val, 0, nb_bits_in_low_word, bits_in_low_word);
297
+ val = deposit32(val, nb_bits_in_low_word, nb_bits_in_high_word,
298
+ bits_in_high_word);
299
+
300
+ return val;
301
+}
302
+
303
+static uint8_t dm163_bank1(const DM163State *s, uint8_t led)
304
+{
305
+ const uint64_t entry = s->bank1_shift_register[led / RGB_MATRIX_NUM_COLS];
306
+ return extract64(entry, 8 * (led % RGB_MATRIX_NUM_COLS), 8);
307
+}
308
+
309
+static void dm163_lat_b_gpio_handler(void *opaque, int line, int new_state)
310
+{
311
+ DM163State *s = opaque;
312
+
313
+ if (s->lat_b && !new_state) {
314
+ for (int led = 0; led < DM163_NUM_LEDS; led++) {
315
+ s->latched_outputs[led] = dm163_bank0(s, led) * dm163_bank1(s, led);
316
+ }
317
+ dm163_propagate_outputs(s);
318
+ }
319
+
320
+ s->lat_b = new_state;
321
+ trace_dm163_lat_b(new_state);
322
+}
323
+
324
+static void dm163_rst_b_gpio_handler(void *opaque, int line, int new_state)
325
+{
326
+ DM163State *s = opaque;
327
+
328
+ s->rst_b = new_state;
329
+ dm163_propagate_outputs(s);
330
+ trace_dm163_rst_b(new_state);
331
+}
332
+
333
+static void dm163_selbk_gpio_handler(void *opaque, int line, int new_state)
334
+{
335
+ DM163State *s = opaque;
336
+
337
+ s->selbk = new_state;
338
+ trace_dm163_selbk(new_state);
339
+}
340
+
341
+static void dm163_sin_gpio_handler(void *opaque, int line, int new_state)
342
+{
343
+ DM163State *s = opaque;
344
+
345
+ s->sin = new_state;
346
+ trace_dm163_sin(new_state);
347
+}
348
+
349
+static void dm163_rows_gpio_handler(void *opaque, int line, int new_state)
350
+{
351
+ DM163State *s = opaque;
352
+
353
+ if (new_state) {
354
+ s->activated_rows |= (1 << line);
355
+ s->buffer_idx_of_row[line] = s->last_buffer_idx;
356
+ s->redraw |= (1 << line);
357
+ trace_dm163_redraw(s->redraw);
358
+ } else {
359
+ s->activated_rows &= ~(1 << line);
360
+ s->row_persistence_delay[line] = ROW_PERSISTENCE;
361
+ }
362
+ trace_dm163_activated_rows(s->activated_rows);
363
+}
364
+
365
+static void dm163_invalidate_display(void *opaque)
366
+{
367
+ DM163State *s = (DM163State *)opaque;
368
+ s->redraw = 0xFF;
369
+ trace_dm163_redraw(s->redraw);
370
+}
371
+
372
+static void update_row_persistence_delay(DM163State *s, unsigned row)
373
+{
374
+ if (s->row_persistence_delay[row]) {
375
+ s->row_persistence_delay[row]--;
376
+ } else {
377
+ /*
378
+ * If the ROW_PERSISTENCE delay is up,
379
+ * the row is turned off.
380
+ */
381
+ s->buffer_idx_of_row[row] = TURNED_OFF_ROW;
382
+ s->redraw |= (1 << row);
383
+ trace_dm163_redraw(s->redraw);
384
+ }
385
+}
386
+
387
+static uint32_t *update_display_of_row(DM163State *s, uint32_t *dest,
388
+ unsigned row)
389
+{
390
+ for (unsigned _ = 0; _ < LED_SQUARE_SIZE; _++) {
391
+ for (int x = 0; x < RGB_MATRIX_NUM_COLS * LED_SQUARE_SIZE; x++) {
392
+ /* UI layer guarantees that there's 32 bits per pixel (Mar 2024) */
393
+ *dest++ = s->buffer[s->buffer_idx_of_row[row]][x / LED_SQUARE_SIZE];
394
+ }
395
+ }
396
+
397
+ dpy_gfx_update(s->console, 0, LED_SQUARE_SIZE * row,
398
+ RGB_MATRIX_NUM_COLS * LED_SQUARE_SIZE, LED_SQUARE_SIZE);
399
+ s->redraw &= ~(1 << row);
400
+ trace_dm163_redraw(s->redraw);
401
+
402
+ return dest;
403
+}
404
+
405
+static void dm163_update_display(void *opaque)
406
+{
407
+ DM163State *s = (DM163State *)opaque;
408
+ DisplaySurface *surface = qemu_console_surface(s->console);
409
+ uint32_t *dest;
410
+
411
+ dest = surface_data(surface);
412
+ for (unsigned row = 0; row < RGB_MATRIX_NUM_ROWS; row++) {
413
+ update_row_persistence_delay(s, row);
414
+ if (!extract8(s->redraw, row, 1)) {
415
+ dest += LED_SQUARE_SIZE * LED_SQUARE_SIZE * RGB_MATRIX_NUM_COLS;
416
+ continue;
417
+ }
418
+ dest = update_display_of_row(s, dest, row);
419
+ }
420
+}
421
+
422
+static const GraphicHwOps dm163_ops = {
423
+ .invalidate = dm163_invalidate_display,
424
+ .gfx_update = dm163_update_display,
425
+};
426
+
427
+static void dm163_realize(DeviceState *dev, Error **errp)
428
+{
429
+ DM163State *s = DM163(dev);
430
+
431
+ qdev_init_gpio_in(dev, dm163_rows_gpio_handler, RGB_MATRIX_NUM_ROWS);
432
+ qdev_init_gpio_in(dev, dm163_sin_gpio_handler, 1);
433
+ qdev_init_gpio_in(dev, dm163_dck_gpio_handler, 1);
434
+ qdev_init_gpio_in(dev, dm163_rst_b_gpio_handler, 1);
435
+ qdev_init_gpio_in(dev, dm163_lat_b_gpio_handler, 1);
436
+ qdev_init_gpio_in(dev, dm163_selbk_gpio_handler, 1);
437
+ qdev_init_gpio_in(dev, dm163_en_b_gpio_handler, 1);
438
+ qdev_init_gpio_out_named(dev, &s->sout, "sout", 1);
439
+
440
+ s->console = graphic_console_init(dev, 0, &dm163_ops, s);
441
+ qemu_console_resize(s->console, RGB_MATRIX_NUM_COLS * LED_SQUARE_SIZE,
442
+ RGB_MATRIX_NUM_ROWS * LED_SQUARE_SIZE);
443
+}
444
+
445
+static void dm163_class_init(ObjectClass *klass, void *data)
446
+{
447
+ DeviceClass *dc = DEVICE_CLASS(klass);
448
+ ResettableClass *rc = RESETTABLE_CLASS(klass);
449
+
450
+ dc->desc = "DM163";
451
+ dc->vmsd = &vmstate_dm163;
452
+ dc->realize = dm163_realize;
453
+ rc->phases.hold = dm163_reset_hold;
454
+ set_bit(DEVICE_CATEGORY_DISPLAY, dc->categories);
455
+}
456
+
457
+static const TypeInfo dm163_types[] = {
458
+ {
459
+ .name = TYPE_DM163,
460
+ .parent = TYPE_DEVICE,
461
+ .instance_size = sizeof(DM163State),
462
+ .class_init = dm163_class_init
463
+ }
464
+};
465
+
466
+DEFINE_TYPES(dm163_types)
467
diff --git a/hw/display/Kconfig b/hw/display/Kconfig
468
index XXXXXXX..XXXXXXX 100644
469
--- a/hw/display/Kconfig
470
+++ b/hw/display/Kconfig
471
@@ -XXX,XX +XXX,XX @@ config XLNX_DISPLAYPORT
472
bool
473
# defaults to "N", enabled by specific boards
474
depends on PIXMAN
475
+
476
+config DM163
477
+ bool
478
diff --git a/hw/display/meson.build b/hw/display/meson.build
479
index XXXXXXX..XXXXXXX 100644
480
--- a/hw/display/meson.build
481
+++ b/hw/display/meson.build
482
@@ -XXX,XX +XXX,XX @@ system_ss.add(when: 'CONFIG_NEXTCUBE', if_true: files('next-fb.c'))
483
484
system_ss.add(when: 'CONFIG_VGA', if_true: files('vga.c'))
485
system_ss.add(when: 'CONFIG_VIRTIO', if_true: files('virtio-dmabuf.c'))
486
+system_ss.add(when: 'CONFIG_DM163', if_true: files('dm163.c'))
487
488
if (config_all_devices.has_key('CONFIG_VGA_CIRRUS') or
489
config_all_devices.has_key('CONFIG_VGA_PCI') or
490
diff --git a/hw/display/trace-events b/hw/display/trace-events
491
index XXXXXXX..XXXXXXX 100644
492
--- a/hw/display/trace-events
493
+++ b/hw/display/trace-events
494
@@ -XXX,XX +XXX,XX @@ macfb_ctrl_write(uint64_t addr, uint64_t value, unsigned int size) "addr 0x%"PRI
495
macfb_sense_read(uint32_t value) "video sense: 0x%"PRIx32
496
macfb_sense_write(uint32_t value) "video sense: 0x%"PRIx32
497
macfb_update_mode(uint32_t width, uint32_t height, uint8_t depth) "setting mode to width %"PRId32 " height %"PRId32 " size %d"
498
+
499
+# dm163.c
500
+dm163_redraw(uint8_t redraw) "0x%02x"
501
+dm163_dck(unsigned new_state) "dck : %u"
502
+dm163_en_b(unsigned new_state) "en_b : %u"
503
+dm163_rst_b(unsigned new_state) "rst_b : %u"
504
+dm163_lat_b(unsigned new_state) "lat_b : %u"
505
+dm163_sin(unsigned new_state) "sin : %u"
506
+dm163_selbk(unsigned new_state) "selbk : %u"
507
+dm163_activated_rows(int new_state) "Activated rows : 0x%" PRIx32 ""
508
+dm163_bits_ppi(unsigned dest_width) "dest_width : %u"
509
+dm163_leds(int led, uint32_t value) "led %d: 0x%x"
510
+dm163_channels(int channel, uint8_t value) "channel %d: 0x%x"
511
+dm163_refresh_rate(uint32_t rr) "refresh rate %d"
48
--
512
--
49
2.16.1
513
2.34.1
50
514
51
515
diff view generated by jsdifflib
1
From: Richard Henderson <richard.henderson@linaro.org>
1
From: Inès Varhol <ines.varhol@telecom-paris.fr>
2
2
3
When storing to an AdvSIMD FP register, all of the high
3
Exposing SYSCFG inputs to the SoC is practical in order to wire the SoC
4
bits of the SVE register are zeroed. Therefore, call it
4
to the optional DM163 display from the board code (GPIOs outputs need
5
more often with is_q as a parameter.
5
to be connected to both SYSCFG inputs and DM163 inputs).
6
6
7
Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
7
STM32L4x5 SYSCFG in-irq interception needed to be changed accordingly.
8
Message-id: 20180211205848.4568-6-richard.henderson@linaro.org
8
9
Reviewed-by: Peter Maydell <peter.maydell@linaro.org>
9
Signed-off-by: Arnaud Minier <arnaud.minier@telecom-paris.fr>
10
Signed-off-by: Inès Varhol <ines.varhol@telecom-paris.fr>
11
Reviewed-by: Philippe Mathieu-Daudé <philmd@linaro.org>
12
Message-id: 20240424200929.240921-3-ines.varhol@telecom-paris.fr
10
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
13
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
11
---
14
---
12
target/arm/translate-a64.c | 162 +++++++++++++++++----------------------------
15
hw/arm/stm32l4x5_soc.c | 6 ++++--
13
1 file changed, 62 insertions(+), 100 deletions(-)
16
tests/qtest/stm32l4x5_gpio-test.c | 13 ++++++++-----
17
tests/qtest/stm32l4x5_syscfg-test.c | 17 ++++++++++-------
18
3 files changed, 22 insertions(+), 14 deletions(-)
14
19
15
diff --git a/target/arm/translate-a64.c b/target/arm/translate-a64.c
20
diff --git a/hw/arm/stm32l4x5_soc.c b/hw/arm/stm32l4x5_soc.c
16
index XXXXXXX..XXXXXXX 100644
21
index XXXXXXX..XXXXXXX 100644
17
--- a/target/arm/translate-a64.c
22
--- a/hw/arm/stm32l4x5_soc.c
18
+++ b/target/arm/translate-a64.c
23
+++ b/hw/arm/stm32l4x5_soc.c
19
@@ -XXX,XX +XXX,XX @@ static TCGv_i32 read_fp_sreg(DisasContext *s, int reg)
24
@@ -XXX,XX +XXX,XX @@
20
return v;
21
}
22
23
+/* Clear the bits above an N-bit vector, for N = (is_q ? 128 : 64).
24
+ * If SVE is not enabled, then there are only 128 bits in the vector.
25
+ */
26
+static void clear_vec_high(DisasContext *s, bool is_q, int rd)
27
+{
28
+ unsigned ofs = fp_reg_offset(s, rd, MO_64);
29
+ unsigned vsz = vec_full_reg_size(s);
30
+
31
+ if (!is_q) {
32
+ TCGv_i64 tcg_zero = tcg_const_i64(0);
33
+ tcg_gen_st_i64(tcg_zero, cpu_env, ofs + 8);
34
+ tcg_temp_free_i64(tcg_zero);
35
+ }
36
+ if (vsz > 16) {
37
+ tcg_gen_gvec_dup8i(ofs + 16, vsz - 16, vsz - 16, 0);
38
+ }
39
+}
40
+
41
static void write_fp_dreg(DisasContext *s, int reg, TCGv_i64 v)
42
{
43
- TCGv_i64 tcg_zero = tcg_const_i64(0);
44
+ unsigned ofs = fp_reg_offset(s, reg, MO_64);
45
46
- tcg_gen_st_i64(v, cpu_env, fp_reg_offset(s, reg, MO_64));
47
- tcg_gen_st_i64(tcg_zero, cpu_env, fp_reg_hi_offset(s, reg));
48
- tcg_temp_free_i64(tcg_zero);
49
+ tcg_gen_st_i64(v, cpu_env, ofs);
50
+ clear_vec_high(s, false, reg);
51
}
52
53
static void write_fp_sreg(DisasContext *s, int reg, TCGv_i32 v)
54
@@ -XXX,XX +XXX,XX @@ static void do_fp_ld(DisasContext *s, int destidx, TCGv_i64 tcg_addr, int size)
55
56
tcg_temp_free_i64(tmplo);
57
tcg_temp_free_i64(tmphi);
58
+
59
+ clear_vec_high(s, true, destidx);
60
}
61
62
/*
25
/*
63
@@ -XXX,XX +XXX,XX @@ static void write_vec_element_i32(DisasContext *s, TCGv_i32 tcg_src,
26
* STM32L4x5 SoC family
64
}
27
*
65
}
28
- * Copyright (c) 2023 Arnaud Minier <arnaud.minier@telecom-paris.fr>
66
29
- * Copyright (c) 2023 Inès Varhol <ines.varhol@telecom-paris.fr>
67
-/* Clear the high 64 bits of a 128 bit vector (in general non-quad
30
+ * Copyright (c) 2023-2024 Arnaud Minier <arnaud.minier@telecom-paris.fr>
68
- * vector ops all need to do this).
31
+ * Copyright (c) 2023-2024 Inès Varhol <ines.varhol@telecom-paris.fr>
69
- */
32
*
70
-static void clear_vec_high(DisasContext *s, int rd)
33
* SPDX-License-Identifier: GPL-2.0-or-later
71
-{
34
*
72
- TCGv_i64 tcg_zero = tcg_const_i64(0);
35
@@ -XXX,XX +XXX,XX @@ static void stm32l4x5_soc_realize(DeviceState *dev_soc, Error **errp)
73
-
74
- write_vec_element(s, tcg_zero, rd, 1, MO_64);
75
- tcg_temp_free_i64(tcg_zero);
76
-}
77
-
78
/* Store from vector register to memory */
79
static void do_vec_st(DisasContext *s, int srcidx, int element,
80
TCGv_i64 tcg_addr, int size)
81
@@ -XXX,XX +XXX,XX @@ static void disas_ldst_multiple_struct(DisasContext *s, uint32_t insn)
82
/* For non-quad operations, setting a slice of the low
83
* 64 bits of the register clears the high 64 bits (in
84
* the ARM ARM pseudocode this is implicit in the fact
85
- * that 'rval' is a 64 bit wide variable). We optimize
86
- * by noticing that we only need to do this the first
87
- * time we touch a register.
88
+ * that 'rval' is a 64 bit wide variable).
89
+ * For quad operations, we might still need to zero the
90
+ * high bits of SVE. We optimize by noticing that we only
91
+ * need to do this the first time we touch a register.
92
*/
93
- if (!is_q && e == 0 && (r == 0 || xs == selem - 1)) {
94
- clear_vec_high(s, tt);
95
+ if (e == 0 && (r == 0 || xs == selem - 1)) {
96
+ clear_vec_high(s, is_q, tt);
97
}
98
}
99
tcg_gen_addi_i64(tcg_addr, tcg_addr, ebytes);
100
@@ -XXX,XX +XXX,XX @@ static void disas_ldst_single_struct(DisasContext *s, uint32_t insn)
101
write_vec_element(s, tcg_tmp, rt, 0, MO_64);
102
if (is_q) {
103
write_vec_element(s, tcg_tmp, rt, 1, MO_64);
104
- } else {
105
- clear_vec_high(s, rt);
106
}
107
tcg_temp_free_i64(tcg_tmp);
108
+ clear_vec_high(s, is_q, rt);
109
} else {
110
/* Load/store one element per register */
111
if (is_load) {
112
@@ -XXX,XX +XXX,XX @@ static void handle_vec_simd_sqshrn(DisasContext *s, bool is_scalar, bool is_q,
113
}
114
115
if (!is_q) {
116
- clear_vec_high(s, rd);
117
write_vec_element(s, tcg_final, rd, 0, MO_64);
118
} else {
119
write_vec_element(s, tcg_final, rd, 1, MO_64);
120
@@ -XXX,XX +XXX,XX @@ static void handle_vec_simd_sqshrn(DisasContext *s, bool is_scalar, bool is_q,
121
tcg_temp_free_i64(tcg_rd);
122
tcg_temp_free_i32(tcg_rd_narrowed);
123
tcg_temp_free_i64(tcg_final);
124
- return;
125
+
126
+ clear_vec_high(s, is_q, rd);
127
}
128
129
/* SQSHLU, UQSHL, SQSHL: saturating left shifts */
130
@@ -XXX,XX +XXX,XX @@ static void handle_simd_qshl(DisasContext *s, bool scalar, bool is_q,
131
tcg_temp_free_i64(tcg_op);
132
}
133
tcg_temp_free_i64(tcg_shift);
134
-
135
- if (!is_q) {
136
- clear_vec_high(s, rd);
137
- }
138
+ clear_vec_high(s, is_q, rd);
139
} else {
140
TCGv_i32 tcg_shift = tcg_const_i32(shift);
141
static NeonGenTwoOpEnvFn * const fns[2][2][3] = {
142
@@ -XXX,XX +XXX,XX @@ static void handle_simd_qshl(DisasContext *s, bool scalar, bool is_q,
143
}
144
tcg_temp_free_i32(tcg_shift);
145
146
- if (!is_q && !scalar) {
147
- clear_vec_high(s, rd);
148
+ if (!scalar) {
149
+ clear_vec_high(s, is_q, rd);
150
}
36
}
151
}
37
}
38
39
+ qdev_pass_gpios(DEVICE(&s->syscfg), dev_soc, NULL);
40
+
41
/* EXTI device */
42
busdev = SYS_BUS_DEVICE(&s->exti);
43
if (!sysbus_realize(busdev, errp)) {
44
diff --git a/tests/qtest/stm32l4x5_gpio-test.c b/tests/qtest/stm32l4x5_gpio-test.c
45
index XXXXXXX..XXXXXXX 100644
46
--- a/tests/qtest/stm32l4x5_gpio-test.c
47
+++ b/tests/qtest/stm32l4x5_gpio-test.c
48
@@ -XXX,XX +XXX,XX @@
49
#define OTYPER_PUSH_PULL 0
50
#define OTYPER_OPEN_DRAIN 1
51
52
+/* SoC forwards GPIOs to SysCfg */
53
+#define SYSCFG "/machine/soc"
54
+
55
const uint32_t moder_reset[NUM_GPIOS] = {
56
0xABFFFFFF,
57
0xFFFFFEBF,
58
@@ -XXX,XX +XXX,XX @@ static void test_gpio_output_mode(const void *data)
59
uint32_t gpio = test_gpio_addr(data);
60
unsigned int gpio_id = get_gpio_id(gpio);
61
62
- qtest_irq_intercept_in(global_qtest, "/machine/soc/syscfg");
63
+ qtest_irq_intercept_in(global_qtest, SYSCFG);
64
65
/* Set a bit in ODR and check nothing happens */
66
gpio_set_bit(gpio, ODR, pin, 1);
67
@@ -XXX,XX +XXX,XX @@ static void test_gpio_input_mode(const void *data)
68
uint32_t gpio = test_gpio_addr(data);
69
unsigned int gpio_id = get_gpio_id(gpio);
70
71
- qtest_irq_intercept_in(global_qtest, "/machine/soc/syscfg");
72
+ qtest_irq_intercept_in(global_qtest, SYSCFG);
73
74
/* Configure a line as input, raise it, and check that the pin is high */
75
gpio_set_2bits(gpio, MODER, pin, MODER_INPUT);
76
@@ -XXX,XX +XXX,XX @@ static void test_pull_up_pull_down(const void *data)
77
uint32_t gpio = test_gpio_addr(data);
78
unsigned int gpio_id = get_gpio_id(gpio);
79
80
- qtest_irq_intercept_in(global_qtest, "/machine/soc/syscfg");
81
+ qtest_irq_intercept_in(global_qtest, SYSCFG);
82
83
/* Configure a line as input with pull-up, check the line is set high */
84
gpio_set_2bits(gpio, MODER, pin, MODER_INPUT);
85
@@ -XXX,XX +XXX,XX @@ static void test_push_pull(const void *data)
86
uint32_t gpio = test_gpio_addr(data);
87
uint32_t gpio2 = GPIO_BASE_ADDR + (GPIO_H - gpio);
88
89
- qtest_irq_intercept_in(global_qtest, "/machine/soc/syscfg");
90
+ qtest_irq_intercept_in(global_qtest, SYSCFG);
91
92
/* Setting a line high externally, configuring it in push-pull output */
93
/* And checking the pin was disconnected */
94
@@ -XXX,XX +XXX,XX @@ static void test_open_drain(const void *data)
95
uint32_t gpio = test_gpio_addr(data);
96
uint32_t gpio2 = GPIO_BASE_ADDR + (GPIO_H - gpio);
97
98
- qtest_irq_intercept_in(global_qtest, "/machine/soc/syscfg");
99
+ qtest_irq_intercept_in(global_qtest, SYSCFG);
100
101
/* Setting a line high externally, configuring it in open-drain output */
102
/* And checking the pin was disconnected */
103
diff --git a/tests/qtest/stm32l4x5_syscfg-test.c b/tests/qtest/stm32l4x5_syscfg-test.c
104
index XXXXXXX..XXXXXXX 100644
105
--- a/tests/qtest/stm32l4x5_syscfg-test.c
106
+++ b/tests/qtest/stm32l4x5_syscfg-test.c
107
@@ -XXX,XX +XXX,XX @@
108
/*
109
* QTest testcase for STM32L4x5_SYSCFG
110
*
111
- * Copyright (c) 2023 Arnaud Minier <arnaud.minier@telecom-paris.fr>
112
- * Copyright (c) 2023 Inès Varhol <ines.varhol@telecom-paris.fr>
113
+ * Copyright (c) 2024 Arnaud Minier <arnaud.minier@telecom-paris.fr>
114
+ * Copyright (c) 2024 Inès Varhol <ines.varhol@telecom-paris.fr>
115
*
116
* This work is licensed under the terms of the GNU GPL, version 2 or later.
117
* See the COPYING file in the top-level directory.
118
@@ -XXX,XX +XXX,XX @@
119
#define SYSCFG_SWPR2 0x28
120
#define INVALID_ADDR 0x2C
121
122
+/* SoC forwards GPIOs to SysCfg */
123
+#define SYSCFG "/machine/soc"
124
+#define EXTI "/machine/soc/exti"
125
+
126
static void syscfg_writel(unsigned int offset, uint32_t value)
127
{
128
writel(SYSCFG_BASE_ADDR + offset, value);
129
@@ -XXX,XX +XXX,XX @@ static uint32_t syscfg_readl(unsigned int offset)
130
131
static void syscfg_set_irq(int num, int level)
132
{
133
- qtest_set_irq_in(global_qtest, "/machine/soc/syscfg",
134
- NULL, num, level);
135
+ qtest_set_irq_in(global_qtest, SYSCFG, NULL, num, level);
152
}
136
}
153
@@ -XXX,XX +XXX,XX @@ static void handle_simd_intfp_conv(DisasContext *s, int rd, int rn,
137
154
}
138
static void system_reset(void)
155
}
139
@@ -XXX,XX +XXX,XX @@ static void test_interrupt(void)
156
140
* Test that GPIO rising lines result in an irq
157
- if (!is_double && elements == 2) {
141
* with the right configuration
158
- clear_vec_high(s, rd);
142
*/
159
- }
143
- qtest_irq_intercept_in(global_qtest, "/machine/soc/exti");
160
-
144
+ qtest_irq_intercept_in(global_qtest, EXTI);
161
tcg_temp_free_i64(tcg_int);
145
162
tcg_temp_free_ptr(tcg_fpst);
146
/* GPIOA is the default source for EXTI lines 0 to 15 */
163
tcg_temp_free_i32(tcg_shift);
147
164
+
148
@@ -XXX,XX +XXX,XX @@ static void test_irq_pin_multiplexer(void)
165
+ clear_vec_high(s, elements << size == 16, rd);
149
* Test that syscfg irq sets the right exti irq
166
}
150
*/
167
151
168
/* UCVTF/SCVTF - Integer to FP conversion */
152
- qtest_irq_intercept_in(global_qtest, "/machine/soc/exti");
169
@@ -XXX,XX +XXX,XX @@ static void handle_simd_shift_fpint_conv(DisasContext *s, bool is_scalar,
153
+ qtest_irq_intercept_in(global_qtest, EXTI);
170
write_vec_element(s, tcg_op, rd, pass, MO_64);
154
171
tcg_temp_free_i64(tcg_op);
155
syscfg_set_irq(0, 1);
172
}
156
173
- if (!is_q) {
157
@@ -XXX,XX +XXX,XX @@ static void test_irq_gpio_multiplexer(void)
174
- clear_vec_high(s, rd);
158
* Test that an irq is generated only by the right GPIO
175
- }
159
*/
176
+ clear_vec_high(s, is_q, rd);
160
177
} else {
161
- qtest_irq_intercept_in(global_qtest, "/machine/soc/exti");
178
int maxpass = is_scalar ? 1 : is_q ? 4 : 2;
162
+ qtest_irq_intercept_in(global_qtest, EXTI);
179
for (pass = 0; pass < maxpass; pass++) {
163
180
@@ -XXX,XX +XXX,XX @@ static void handle_simd_shift_fpint_conv(DisasContext *s, bool is_scalar,
164
/* GPIOA is the default source for EXTI lines 0 to 15 */
181
}
182
tcg_temp_free_i32(tcg_op);
183
}
184
- if (!is_q && !is_scalar) {
185
- clear_vec_high(s, rd);
186
+ if (!is_scalar) {
187
+ clear_vec_high(s, is_q, rd);
188
}
189
}
190
191
@@ -XXX,XX +XXX,XX @@ static void handle_3same_float(DisasContext *s, int size, int elements,
192
193
tcg_temp_free_ptr(fpst);
194
195
- if ((elements << size) < 4) {
196
- /* scalar, or non-quad vector op */
197
- clear_vec_high(s, rd);
198
- }
199
+ clear_vec_high(s, elements * (size ? 8 : 4) > 8, rd);
200
}
201
202
/* AdvSIMD scalar three same
203
@@ -XXX,XX +XXX,XX @@ static void handle_2misc_fcmp_zero(DisasContext *s, int opcode,
204
}
205
write_vec_element(s, tcg_res, rd, pass, MO_64);
206
}
207
- if (is_scalar) {
208
- clear_vec_high(s, rd);
209
- }
210
-
211
tcg_temp_free_i64(tcg_res);
212
tcg_temp_free_i64(tcg_zero);
213
tcg_temp_free_i64(tcg_op);
214
+
215
+ clear_vec_high(s, !is_scalar, rd);
216
} else {
217
TCGv_i32 tcg_op = tcg_temp_new_i32();
218
TCGv_i32 tcg_zero = tcg_const_i32(0);
219
@@ -XXX,XX +XXX,XX @@ static void handle_2misc_fcmp_zero(DisasContext *s, int opcode,
220
tcg_temp_free_i32(tcg_res);
221
tcg_temp_free_i32(tcg_zero);
222
tcg_temp_free_i32(tcg_op);
223
- if (!is_q && !is_scalar) {
224
- clear_vec_high(s, rd);
225
+ if (!is_scalar) {
226
+ clear_vec_high(s, is_q, rd);
227
}
228
}
229
230
@@ -XXX,XX +XXX,XX @@ static void handle_2misc_reciprocal(DisasContext *s, int opcode,
231
}
232
write_vec_element(s, tcg_res, rd, pass, MO_64);
233
}
234
- if (is_scalar) {
235
- clear_vec_high(s, rd);
236
- }
237
-
238
tcg_temp_free_i64(tcg_res);
239
tcg_temp_free_i64(tcg_op);
240
+ clear_vec_high(s, !is_scalar, rd);
241
} else {
242
TCGv_i32 tcg_op = tcg_temp_new_i32();
243
TCGv_i32 tcg_res = tcg_temp_new_i32();
244
@@ -XXX,XX +XXX,XX @@ static void handle_2misc_reciprocal(DisasContext *s, int opcode,
245
}
246
tcg_temp_free_i32(tcg_res);
247
tcg_temp_free_i32(tcg_op);
248
- if (!is_q && !is_scalar) {
249
- clear_vec_high(s, rd);
250
+ if (!is_scalar) {
251
+ clear_vec_high(s, is_q, rd);
252
}
253
}
254
tcg_temp_free_ptr(fpst);
255
@@ -XXX,XX +XXX,XX @@ static void handle_2misc_narrow(DisasContext *s, bool scalar,
256
write_vec_element_i32(s, tcg_res[pass], rd, destelt + pass, MO_32);
257
tcg_temp_free_i32(tcg_res[pass]);
258
}
259
- if (!is_q) {
260
- clear_vec_high(s, rd);
261
- }
262
+ clear_vec_high(s, is_q, rd);
263
}
264
265
/* Remaining saturating accumulating ops */
266
@@ -XXX,XX +XXX,XX @@ static void handle_2misc_satacc(DisasContext *s, bool is_scalar, bool is_u,
267
}
268
write_vec_element(s, tcg_rd, rd, pass, MO_64);
269
}
270
- if (is_scalar) {
271
- clear_vec_high(s, rd);
272
- }
273
-
274
tcg_temp_free_i64(tcg_rd);
275
tcg_temp_free_i64(tcg_rn);
276
+ clear_vec_high(s, !is_scalar, rd);
277
} else {
278
TCGv_i32 tcg_rn = tcg_temp_new_i32();
279
TCGv_i32 tcg_rd = tcg_temp_new_i32();
280
@@ -XXX,XX +XXX,XX @@ static void handle_2misc_satacc(DisasContext *s, bool is_scalar, bool is_u,
281
}
282
write_vec_element_i32(s, tcg_rd, rd, pass, MO_32);
283
}
284
-
285
- if (!is_q) {
286
- clear_vec_high(s, rd);
287
- }
288
-
289
tcg_temp_free_i32(tcg_rd);
290
tcg_temp_free_i32(tcg_rn);
291
+ clear_vec_high(s, is_q, rd);
292
}
293
}
294
295
@@ -XXX,XX +XXX,XX @@ static void handle_vec_simd_shri(DisasContext *s, bool is_q, bool is_u,
296
tcg_temp_free_i64(tcg_round);
297
298
done:
299
- if (!is_q) {
300
- clear_vec_high(s, rd);
301
- }
302
+ clear_vec_high(s, is_q, rd);
303
}
304
305
static void gen_shl8_ins_i64(TCGv_i64 d, TCGv_i64 a, int64_t shift)
306
@@ -XXX,XX +XXX,XX @@ static void handle_vec_simd_shrn(DisasContext *s, bool is_q,
307
}
308
309
if (!is_q) {
310
- clear_vec_high(s, rd);
311
write_vec_element(s, tcg_final, rd, 0, MO_64);
312
} else {
313
write_vec_element(s, tcg_final, rd, 1, MO_64);
314
}
315
-
316
if (round) {
317
tcg_temp_free_i64(tcg_round);
318
}
319
tcg_temp_free_i64(tcg_rn);
320
tcg_temp_free_i64(tcg_rd);
321
tcg_temp_free_i64(tcg_final);
322
- return;
323
+
324
+ clear_vec_high(s, is_q, rd);
325
}
326
327
328
@@ -XXX,XX +XXX,XX @@ static void handle_3rd_narrowing(DisasContext *s, int is_q, int is_u, int size,
329
write_vec_element_i32(s, tcg_res[pass], rd, pass + part, MO_32);
330
tcg_temp_free_i32(tcg_res[pass]);
331
}
332
- if (!is_q) {
333
- clear_vec_high(s, rd);
334
- }
335
+ clear_vec_high(s, is_q, rd);
336
}
337
338
static void handle_pmull_64(DisasContext *s, int is_q, int rd, int rn, int rm)
339
@@ -XXX,XX +XXX,XX @@ static void handle_simd_3same_pair(DisasContext *s, int is_q, int u, int opcode,
340
write_vec_element_i32(s, tcg_res[pass], rd, pass, MO_32);
341
tcg_temp_free_i32(tcg_res[pass]);
342
}
343
- if (!is_q) {
344
- clear_vec_high(s, rd);
345
- }
346
+ clear_vec_high(s, is_q, rd);
347
}
348
349
if (fpst) {
350
@@ -XXX,XX +XXX,XX @@ static void disas_simd_3same_int(DisasContext *s, uint32_t insn)
351
tcg_temp_free_i32(tcg_op2);
352
}
353
}
354
-
355
- if (!is_q) {
356
- clear_vec_high(s, rd);
357
- }
358
+ clear_vec_high(s, is_q, rd);
359
}
360
361
/* AdvSIMD three same
362
@@ -XXX,XX +XXX,XX @@ static void handle_rev(DisasContext *s, int opcode, bool u,
363
write_vec_element(s, tcg_tmp, rd, i, grp_size);
364
tcg_temp_free_i64(tcg_tmp);
365
}
366
- if (!is_q) {
367
- clear_vec_high(s, rd);
368
- }
369
+ clear_vec_high(s, is_q, rd);
370
} else {
371
int revmask = (1 << grp_size) - 1;
372
int esize = 8 << size;
373
@@ -XXX,XX +XXX,XX @@ static void disas_simd_two_reg_misc(DisasContext *s, uint32_t insn)
374
tcg_temp_free_i32(tcg_op);
375
}
376
}
377
- if (!is_q) {
378
- clear_vec_high(s, rd);
379
- }
380
+ clear_vec_high(s, is_q, rd);
381
382
if (need_rmode) {
383
gen_helper_set_rmode(tcg_rmode, tcg_rmode, cpu_env);
384
@@ -XXX,XX +XXX,XX @@ static void disas_simd_indexed(DisasContext *s, uint32_t insn)
385
tcg_temp_free_i64(tcg_res);
386
}
387
388
- if (is_scalar) {
389
- clear_vec_high(s, rd);
390
- }
391
-
392
tcg_temp_free_i64(tcg_idx);
393
+ clear_vec_high(s, !is_scalar, rd);
394
} else if (!is_long) {
395
/* 32 bit floating point, or 16 or 32 bit integer.
396
* For the 16 bit scalar case we use the usual Neon helpers and
397
@@ -XXX,XX +XXX,XX @@ static void disas_simd_indexed(DisasContext *s, uint32_t insn)
398
}
399
400
tcg_temp_free_i32(tcg_idx);
401
-
402
- if (!is_q) {
403
- clear_vec_high(s, rd);
404
- }
405
+ clear_vec_high(s, is_q, rd);
406
} else {
407
/* long ops: 16x16->32 or 32x32->64 */
408
TCGv_i64 tcg_res[2];
409
@@ -XXX,XX +XXX,XX @@ static void disas_simd_indexed(DisasContext *s, uint32_t insn)
410
}
411
tcg_temp_free_i64(tcg_idx);
412
413
- if (is_scalar) {
414
- clear_vec_high(s, rd);
415
- }
416
+ clear_vec_high(s, !is_scalar, rd);
417
} else {
418
TCGv_i32 tcg_idx = tcg_temp_new_i32();
419
165
420
--
166
--
421
2.16.1
167
2.34.1
422
168
423
169
diff view generated by jsdifflib
1
M profile cores have a similar setup for cache ID registers
1
From: Inès Varhol <ines.varhol@telecom-paris.fr>
2
to A profile:
3
* Cache Level ID Register (CLIDR) is a fixed value
4
* Cache Type Register (CTR) is a fixed value
5
* Cache Size ID Registers (CCSIDR) are a bank of registers;
6
which one you see is selected by the Cache Size Selection
7
Register (CSSELR)
8
2
9
The only difference is that they're in the NVIC memory mapped
3
Signed-off-by: Arnaud Minier <arnaud.minier@telecom-paris.fr>
10
register space rather than being coprocessor registers.
4
Signed-off-by: Inès Varhol <ines.varhol@telecom-paris.fr>
11
Implement the M profile view of them.
5
Reviewed-by: Philippe Mathieu-Daudé <philmd@linaro.org>
6
Message-id: 20240424200929.240921-4-ines.varhol@telecom-paris.fr
7
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
8
---
9
hw/arm/b-l475e-iot01a.c | 46 ++++++++++++++++++++++++++++-------------
10
1 file changed, 32 insertions(+), 14 deletions(-)
12
11
13
Since neither Cortex-M3 nor Cortex-M4 implement caches,
12
diff --git a/hw/arm/b-l475e-iot01a.c b/hw/arm/b-l475e-iot01a.c
14
we don't need to update their init functions and can leave
15
the ctr/clidr/ccsidr[] fields in their ARMCPU structs at zero.
16
Newer cores (like the Cortex-M33) will want to be able to
17
set these ID registers to non-zero values, though.
18
19
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
20
Reviewed-by: Richard Henderson <richard.henderson@linaro.org>
21
Message-id: 20180209165810.6668-6-peter.maydell@linaro.org
22
---
23
target/arm/cpu.h | 26 ++++++++++++++++++++++++++
24
hw/intc/armv7m_nvic.c | 16 ++++++++++++++++
25
target/arm/machine.c | 36 ++++++++++++++++++++++++++++++++++++
26
3 files changed, 78 insertions(+)
27
28
diff --git a/target/arm/cpu.h b/target/arm/cpu.h
29
index XXXXXXX..XXXXXXX 100644
13
index XXXXXXX..XXXXXXX 100644
30
--- a/target/arm/cpu.h
14
--- a/hw/arm/b-l475e-iot01a.c
31
+++ b/target/arm/cpu.h
15
+++ b/hw/arm/b-l475e-iot01a.c
32
@@ -XXX,XX +XXX,XX @@ typedef struct CPUARMState {
16
@@ -XXX,XX +XXX,XX @@
33
uint32_t faultmask[M_REG_NUM_BANKS];
17
* B-L475E-IOT01A Discovery Kit machine
34
uint32_t aircr; /* only holds r/w state if security extn implemented */
18
* (B-L475E-IOT01A IoT Node)
35
uint32_t secure; /* Is CPU in Secure state? (not guest visible) */
19
*
36
+ uint32_t csselr[M_REG_NUM_BANKS];
20
- * Copyright (c) 2023 Arnaud Minier <arnaud.minier@telecom-paris.fr>
37
} v7m;
21
- * Copyright (c) 2023 Inès Varhol <ines.varhol@telecom-paris.fr>
38
22
+ * Copyright (c) 2023-2024 Arnaud Minier <arnaud.minier@telecom-paris.fr>
39
/* Information associated with an exception about to be taken:
23
+ * Copyright (c) 2023-2024 Inès Varhol <ines.varhol@telecom-paris.fr>
40
@@ -XXX,XX +XXX,XX @@ FIELD(V7M_MPU_CTRL, ENABLE, 0, 1)
24
*
41
FIELD(V7M_MPU_CTRL, HFNMIENA, 1, 1)
25
* SPDX-License-Identifier: GPL-2.0-or-later
42
FIELD(V7M_MPU_CTRL, PRIVDEFENA, 2, 1)
26
*
43
27
@@ -XXX,XX +XXX,XX @@
44
+/* v7M CLIDR bits */
28
45
+FIELD(V7M_CLIDR, CTYPE_ALL, 0, 21)
29
/* B-L475E-IOT01A implementation is derived from netduinoplus2 */
46
+FIELD(V7M_CLIDR, LOUIS, 21, 3)
30
47
+FIELD(V7M_CLIDR, LOC, 24, 3)
31
-static void b_l475e_iot01a_init(MachineState *machine)
48
+FIELD(V7M_CLIDR, LOUU, 27, 3)
32
+#define TYPE_B_L475E_IOT01A MACHINE_TYPE_NAME("b-l475e-iot01a")
49
+FIELD(V7M_CLIDR, ICB, 30, 2)
33
+OBJECT_DECLARE_SIMPLE_TYPE(Bl475eMachineState, B_L475E_IOT01A)
50
+
34
+
51
+FIELD(V7M_CSSELR, IND, 0, 1)
35
+typedef struct Bl475eMachineState {
52
+FIELD(V7M_CSSELR, LEVEL, 1, 3)
36
+ MachineState parent_obj;
53
+/* We use the combination of InD and Level to index into cpu->ccsidr[];
54
+ * define a mask for this and check that it doesn't permit running off
55
+ * the end of the array.
56
+ */
57
+FIELD(V7M_CSSELR, INDEX, 0, 4)
58
+
37
+
59
+QEMU_BUILD_BUG_ON(ARRAY_SIZE(((ARMCPU *)0)->ccsidr) <= R_V7M_CSSELR_INDEX_MASK);
38
+ Stm32l4x5SocState soc;
39
+} Bl475eMachineState;
60
+
40
+
61
/* If adding a feature bit which corresponds to a Linux ELF
41
+static void bl475e_init(MachineState *machine)
62
* HWCAP bit, remember to update the feature-bit-to-hwcap
42
{
63
* mapping in linux-user/elfload.c:get_elf_hwcap().
43
+ Bl475eMachineState *s = B_L475E_IOT01A(machine);
64
@@ -XXX,XX +XXX,XX @@ static inline int arm_debug_target_el(CPUARMState *env)
44
const Stm32l4x5SocClass *sc;
65
}
45
- DeviceState *dev;
46
47
- dev = qdev_new(TYPE_STM32L4X5XG_SOC);
48
- object_property_add_child(OBJECT(machine), "soc", OBJECT(dev));
49
- sysbus_realize_and_unref(SYS_BUS_DEVICE(dev), &error_fatal);
50
+ object_initialize_child(OBJECT(machine), "soc", &s->soc,
51
+ TYPE_STM32L4X5XG_SOC);
52
+ sysbus_realize(SYS_BUS_DEVICE(&s->soc), &error_fatal);
53
54
- sc = STM32L4X5_SOC_GET_CLASS(dev);
55
- armv7m_load_kernel(ARM_CPU(first_cpu),
56
- machine->kernel_filename,
57
- 0, sc->flash_size);
58
+ sc = STM32L4X5_SOC_GET_CLASS(&s->soc);
59
+ armv7m_load_kernel(ARM_CPU(first_cpu), machine->kernel_filename, 0,
60
+ sc->flash_size);
66
}
61
}
67
62
68
+static inline bool arm_v7m_csselr_razwi(ARMCPU *cpu)
63
-static void b_l475e_iot01a_machine_init(MachineClass *mc)
69
+{
64
+static void bl475e_machine_init(ObjectClass *oc, void *data)
70
+ /* If all the CLIDR.Ctypem bits are 0 there are no caches, and
71
+ * CSSELR is RAZ/WI.
72
+ */
73
+ return (cpu->clidr & R_V7M_CLIDR_CTYPE_ALL_MASK) != 0;
74
+}
75
+
76
static inline bool aa64_generate_debug_exceptions(CPUARMState *env)
77
{
65
{
78
if (arm_is_secure(env)) {
66
+ MachineClass *mc = MACHINE_CLASS(oc);
79
diff --git a/hw/intc/armv7m_nvic.c b/hw/intc/armv7m_nvic.c
67
static const char *machine_valid_cpu_types[] = {
80
index XXXXXXX..XXXXXXX 100644
68
ARM_CPU_TYPE_NAME("cortex-m4"),
81
--- a/hw/intc/armv7m_nvic.c
69
NULL
82
+++ b/hw/intc/armv7m_nvic.c
70
};
83
@@ -XXX,XX +XXX,XX @@ static uint32_t nvic_readl(NVICState *s, uint32_t offset, MemTxAttrs attrs)
71
mc->desc = "B-L475E-IOT01A Discovery Kit (Cortex-M4)";
84
return cpu->id_isar4;
72
- mc->init = b_l475e_iot01a_init;
85
case 0xd74: /* ISAR5. */
73
+ mc->init = bl475e_init;
86
return cpu->id_isar5;
74
mc->valid_cpu_types = machine_valid_cpu_types;
87
+ case 0xd78: /* CLIDR */
75
88
+ return cpu->clidr;
76
/* SRAM pre-allocated as part of the SoC instantiation */
89
+ case 0xd7c: /* CTR */
77
mc->default_ram_size = 0;
90
+ return cpu->ctr;
78
}
91
+ case 0xd80: /* CSSIDR */
79
80
-DEFINE_MACHINE("b-l475e-iot01a", b_l475e_iot01a_machine_init)
81
+static const TypeInfo bl475e_machine_type[] = {
92
+ {
82
+ {
93
+ int idx = cpu->env.v7m.csselr[attrs.secure] & R_V7M_CSSELR_INDEX_MASK;
83
+ .name = TYPE_B_L475E_IOT01A,
94
+ return cpu->ccsidr[idx];
84
+ .parent = TYPE_MACHINE,
95
+ }
85
+ .instance_size = sizeof(Bl475eMachineState),
96
+ case 0xd84: /* CSSELR */
86
+ .class_init = bl475e_machine_init,
97
+ return cpu->env.v7m.csselr[attrs.secure];
98
/* TODO: Implement debug registers. */
99
case 0xd90: /* MPU_TYPE */
100
/* Unified MPU; if the MPU is not present this value is zero */
101
@@ -XXX,XX +XXX,XX @@ static void nvic_writel(NVICState *s, uint32_t offset, uint32_t value,
102
qemu_log_mask(LOG_UNIMP,
103
"NVIC: Aux fault status registers unimplemented\n");
104
break;
105
+ case 0xd84: /* CSSELR */
106
+ if (!arm_v7m_csselr_razwi(cpu)) {
107
+ cpu->env.v7m.csselr[attrs.secure] = value & R_V7M_CSSELR_INDEX_MASK;
108
+ }
109
+ break;
110
case 0xd90: /* MPU_TYPE */
111
return; /* RO */
112
case 0xd94: /* MPU_CTRL */
113
diff --git a/target/arm/machine.c b/target/arm/machine.c
114
index XXXXXXX..XXXXXXX 100644
115
--- a/target/arm/machine.c
116
+++ b/target/arm/machine.c
117
@@ -XXX,XX +XXX,XX @@ static const VMStateDescription vmstate_m_faultmask_primask = {
118
}
119
};
120
121
+/* CSSELR is in a subsection because we didn't implement it previously.
122
+ * Migration from an old implementation will leave it at zero, which
123
+ * is OK since the only CPUs in the old implementation make the
124
+ * register RAZ/WI.
125
+ * Since there was no version of QEMU which implemented the CSSELR for
126
+ * just non-secure, we transfer both banks here rather than putting
127
+ * the secure banked version in the m-security subsection.
128
+ */
129
+static bool csselr_vmstate_validate(void *opaque, int version_id)
130
+{
131
+ ARMCPU *cpu = opaque;
132
+
133
+ return cpu->env.v7m.csselr[M_REG_NS] <= R_V7M_CSSELR_INDEX_MASK
134
+ && cpu->env.v7m.csselr[M_REG_S] <= R_V7M_CSSELR_INDEX_MASK;
135
+}
136
+
137
+static bool m_csselr_needed(void *opaque)
138
+{
139
+ ARMCPU *cpu = opaque;
140
+
141
+ return !arm_v7m_csselr_razwi(cpu);
142
+}
143
+
144
+static const VMStateDescription vmstate_m_csselr = {
145
+ .name = "cpu/m/csselr",
146
+ .version_id = 1,
147
+ .minimum_version_id = 1,
148
+ .needed = m_csselr_needed,
149
+ .fields = (VMStateField[]) {
150
+ VMSTATE_UINT32_ARRAY(env.v7m.csselr, ARMCPU, M_REG_NUM_BANKS),
151
+ VMSTATE_VALIDATE("CSSELR is valid", csselr_vmstate_validate),
152
+ VMSTATE_END_OF_LIST()
153
+ }
87
+ }
154
+};
88
+};
155
+
89
+
156
static const VMStateDescription vmstate_m = {
90
+DEFINE_TYPES(bl475e_machine_type)
157
.name = "cpu/m",
158
.version_id = 4,
159
@@ -XXX,XX +XXX,XX @@ static const VMStateDescription vmstate_m = {
160
},
161
.subsections = (const VMStateDescription*[]) {
162
&vmstate_m_faultmask_primask,
163
+ &vmstate_m_csselr,
164
NULL
165
}
166
};
167
--
91
--
168
2.16.1
92
2.34.1
169
93
170
94
diff view generated by jsdifflib
1
From: Richard Henderson <richard.henderson@linaro.org>
1
From: Inès Varhol <ines.varhol@telecom-paris.fr>
2
2
3
Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
3
Signed-off-by: Arnaud Minier <arnaud.minier@telecom-paris.fr>
4
Message-id: 20180211205848.4568-3-richard.henderson@linaro.org
4
Signed-off-by: Inès Varhol <ines.varhol@telecom-paris.fr>
5
Reviewed-by: Peter Maydell <peter.maydell@linaro.org>
5
Reviewed-by: Philippe Mathieu-Daudé <philmd@linaro.org>
6
Message-id: 20240424200929.240921-5-ines.varhol@telecom-paris.fr
6
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
7
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
7
---
8
---
8
target/arm/cpu.h | 35 ++++++++++++++++++-----------------
9
hw/arm/b-l475e-iot01a.c | 59 +++++++++++++++++++++++++++++++++++++++--
9
target/arm/helper.c | 6 ++++--
10
hw/arm/Kconfig | 1 +
10
target/arm/translate-a64.c | 3 +++
11
2 files changed, 58 insertions(+), 2 deletions(-)
11
3 files changed, 25 insertions(+), 19 deletions(-)
12
12
13
diff --git a/target/arm/cpu.h b/target/arm/cpu.h
13
diff --git a/hw/arm/b-l475e-iot01a.c b/hw/arm/b-l475e-iot01a.c
14
index XXXXXXX..XXXXXXX 100644
14
index XXXXXXX..XXXXXXX 100644
15
--- a/target/arm/cpu.h
15
--- a/hw/arm/b-l475e-iot01a.c
16
+++ b/target/arm/cpu.h
16
+++ b/hw/arm/b-l475e-iot01a.c
17
@@ -XXX,XX +XXX,XX @@ static inline uint64_t cpreg_to_kvm_id(uint32_t cpregid)
17
@@ -XXX,XX +XXX,XX @@
18
#include "hw/boards.h"
19
#include "hw/qdev-properties.h"
20
#include "qemu/error-report.h"
21
-#include "hw/arm/stm32l4x5_soc.h"
22
#include "hw/arm/boot.h"
23
+#include "hw/core/split-irq.h"
24
+#include "hw/arm/stm32l4x5_soc.h"
25
+#include "hw/gpio/stm32l4x5_gpio.h"
26
+#include "hw/display/dm163.h"
27
28
-/* B-L475E-IOT01A implementation is derived from netduinoplus2 */
29
+/* B-L475E-IOT01A implementation is inspired from netduinoplus2 and arduino */
30
+
31
+/*
32
+ * There are actually 14 input pins in the DM163 device.
33
+ * Here the DM163 input pin EN isn't connected to the STM32L4x5
34
+ * GPIOs as the IM120417002 colors shield doesn't actually use
35
+ * this pin to drive the RGB matrix.
36
+ */
37
+#define NUM_DM163_INPUTS 13
38
+
39
+static const unsigned dm163_input[NUM_DM163_INPUTS] = {
40
+ 1 * GPIO_NUM_PINS + 2, /* ROW0 PB2 */
41
+ 0 * GPIO_NUM_PINS + 15, /* ROW1 PA15 */
42
+ 0 * GPIO_NUM_PINS + 2, /* ROW2 PA2 */
43
+ 0 * GPIO_NUM_PINS + 7, /* ROW3 PA7 */
44
+ 0 * GPIO_NUM_PINS + 6, /* ROW4 PA6 */
45
+ 0 * GPIO_NUM_PINS + 5, /* ROW5 PA5 */
46
+ 1 * GPIO_NUM_PINS + 0, /* ROW6 PB0 */
47
+ 0 * GPIO_NUM_PINS + 3, /* ROW7 PA3 */
48
+ 0 * GPIO_NUM_PINS + 4, /* SIN (SDA) PA4 */
49
+ 1 * GPIO_NUM_PINS + 1, /* DCK (SCK) PB1 */
50
+ 2 * GPIO_NUM_PINS + 3, /* RST_B (RST) PC3 */
51
+ 2 * GPIO_NUM_PINS + 4, /* LAT_B (LAT) PC4 */
52
+ 2 * GPIO_NUM_PINS + 5, /* SELBK (SB) PC5 */
53
+};
54
55
#define TYPE_B_L475E_IOT01A MACHINE_TYPE_NAME("b-l475e-iot01a")
56
OBJECT_DECLARE_SIMPLE_TYPE(Bl475eMachineState, B_L475E_IOT01A)
57
@@ -XXX,XX +XXX,XX @@ typedef struct Bl475eMachineState {
58
MachineState parent_obj;
59
60
Stm32l4x5SocState soc;
61
+ SplitIRQ gpio_splitters[NUM_DM163_INPUTS];
62
+ DM163State dm163;
63
} Bl475eMachineState;
64
65
static void bl475e_init(MachineState *machine)
66
{
67
Bl475eMachineState *s = B_L475E_IOT01A(machine);
68
const Stm32l4x5SocClass *sc;
69
+ DeviceState *dev, *gpio_out_splitter;
70
+ unsigned gpio, pin;
71
72
object_initialize_child(OBJECT(machine), "soc", &s->soc,
73
TYPE_STM32L4X5XG_SOC);
74
@@ -XXX,XX +XXX,XX @@ static void bl475e_init(MachineState *machine)
75
sc = STM32L4X5_SOC_GET_CLASS(&s->soc);
76
armv7m_load_kernel(ARM_CPU(first_cpu), machine->kernel_filename, 0,
77
sc->flash_size);
78
+
79
+ if (object_class_by_name(TYPE_DM163)) {
80
+ object_initialize_child(OBJECT(machine), "dm163",
81
+ &s->dm163, TYPE_DM163);
82
+ dev = DEVICE(&s->dm163);
83
+ qdev_realize(dev, NULL, &error_abort);
84
+
85
+ for (unsigned i = 0; i < NUM_DM163_INPUTS; i++) {
86
+ object_initialize_child(OBJECT(machine), "gpio-out-splitters[*]",
87
+ &s->gpio_splitters[i], TYPE_SPLIT_IRQ);
88
+ gpio_out_splitter = DEVICE(&s->gpio_splitters[i]);
89
+ qdev_prop_set_uint32(gpio_out_splitter, "num-lines", 2);
90
+ qdev_realize(gpio_out_splitter, NULL, &error_fatal);
91
+
92
+ qdev_connect_gpio_out(gpio_out_splitter, 0,
93
+ qdev_get_gpio_in(DEVICE(&s->soc), dm163_input[i]));
94
+ qdev_connect_gpio_out(gpio_out_splitter, 1,
95
+ qdev_get_gpio_in(dev, i));
96
+ gpio = dm163_input[i] / GPIO_NUM_PINS;
97
+ pin = dm163_input[i] % GPIO_NUM_PINS;
98
+ qdev_connect_gpio_out(DEVICE(&s->soc.gpio[gpio]), pin,
99
+ qdev_get_gpio_in(DEVICE(gpio_out_splitter), 0));
100
+ }
101
+ }
18
}
102
}
19
103
20
/* ARMCPRegInfo type field bits. If the SPECIAL bit is set this is a
104
static void bl475e_machine_init(ObjectClass *oc, void *data)
21
- * special-behaviour cp reg and bits [15..8] indicate what behaviour
105
diff --git a/hw/arm/Kconfig b/hw/arm/Kconfig
22
+ * special-behaviour cp reg and bits [11..8] indicate what behaviour
23
* it has. Otherwise it is a simple cp reg, where CONST indicates that
24
* TCG can assume the value to be constant (ie load at translate time)
25
* and 64BIT indicates a 64 bit wide coprocessor register. SUPPRESS_TB_END
26
@@ -XXX,XX +XXX,XX @@ static inline uint64_t cpreg_to_kvm_id(uint32_t cpregid)
27
* need to be surrounded by gen_io_start()/gen_io_end(). In particular,
28
* registers which implement clocks or timers require this.
29
*/
30
-#define ARM_CP_SPECIAL 1
31
-#define ARM_CP_CONST 2
32
-#define ARM_CP_64BIT 4
33
-#define ARM_CP_SUPPRESS_TB_END 8
34
-#define ARM_CP_OVERRIDE 16
35
-#define ARM_CP_ALIAS 32
36
-#define ARM_CP_IO 64
37
-#define ARM_CP_NO_RAW 128
38
-#define ARM_CP_NOP (ARM_CP_SPECIAL | (1 << 8))
39
-#define ARM_CP_WFI (ARM_CP_SPECIAL | (2 << 8))
40
-#define ARM_CP_NZCV (ARM_CP_SPECIAL | (3 << 8))
41
-#define ARM_CP_CURRENTEL (ARM_CP_SPECIAL | (4 << 8))
42
-#define ARM_CP_DC_ZVA (ARM_CP_SPECIAL | (5 << 8))
43
-#define ARM_LAST_SPECIAL ARM_CP_DC_ZVA
44
+#define ARM_CP_SPECIAL 0x0001
45
+#define ARM_CP_CONST 0x0002
46
+#define ARM_CP_64BIT 0x0004
47
+#define ARM_CP_SUPPRESS_TB_END 0x0008
48
+#define ARM_CP_OVERRIDE 0x0010
49
+#define ARM_CP_ALIAS 0x0020
50
+#define ARM_CP_IO 0x0040
51
+#define ARM_CP_NO_RAW 0x0080
52
+#define ARM_CP_NOP (ARM_CP_SPECIAL | 0x0100)
53
+#define ARM_CP_WFI (ARM_CP_SPECIAL | 0x0200)
54
+#define ARM_CP_NZCV (ARM_CP_SPECIAL | 0x0300)
55
+#define ARM_CP_CURRENTEL (ARM_CP_SPECIAL | 0x0400)
56
+#define ARM_CP_DC_ZVA (ARM_CP_SPECIAL | 0x0500)
57
+#define ARM_LAST_SPECIAL ARM_CP_DC_ZVA
58
+#define ARM_CP_FPU 0x1000
59
/* Used only as a terminator for ARMCPRegInfo lists */
60
-#define ARM_CP_SENTINEL 0xffff
61
+#define ARM_CP_SENTINEL 0xffff
62
/* Mask of only the flag bits in a type field */
63
-#define ARM_CP_FLAG_MASK 0xff
64
+#define ARM_CP_FLAG_MASK 0x10ff
65
66
/* Valid values for ARMCPRegInfo state field, indicating which of
67
* the AArch32 and AArch64 execution states this register is visible in.
68
diff --git a/target/arm/helper.c b/target/arm/helper.c
69
index XXXXXXX..XXXXXXX 100644
106
index XXXXXXX..XXXXXXX 100644
70
--- a/target/arm/helper.c
107
--- a/hw/arm/Kconfig
71
+++ b/target/arm/helper.c
108
+++ b/hw/arm/Kconfig
72
@@ -XXX,XX +XXX,XX @@ static const ARMCPRegInfo v8_cp_reginfo[] = {
109
@@ -XXX,XX +XXX,XX @@ config B_L475E_IOT01A
73
.writefn = aa64_daif_write, .resetfn = arm_cp_reset_ignore },
110
default y
74
{ .name = "FPCR", .state = ARM_CP_STATE_AA64,
111
depends on TCG && ARM
75
.opc0 = 3, .opc1 = 3, .opc2 = 0, .crn = 4, .crm = 4,
112
select STM32L4X5_SOC
76
- .access = PL0_RW, .readfn = aa64_fpcr_read, .writefn = aa64_fpcr_write },
113
+ imply DM163
77
+ .access = PL0_RW, .type = ARM_CP_FPU,
114
78
+ .readfn = aa64_fpcr_read, .writefn = aa64_fpcr_write },
115
config STM32L4X5_SOC
79
{ .name = "FPSR", .state = ARM_CP_STATE_AA64,
116
bool
80
.opc0 = 3, .opc1 = 3, .opc2 = 1, .crn = 4, .crm = 4,
81
- .access = PL0_RW, .readfn = aa64_fpsr_read, .writefn = aa64_fpsr_write },
82
+ .access = PL0_RW, .type = ARM_CP_FPU,
83
+ .readfn = aa64_fpsr_read, .writefn = aa64_fpsr_write },
84
{ .name = "DCZID_EL0", .state = ARM_CP_STATE_AA64,
85
.opc0 = 3, .opc1 = 3, .opc2 = 7, .crn = 0, .crm = 0,
86
.access = PL0_R, .type = ARM_CP_NO_RAW,
87
diff --git a/target/arm/translate-a64.c b/target/arm/translate-a64.c
88
index XXXXXXX..XXXXXXX 100644
89
--- a/target/arm/translate-a64.c
90
+++ b/target/arm/translate-a64.c
91
@@ -XXX,XX +XXX,XX @@ static void handle_sys(DisasContext *s, uint32_t insn, bool isread,
92
default:
93
break;
94
}
95
+ if ((ri->type & ARM_CP_FPU) && !fp_access_check(s)) {
96
+ return;
97
+ }
98
99
if ((tb_cflags(s->base.tb) & CF_USE_ICOUNT) && (ri->type & ARM_CP_IO)) {
100
gen_io_start();
101
--
117
--
102
2.16.1
118
2.34.1
103
119
104
120
diff view generated by jsdifflib
1
From: Philippe Mathieu-Daudé <f4bug@amsat.org>
1
From: Inès Varhol <ines.varhol@telecom-paris.fr>
2
2
3
(qemu) info mtree
3
`test_dm163_bank()`
4
address-space: cpu-memory-0
4
Checks that the pin "sout" of the DM163 led driver outputs the values
5
0000000000000000-ffffffffffffffff (prio 0, i/o): system
5
received on pin "sin" with the expected latency (depending on the bank).
6
0000000000000000-0000000007ffffff (prio 0, rom): aspeed.boot_rom
6
7
000000001e600000-000000001e7fffff (prio -1, i/o): aspeed_soc.io
7
`test_dm163_gpio_connection()`
8
- 000000001e784000-000000001e78401f (prio 0, i/o): serial
8
Check that changes to relevant STM32L4x5 GPIO pins are propagated to the
9
000000001e620000-000000001e6200ff (prio 0, i/o): aspeed.smc.ast2500-fmc
9
DM163 device.
10
000000001e630000-000000001e6300ff (prio 0, i/o): aspeed.smc.ast2500-spi1
10
11
[...]
11
Signed-off-by: Arnaud Minier <arnaud.minier@telecom-paris.fr>
12
000000001e720000-000000001e728fff (prio 0, ram): aspeed.sram
12
Signed-off-by: Inès Varhol <ines.varhol@telecom-paris.fr>
13
000000001e782000-000000001e782fff (prio 0, i/o): aspeed.timer
13
Acked-by: Thomas Huth <thuth@redhat.com>
14
+ 000000001e784000-000000001e78401f (prio 0, i/o): serial
14
Reviewed-by: Philippe Mathieu-Daudé <philmd@linaro.org>
15
000000001e785000-000000001e78501f (prio 0, i/o): aspeed.wdt
15
Message-id: 20240424200929.240921-6-ines.varhol@telecom-paris.fr
16
000000001e785020-000000001e78503f (prio 0, i/o): aspeed.wdt
17
18
Signed-off-by: Philippe Mathieu-Daudé <f4bug@amsat.org>
19
Reviewed-by: Cédric Le Goater <clg@kaod.org>
20
Reviewed-by: Andrew Jeffery <andrew@aj.id.au>
21
Message-id: 20180209085755.30414-2-f4bug@amsat.org
22
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
16
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
23
---
17
---
24
hw/arm/aspeed_soc.c | 3 ++-
18
tests/qtest/dm163-test.c | 194 +++++++++++++++++++++++++++++++++++++++
25
1 file changed, 2 insertions(+), 1 deletion(-)
19
tests/qtest/meson.build | 2 +
26
20
2 files changed, 196 insertions(+)
27
diff --git a/hw/arm/aspeed_soc.c b/hw/arm/aspeed_soc.c
21
create mode 100644 tests/qtest/dm163-test.c
22
23
diff --git a/tests/qtest/dm163-test.c b/tests/qtest/dm163-test.c
24
new file mode 100644
25
index XXXXXXX..XXXXXXX
26
--- /dev/null
27
+++ b/tests/qtest/dm163-test.c
28
@@ -XXX,XX +XXX,XX @@
29
+/*
30
+ * QTest testcase for DM163
31
+ *
32
+ * Copyright (C) 2024 Samuel Tardieu <sam@rfc1149.net>
33
+ * Copyright (C) 2024 Arnaud Minier <arnaud.minier@telecom-paris.fr>
34
+ * Copyright (C) 2024 Inès Varhol <ines.varhol@telecom-paris.fr>
35
+ *
36
+ * SPDX-License-Identifier: GPL-2.0-or-later
37
+ */
38
+
39
+#include "qemu/osdep.h"
40
+#include "libqtest.h"
41
+
42
+enum DM163_INPUTS {
43
+ SIN = 8,
44
+ DCK = 9,
45
+ RST_B = 10,
46
+ LAT_B = 11,
47
+ SELBK = 12,
48
+ EN_B = 13
49
+};
50
+
51
+#define DEVICE_NAME "/machine/dm163"
52
+#define GPIO_OUT(name, value) qtest_set_irq_in(qts, DEVICE_NAME, NULL, name, \
53
+ value)
54
+#define GPIO_PULSE(name) \
55
+ do { \
56
+ GPIO_OUT(name, 1); \
57
+ GPIO_OUT(name, 0); \
58
+ } while (0)
59
+
60
+
61
+static void rise_gpio_pin_dck(QTestState *qts)
62
+{
63
+ /* Configure output mode for pin PB1 */
64
+ qtest_writel(qts, 0x48000400, 0xFFFFFEB7);
65
+ /* Write 1 in ODR for PB1 */
66
+ qtest_writel(qts, 0x48000414, 0x00000002);
67
+}
68
+
69
+static void lower_gpio_pin_dck(QTestState *qts)
70
+{
71
+ /* Configure output mode for pin PB1 */
72
+ qtest_writel(qts, 0x48000400, 0xFFFFFEB7);
73
+ /* Write 0 in ODR for PB1 */
74
+ qtest_writel(qts, 0x48000414, 0x00000000);
75
+}
76
+
77
+static void rise_gpio_pin_selbk(QTestState *qts)
78
+{
79
+ /* Configure output mode for pin PC5 */
80
+ qtest_writel(qts, 0x48000800, 0xFFFFF7FF);
81
+ /* Write 1 in ODR for PC5 */
82
+ qtest_writel(qts, 0x48000814, 0x00000020);
83
+}
84
+
85
+static void lower_gpio_pin_selbk(QTestState *qts)
86
+{
87
+ /* Configure output mode for pin PC5 */
88
+ qtest_writel(qts, 0x48000800, 0xFFFFF7FF);
89
+ /* Write 0 in ODR for PC5 */
90
+ qtest_writel(qts, 0x48000814, 0x00000000);
91
+}
92
+
93
+static void rise_gpio_pin_lat_b(QTestState *qts)
94
+{
95
+ /* Configure output mode for pin PC4 */
96
+ qtest_writel(qts, 0x48000800, 0xFFFFFDFF);
97
+ /* Write 1 in ODR for PC4 */
98
+ qtest_writel(qts, 0x48000814, 0x00000010);
99
+}
100
+
101
+static void lower_gpio_pin_lat_b(QTestState *qts)
102
+{
103
+ /* Configure output mode for pin PC4 */
104
+ qtest_writel(qts, 0x48000800, 0xFFFFFDFF);
105
+ /* Write 0 in ODR for PC4 */
106
+ qtest_writel(qts, 0x48000814, 0x00000000);
107
+}
108
+
109
+static void rise_gpio_pin_rst_b(QTestState *qts)
110
+{
111
+ /* Configure output mode for pin PC3 */
112
+ qtest_writel(qts, 0x48000800, 0xFFFFFF7F);
113
+ /* Write 1 in ODR for PC3 */
114
+ qtest_writel(qts, 0x48000814, 0x00000008);
115
+}
116
+
117
+static void lower_gpio_pin_rst_b(QTestState *qts)
118
+{
119
+ /* Configure output mode for pin PC3 */
120
+ qtest_writel(qts, 0x48000800, 0xFFFFFF7F);
121
+ /* Write 0 in ODR for PC3 */
122
+ qtest_writel(qts, 0x48000814, 0x00000000);
123
+}
124
+
125
+static void rise_gpio_pin_sin(QTestState *qts)
126
+{
127
+ /* Configure output mode for pin PA4 */
128
+ qtest_writel(qts, 0x48000000, 0xFFFFFDFF);
129
+ /* Write 1 in ODR for PA4 */
130
+ qtest_writel(qts, 0x48000014, 0x00000010);
131
+}
132
+
133
+static void lower_gpio_pin_sin(QTestState *qts)
134
+{
135
+ /* Configure output mode for pin PA4 */
136
+ qtest_writel(qts, 0x48000000, 0xFFFFFDFF);
137
+ /* Write 0 in ODR for PA4 */
138
+ qtest_writel(qts, 0x48000014, 0x00000000);
139
+}
140
+
141
+static void test_dm163_bank(const void *opaque)
142
+{
143
+ const unsigned bank = (uintptr_t) opaque;
144
+ const int width = bank ? 192 : 144;
145
+
146
+ QTestState *qts = qtest_initf("-M b-l475e-iot01a");
147
+ qtest_irq_intercept_out_named(qts, DEVICE_NAME, "sout");
148
+ GPIO_OUT(RST_B, 1);
149
+ GPIO_OUT(EN_B, 0);
150
+ GPIO_OUT(DCK, 0);
151
+ GPIO_OUT(SELBK, bank);
152
+ GPIO_OUT(LAT_B, 1);
153
+
154
+ /* Fill bank with zeroes */
155
+ GPIO_OUT(SIN, 0);
156
+ for (int i = 0; i < width; i++) {
157
+ GPIO_PULSE(DCK);
158
+ }
159
+ /* Fill bank with ones, check that we get the previous zeroes */
160
+ GPIO_OUT(SIN, 1);
161
+ for (int i = 0; i < width; i++) {
162
+ GPIO_PULSE(DCK);
163
+ g_assert(!qtest_get_irq(qts, 0));
164
+ }
165
+
166
+ /* Pulse one more bit in the bank, check that we get a one */
167
+ GPIO_PULSE(DCK);
168
+ g_assert(qtest_get_irq(qts, 0));
169
+
170
+ qtest_quit(qts);
171
+}
172
+
173
+static void test_dm163_gpio_connection(void)
174
+{
175
+ QTestState *qts = qtest_init("-M b-l475e-iot01a");
176
+ qtest_irq_intercept_in(qts, DEVICE_NAME);
177
+
178
+ g_assert_false(qtest_get_irq(qts, SIN));
179
+ g_assert_false(qtest_get_irq(qts, DCK));
180
+ g_assert_false(qtest_get_irq(qts, RST_B));
181
+ g_assert_false(qtest_get_irq(qts, LAT_B));
182
+ g_assert_false(qtest_get_irq(qts, SELBK));
183
+
184
+ rise_gpio_pin_dck(qts);
185
+ g_assert_true(qtest_get_irq(qts, DCK));
186
+ lower_gpio_pin_dck(qts);
187
+ g_assert_false(qtest_get_irq(qts, DCK));
188
+
189
+ rise_gpio_pin_lat_b(qts);
190
+ g_assert_true(qtest_get_irq(qts, LAT_B));
191
+ lower_gpio_pin_lat_b(qts);
192
+ g_assert_false(qtest_get_irq(qts, LAT_B));
193
+
194
+ rise_gpio_pin_selbk(qts);
195
+ g_assert_true(qtest_get_irq(qts, SELBK));
196
+ lower_gpio_pin_selbk(qts);
197
+ g_assert_false(qtest_get_irq(qts, SELBK));
198
+
199
+ rise_gpio_pin_rst_b(qts);
200
+ g_assert_true(qtest_get_irq(qts, RST_B));
201
+ lower_gpio_pin_rst_b(qts);
202
+ g_assert_false(qtest_get_irq(qts, RST_B));
203
+
204
+ rise_gpio_pin_sin(qts);
205
+ g_assert_true(qtest_get_irq(qts, SIN));
206
+ lower_gpio_pin_sin(qts);
207
+ g_assert_false(qtest_get_irq(qts, SIN));
208
+
209
+ g_assert_false(qtest_get_irq(qts, DCK));
210
+ g_assert_false(qtest_get_irq(qts, LAT_B));
211
+ g_assert_false(qtest_get_irq(qts, SELBK));
212
+ g_assert_false(qtest_get_irq(qts, RST_B));
213
+}
214
+
215
+int main(int argc, char **argv)
216
+{
217
+ g_test_init(&argc, &argv, NULL);
218
+ qtest_add_data_func("/dm163/bank0", (void *)0, test_dm163_bank);
219
+ qtest_add_data_func("/dm163/bank1", (void *)1, test_dm163_bank);
220
+ qtest_add_func("/dm163/gpio_connection", test_dm163_gpio_connection);
221
+ return g_test_run();
222
+}
223
diff --git a/tests/qtest/meson.build b/tests/qtest/meson.build
28
index XXXXXXX..XXXXXXX 100644
224
index XXXXXXX..XXXXXXX 100644
29
--- a/hw/arm/aspeed_soc.c
225
--- a/tests/qtest/meson.build
30
+++ b/hw/arm/aspeed_soc.c
226
+++ b/tests/qtest/meson.build
31
@@ -XXX,XX +XXX,XX @@ static void aspeed_soc_realize(DeviceState *dev, Error **errp)
227
@@ -XXX,XX +XXX,XX @@ qtests_arm = \
32
/* UART - attach an 8250 to the IO space as our UART5 */
228
(config_all_devices.has_key('CONFIG_MICROBIT') ? ['microbit-test'] : []) + \
33
if (serial_hds[0]) {
229
(config_all_devices.has_key('CONFIG_STM32L4X5_SOC') ? qtests_stm32l4x5 : []) + \
34
qemu_irq uart5 = qdev_get_gpio_in(DEVICE(&s->vic), uart_irqs[4]);
230
(config_all_devices.has_key('CONFIG_FSI_APB2OPB_ASPEED') ? ['aspeed_fsi-test'] : []) + \
35
- serial_mm_init(&s->iomem, ASPEED_SOC_UART_5_BASE, 2,
231
+ (config_all_devices.has_key('CONFIG_STM32L4X5_SOC') and
36
+ serial_mm_init(get_system_memory(),
232
+ config_all_devices.has_key('CONFIG_DM163')? ['dm163-test'] : []) + \
37
+ ASPEED_SOC_IOMEM_BASE + ASPEED_SOC_UART_5_BASE, 2,
233
['arm-cpu-features',
38
uart5, 38400, serial_hds[0], DEVICE_LITTLE_ENDIAN);
234
'boot-serial-test']
39
}
40
235
41
--
236
--
42
2.16.1
237
2.34.1
43
238
44
239
diff view generated by jsdifflib