1
target-arm queue. This has the "plumb txattrs through various
1
Arm changes for before softfreeze: mostly my PL061/GPIO patches,
2
bits of exec.c" patches, and a collection of bug fixes from
2
but also a new M-profile board and various other things.
3
various people.
4
3
5
thanks
4
thanks
6
-- PMM
5
-- PMM
7
6
7
The following changes since commit 05de778b5b8ab0b402996769117b88c7ea5c7c61:
8
8
9
9
Merge remote-tracking branch 'remotes/mst/tags/for_upstream' into staging (2021-07-09 14:30:01 +0100)
10
The following changes since commit a3ac12fba028df90f7b3dbec924995c126c41022:
11
12
Merge remote-tracking branch 'remotes/ehabkost/tags/numa-next-pull-request' into staging (2018-05-31 11:12:36 +0100)
13
10
14
are available in the Git repository at:
11
are available in the Git repository at:
15
12
16
git://git.linaro.org/people/pmaydell/qemu-arm.git tags/pull-target-arm-20180531
13
https://git.linaro.org/people/pmaydell/qemu-arm.git tags/pull-target-arm-20210709
17
14
18
for you to fetch changes up to 49d1dca0520ea71bc21867fab6647f474fcf857b:
15
for you to fetch changes up to 05449abb1d4c5f0c69ceb3d8d03cbc75de39b646:
19
16
20
KVM: GIC: Fix memory leak due to calling kvm_init_irq_routing twice (2018-05-31 14:52:53 +0100)
17
hw/intc: Improve formatting of MEMTX_ERROR guest error message (2021-07-09 16:09:12 +0100)
21
18
22
----------------------------------------------------------------
19
----------------------------------------------------------------
23
target-arm queue:
20
target-arm queue:
24
* target/arm: Honour FPCR.FZ in FRECPX
21
* New machine type: stm32vldiscovery
25
* MAINTAINERS: Add entries for newer MPS2 boards and devices
22
* hw/intc/arm_gicv3_cpuif: Fix virtual irq number check in icv_[dir|eoir]_write
26
* hw/intc/arm_gicv3: Fix APxR<n> register dispatching
23
* hw/gpio/pl061: Honour Luminary PL061 PUR and PDR registers
27
* arm_gicv3_kvm: fix bug in writing zero bits back to the in-kernel
24
* virt: Fix implementation of GPIO-based powerdown/shutdown mechanism
28
GIC state
25
* Correct the encoding of MDCCSR_EL0 and DBGDSCRint
29
* tcg: Fix helper function vs host abi for float16
26
* hw/intc: Improve formatting of MEMTX_ERROR guest error message
30
* arm: fix qemu crash on startup with -bios option
31
* arm: fix malloc type mismatch
32
* xlnx-zdma: Correct mem leaks and memset to zero on desc unaligned errors
33
* Correct CPACR reset value for v7 cores
34
* memory.h: Improve IOMMU related documentation
35
* exec: Plumb transaction attributes through various functions in
36
preparation for allowing IOMMUs to see them
37
* vmstate.h: Provide VMSTATE_BOOL_SUB_ARRAY
38
* ARM: ACPI: Fix use-after-free due to memory realloc
39
* KVM: GIC: Fix memory leak due to calling kvm_init_irq_routing twice
40
27
41
----------------------------------------------------------------
28
----------------------------------------------------------------
42
Francisco Iglesias (1):
29
Alexandre Iooss (4):
43
xlnx-zdma: Correct mem leaks and memset to zero on desc unaligned errors
30
stm32f100: Add the stm32f100 SoC
31
stm32vldiscovery: Add the STM32VLDISCOVERY Machine
32
docs/system: arm: Add stm32 boards description
33
tests/boot-serial-test: Add STM32VLDISCOVERY board testcase
44
34
45
Igor Mammedov (1):
35
Peter Maydell (10):
46
arm: fix qemu crash on startup with -bios option
36
hw/gpio/pl061: Convert DPRINTF to tracepoints
37
hw/gpio/pl061: Clean up read/write offset handling logic
38
hw/gpio/pl061: Add tracepoints for register read and write
39
hw/gpio/pl061: Document the interface of this device
40
hw/gpio/pl061: Honour Luminary PL061 PUR and PDR registers
41
hw/gpio/pl061: Make pullup/pulldown of outputs configurable
42
hw/arm/virt: Make PL061 GPIO lines pulled low, not high
43
hw/gpio/pl061: Convert to 3-phase reset and assert GPIO lines correctly on reset
44
hw/gpio/pl061: Document a shortcoming in our implementation
45
hw/arm/stellaris: Expand comment about handling of OLED chipselect
47
46
48
Jan Kiszka (1):
47
Rebecca Cran (1):
49
hw/intc/arm_gicv3: Fix APxR<n> register dispatching
48
hw/intc: Improve formatting of MEMTX_ERROR guest error message
50
49
51
Paolo Bonzini (1):
50
Ricardo Koller (1):
52
arm: fix malloc type mismatch
51
hw/intc/arm_gicv3_cpuif: Fix virtual irq number check in icv_[dir|eoir]_write
53
52
54
Peter Maydell (17):
53
hnick@vmware.com (1):
55
target/arm: Honour FPCR.FZ in FRECPX
54
target/arm: Correct the encoding of MDCCSR_EL0 and DBGDSCRint
56
MAINTAINERS: Add entries for newer MPS2 boards and devices
57
Correct CPACR reset value for v7 cores
58
memory.h: Improve IOMMU related documentation
59
Make tb_invalidate_phys_addr() take a MemTxAttrs argument
60
Make address_space_translate{, _cached}() take a MemTxAttrs argument
61
Make address_space_map() take a MemTxAttrs argument
62
Make address_space_access_valid() take a MemTxAttrs argument
63
Make flatview_extend_translation() take a MemTxAttrs argument
64
Make memory_region_access_valid() take a MemTxAttrs argument
65
Make MemoryRegion valid.accepts callback take a MemTxAttrs argument
66
Make flatview_access_valid() take a MemTxAttrs argument
67
Make flatview_translate() take a MemTxAttrs argument
68
Make address_space_get_iotlb_entry() take a MemTxAttrs argument
69
Make flatview_do_translate() take a MemTxAttrs argument
70
Make address_space_translate_iommu take a MemTxAttrs argument
71
vmstate.h: Provide VMSTATE_BOOL_SUB_ARRAY
72
55
73
Richard Henderson (1):
56
docs/system/arm/stm32.rst | 66 +++++++
74
tcg: Fix helper function vs host abi for float16
57
docs/system/target-arm.rst | 1 +
58
default-configs/devices/arm-softmmu.mak | 1 +
59
include/hw/arm/stm32f100_soc.h | 57 ++++++
60
hw/arm/stellaris.c | 56 +++++-
61
hw/arm/stm32f100_soc.c | 182 +++++++++++++++++
62
hw/arm/stm32vldiscovery.c | 66 +++++++
63
hw/arm/virt.c | 3 +
64
hw/gpio/pl061.c | 341 +++++++++++++++++++++++++-------
65
hw/intc/arm_gicv3_cpuif.c | 4 +-
66
hw/intc/arm_gicv3_redist.c | 4 +-
67
target/arm/helper.c | 16 +-
68
tests/qtest/boot-serial-test.c | 37 ++++
69
MAINTAINERS | 13 ++
70
hw/arm/Kconfig | 10 +
71
hw/arm/meson.build | 2 +
72
hw/gpio/trace-events | 9 +
73
17 files changed, 790 insertions(+), 78 deletions(-)
74
create mode 100644 docs/system/arm/stm32.rst
75
create mode 100644 include/hw/arm/stm32f100_soc.h
76
create mode 100644 hw/arm/stm32f100_soc.c
77
create mode 100644 hw/arm/stm32vldiscovery.c
75
78
76
Shannon Zhao (3):
77
arm_gicv3_kvm: increase clroffset accordingly
78
ARM: ACPI: Fix use-after-free due to memory realloc
79
KVM: GIC: Fix memory leak due to calling kvm_init_irq_routing twice
80
81
include/exec/exec-all.h | 5 +-
82
include/exec/helper-head.h | 2 +-
83
include/exec/memory-internal.h | 3 +-
84
include/exec/memory.h | 128 +++++++++++++++++++++++++++++++++++------
85
include/migration/vmstate.h | 3 +
86
include/sysemu/dma.h | 6 +-
87
accel/tcg/translate-all.c | 4 +-
88
exec.c | 95 ++++++++++++++++++------------
89
hw/arm/boot.c | 18 +++---
90
hw/arm/virt-acpi-build.c | 20 +++++--
91
hw/dma/xlnx-zdma.c | 10 +++-
92
hw/hppa/dino.c | 3 +-
93
hw/intc/arm_gic_kvm.c | 1 -
94
hw/intc/arm_gicv3_cpuif.c | 12 ++--
95
hw/intc/arm_gicv3_kvm.c | 2 +-
96
hw/nvram/fw_cfg.c | 12 ++--
97
hw/s390x/s390-pci-inst.c | 3 +-
98
hw/scsi/esp.c | 3 +-
99
hw/vfio/common.c | 3 +-
100
hw/virtio/vhost.c | 3 +-
101
hw/xen/xen_pt_msi.c | 3 +-
102
memory.c | 12 ++--
103
memory_ldst.inc.c | 18 +++---
104
target/arm/gdbstub.c | 3 +-
105
target/arm/helper-a64.c | 41 +++++++------
106
target/arm/helper.c | 90 ++++++++++++++++-------------
107
target/ppc/mmu-hash64.c | 3 +-
108
target/riscv/helper.c | 2 +-
109
target/s390x/diag.c | 6 +-
110
target/s390x/excp_helper.c | 3 +-
111
target/s390x/mmu_helper.c | 3 +-
112
target/s390x/sigp.c | 3 +-
113
target/xtensa/op_helper.c | 3 +-
114
MAINTAINERS | 9 ++-
115
34 files changed, 353 insertions(+), 182 deletions(-)
116
diff view generated by jsdifflib
1
From: Shannon Zhao <zhaoshenglong@huawei.com>
1
From: Alexandre Iooss <erdnaxe@crans.org>
2
2
3
kvm_irqchip_create called by kvm_init will call kvm_init_irq_routing to
3
This SoC is similar to stm32f205 SoC.
4
initialize global capability variables. If we call kvm_init_irq_routing in
4
This will be used by the STM32VLDISCOVERY to create a machine.
5
GIC realize function, previous allocated memory will leak.
5
6
6
Signed-off-by: Alexandre Iooss <erdnaxe@crans.org>
7
Fix this by deleting the unnecessary call.
7
Reviewed-by: Alistair Francis <alistair.francis@wdc.com>
8
8
Message-id: 20210617165647.2575955-2-erdnaxe@crans.org
9
Signed-off-by: Shannon Zhao <zhaoshenglong@huawei.com>
10
Reviewed-by: Eric Auger <eric.auger@redhat.com>
11
Message-id: 1527750994-14360-1-git-send-email-zhaoshenglong@huawei.com
12
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
9
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
13
---
10
---
14
hw/intc/arm_gic_kvm.c | 1 -
11
include/hw/arm/stm32f100_soc.h | 57 +++++++++++
15
hw/intc/arm_gicv3_kvm.c | 1 -
12
hw/arm/stm32f100_soc.c | 182 +++++++++++++++++++++++++++++++++
16
2 files changed, 2 deletions(-)
13
MAINTAINERS | 6 ++
17
14
hw/arm/Kconfig | 6 ++
18
diff --git a/hw/intc/arm_gic_kvm.c b/hw/intc/arm_gic_kvm.c
15
hw/arm/meson.build | 1 +
16
5 files changed, 252 insertions(+)
17
create mode 100644 include/hw/arm/stm32f100_soc.h
18
create mode 100644 hw/arm/stm32f100_soc.c
19
20
diff --git a/include/hw/arm/stm32f100_soc.h b/include/hw/arm/stm32f100_soc.h
21
new file mode 100644
22
index XXXXXXX..XXXXXXX
23
--- /dev/null
24
+++ b/include/hw/arm/stm32f100_soc.h
25
@@ -XXX,XX +XXX,XX @@
26
+/*
27
+ * STM32F100 SoC
28
+ *
29
+ * Copyright (c) 2021 Alexandre Iooss <erdnaxe@crans.org>
30
+ *
31
+ * Permission is hereby granted, free of charge, to any person obtaining a copy
32
+ * of this software and associated documentation files (the "Software"), to deal
33
+ * in the Software without restriction, including without limitation the rights
34
+ * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
35
+ * copies of the Software, and to permit persons to whom the Software is
36
+ * furnished to do so, subject to the following conditions:
37
+ *
38
+ * The above copyright notice and this permission notice shall be included in
39
+ * all copies or substantial portions of the Software.
40
+ *
41
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
42
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
43
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
44
+ * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
45
+ * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
46
+ * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
47
+ * THE SOFTWARE.
48
+ */
49
+
50
+#ifndef HW_ARM_STM32F100_SOC_H
51
+#define HW_ARM_STM32F100_SOC_H
52
+
53
+#include "hw/char/stm32f2xx_usart.h"
54
+#include "hw/ssi/stm32f2xx_spi.h"
55
+#include "hw/arm/armv7m.h"
56
+#include "qom/object.h"
57
+
58
+#define TYPE_STM32F100_SOC "stm32f100-soc"
59
+OBJECT_DECLARE_SIMPLE_TYPE(STM32F100State, STM32F100_SOC)
60
+
61
+#define STM_NUM_USARTS 3
62
+#define STM_NUM_SPIS 2
63
+
64
+#define FLASH_BASE_ADDRESS 0x08000000
65
+#define FLASH_SIZE (128 * 1024)
66
+#define SRAM_BASE_ADDRESS 0x20000000
67
+#define SRAM_SIZE (8 * 1024)
68
+
69
+struct STM32F100State {
70
+ /*< private >*/
71
+ SysBusDevice parent_obj;
72
+
73
+ /*< public >*/
74
+ char *cpu_type;
75
+
76
+ ARMv7MState armv7m;
77
+
78
+ STM32F2XXUsartState usart[STM_NUM_USARTS];
79
+ STM32F2XXSPIState spi[STM_NUM_SPIS];
80
+};
81
+
82
+#endif
83
diff --git a/hw/arm/stm32f100_soc.c b/hw/arm/stm32f100_soc.c
84
new file mode 100644
85
index XXXXXXX..XXXXXXX
86
--- /dev/null
87
+++ b/hw/arm/stm32f100_soc.c
88
@@ -XXX,XX +XXX,XX @@
89
+/*
90
+ * STM32F100 SoC
91
+ *
92
+ * Copyright (c) 2021 Alexandre Iooss <erdnaxe@crans.org>
93
+ * Copyright (c) 2014 Alistair Francis <alistair@alistair23.me>
94
+ *
95
+ * Permission is hereby granted, free of charge, to any person obtaining a copy
96
+ * of this software and associated documentation files (the "Software"), to deal
97
+ * in the Software without restriction, including without limitation the rights
98
+ * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
99
+ * copies of the Software, and to permit persons to whom the Software is
100
+ * furnished to do so, subject to the following conditions:
101
+ *
102
+ * The above copyright notice and this permission notice shall be included in
103
+ * all copies or substantial portions of the Software.
104
+ *
105
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
106
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
107
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
108
+ * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
109
+ * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
110
+ * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
111
+ * THE SOFTWARE.
112
+ */
113
+
114
+#include "qemu/osdep.h"
115
+#include "qapi/error.h"
116
+#include "qemu/module.h"
117
+#include "hw/arm/boot.h"
118
+#include "exec/address-spaces.h"
119
+#include "hw/arm/stm32f100_soc.h"
120
+#include "hw/qdev-properties.h"
121
+#include "hw/misc/unimp.h"
122
+#include "sysemu/sysemu.h"
123
+
124
+/* stm32f100_soc implementation is derived from stm32f205_soc */
125
+
126
+static const uint32_t usart_addr[STM_NUM_USARTS] = { 0x40013800, 0x40004400,
127
+ 0x40004800 };
128
+static const uint32_t spi_addr[STM_NUM_SPIS] = { 0x40013000, 0x40003800 };
129
+
130
+static const int usart_irq[STM_NUM_USARTS] = {37, 38, 39};
131
+static const int spi_irq[STM_NUM_SPIS] = {35, 36};
132
+
133
+static void stm32f100_soc_initfn(Object *obj)
134
+{
135
+ STM32F100State *s = STM32F100_SOC(obj);
136
+ int i;
137
+
138
+ object_initialize_child(obj, "armv7m", &s->armv7m, TYPE_ARMV7M);
139
+
140
+ for (i = 0; i < STM_NUM_USARTS; i++) {
141
+ object_initialize_child(obj, "usart[*]", &s->usart[i],
142
+ TYPE_STM32F2XX_USART);
143
+ }
144
+
145
+ for (i = 0; i < STM_NUM_SPIS; i++) {
146
+ object_initialize_child(obj, "spi[*]", &s->spi[i], TYPE_STM32F2XX_SPI);
147
+ }
148
+}
149
+
150
+static void stm32f100_soc_realize(DeviceState *dev_soc, Error **errp)
151
+{
152
+ STM32F100State *s = STM32F100_SOC(dev_soc);
153
+ DeviceState *dev, *armv7m;
154
+ SysBusDevice *busdev;
155
+ int i;
156
+
157
+ MemoryRegion *system_memory = get_system_memory();
158
+ MemoryRegion *sram = g_new(MemoryRegion, 1);
159
+ MemoryRegion *flash = g_new(MemoryRegion, 1);
160
+ MemoryRegion *flash_alias = g_new(MemoryRegion, 1);
161
+
162
+ /*
163
+ * Init flash region
164
+ * Flash starts at 0x08000000 and then is aliased to boot memory at 0x0
165
+ */
166
+ memory_region_init_rom(flash, OBJECT(dev_soc), "STM32F100.flash",
167
+ FLASH_SIZE, &error_fatal);
168
+ memory_region_init_alias(flash_alias, OBJECT(dev_soc),
169
+ "STM32F100.flash.alias", flash, 0, FLASH_SIZE);
170
+ memory_region_add_subregion(system_memory, FLASH_BASE_ADDRESS, flash);
171
+ memory_region_add_subregion(system_memory, 0, flash_alias);
172
+
173
+ /* Init SRAM region */
174
+ memory_region_init_ram(sram, NULL, "STM32F100.sram", SRAM_SIZE,
175
+ &error_fatal);
176
+ memory_region_add_subregion(system_memory, SRAM_BASE_ADDRESS, sram);
177
+
178
+ /* Init ARMv7m */
179
+ armv7m = DEVICE(&s->armv7m);
180
+ qdev_prop_set_uint32(armv7m, "num-irq", 61);
181
+ qdev_prop_set_string(armv7m, "cpu-type", s->cpu_type);
182
+ qdev_prop_set_bit(armv7m, "enable-bitband", true);
183
+ object_property_set_link(OBJECT(&s->armv7m), "memory",
184
+ OBJECT(get_system_memory()), &error_abort);
185
+ if (!sysbus_realize(SYS_BUS_DEVICE(&s->armv7m), errp)) {
186
+ return;
187
+ }
188
+
189
+ /* Attach UART (uses USART registers) and USART controllers */
190
+ for (i = 0; i < STM_NUM_USARTS; i++) {
191
+ dev = DEVICE(&(s->usart[i]));
192
+ qdev_prop_set_chr(dev, "chardev", serial_hd(i));
193
+ if (!sysbus_realize(SYS_BUS_DEVICE(&s->usart[i]), errp)) {
194
+ return;
195
+ }
196
+ busdev = SYS_BUS_DEVICE(dev);
197
+ sysbus_mmio_map(busdev, 0, usart_addr[i]);
198
+ sysbus_connect_irq(busdev, 0, qdev_get_gpio_in(armv7m, usart_irq[i]));
199
+ }
200
+
201
+ /* SPI 1 and 2 */
202
+ for (i = 0; i < STM_NUM_SPIS; i++) {
203
+ dev = DEVICE(&(s->spi[i]));
204
+ if (!sysbus_realize(SYS_BUS_DEVICE(&s->spi[i]), errp)) {
205
+ return;
206
+ }
207
+ busdev = SYS_BUS_DEVICE(dev);
208
+ sysbus_mmio_map(busdev, 0, spi_addr[i]);
209
+ sysbus_connect_irq(busdev, 0, qdev_get_gpio_in(armv7m, spi_irq[i]));
210
+ }
211
+
212
+ create_unimplemented_device("timer[2]", 0x40000000, 0x400);
213
+ create_unimplemented_device("timer[3]", 0x40000400, 0x400);
214
+ create_unimplemented_device("timer[4]", 0x40000800, 0x400);
215
+ create_unimplemented_device("timer[6]", 0x40001000, 0x400);
216
+ create_unimplemented_device("timer[7]", 0x40001400, 0x400);
217
+ create_unimplemented_device("RTC", 0x40002800, 0x400);
218
+ create_unimplemented_device("WWDG", 0x40002C00, 0x400);
219
+ create_unimplemented_device("IWDG", 0x40003000, 0x400);
220
+ create_unimplemented_device("I2C1", 0x40005400, 0x400);
221
+ create_unimplemented_device("I2C2", 0x40005800, 0x400);
222
+ create_unimplemented_device("BKP", 0x40006C00, 0x400);
223
+ create_unimplemented_device("PWR", 0x40007000, 0x400);
224
+ create_unimplemented_device("DAC", 0x40007400, 0x400);
225
+ create_unimplemented_device("CEC", 0x40007800, 0x400);
226
+ create_unimplemented_device("AFIO", 0x40010000, 0x400);
227
+ create_unimplemented_device("EXTI", 0x40010400, 0x400);
228
+ create_unimplemented_device("GPIOA", 0x40010800, 0x400);
229
+ create_unimplemented_device("GPIOB", 0x40010C00, 0x400);
230
+ create_unimplemented_device("GPIOC", 0x40011000, 0x400);
231
+ create_unimplemented_device("GPIOD", 0x40011400, 0x400);
232
+ create_unimplemented_device("GPIOE", 0x40011800, 0x400);
233
+ create_unimplemented_device("ADC1", 0x40012400, 0x400);
234
+ create_unimplemented_device("timer[1]", 0x40012C00, 0x400);
235
+ create_unimplemented_device("timer[15]", 0x40014000, 0x400);
236
+ create_unimplemented_device("timer[16]", 0x40014400, 0x400);
237
+ create_unimplemented_device("timer[17]", 0x40014800, 0x400);
238
+ create_unimplemented_device("DMA", 0x40020000, 0x400);
239
+ create_unimplemented_device("RCC", 0x40021000, 0x400);
240
+ create_unimplemented_device("Flash Int", 0x40022000, 0x400);
241
+ create_unimplemented_device("CRC", 0x40023000, 0x400);
242
+}
243
+
244
+static Property stm32f100_soc_properties[] = {
245
+ DEFINE_PROP_STRING("cpu-type", STM32F100State, cpu_type),
246
+ DEFINE_PROP_END_OF_LIST(),
247
+};
248
+
249
+static void stm32f100_soc_class_init(ObjectClass *klass, void *data)
250
+{
251
+ DeviceClass *dc = DEVICE_CLASS(klass);
252
+
253
+ dc->realize = stm32f100_soc_realize;
254
+ device_class_set_props(dc, stm32f100_soc_properties);
255
+}
256
+
257
+static const TypeInfo stm32f100_soc_info = {
258
+ .name = TYPE_STM32F100_SOC,
259
+ .parent = TYPE_SYS_BUS_DEVICE,
260
+ .instance_size = sizeof(STM32F100State),
261
+ .instance_init = stm32f100_soc_initfn,
262
+ .class_init = stm32f100_soc_class_init,
263
+};
264
+
265
+static void stm32f100_soc_types(void)
266
+{
267
+ type_register_static(&stm32f100_soc_info);
268
+}
269
+
270
+type_init(stm32f100_soc_types)
271
diff --git a/MAINTAINERS b/MAINTAINERS
19
index XXXXXXX..XXXXXXX 100644
272
index XXXXXXX..XXXXXXX 100644
20
--- a/hw/intc/arm_gic_kvm.c
273
--- a/MAINTAINERS
21
+++ b/hw/intc/arm_gic_kvm.c
274
+++ b/MAINTAINERS
22
@@ -XXX,XX +XXX,XX @@ static void kvm_arm_gic_realize(DeviceState *dev, Error **errp)
275
@@ -XXX,XX +XXX,XX @@ L: qemu-arm@nongnu.org
23
276
S: Maintained
24
if (kvm_has_gsi_routing()) {
277
F: hw/arm/virt-acpi-build.c
25
/* set up irq routing */
278
26
- kvm_init_irq_routing(kvm_state);
279
+STM32F100
27
for (i = 0; i < s->num_irq - GIC_INTERNAL; ++i) {
280
+M: Alexandre Iooss <erdnaxe@crans.org>
28
kvm_irqchip_add_irq_route(kvm_state, i, 0, i);
281
+L: qemu-arm@nongnu.org
29
}
282
+S: Maintained
30
diff --git a/hw/intc/arm_gicv3_kvm.c b/hw/intc/arm_gicv3_kvm.c
283
+F: hw/arm/stm32f100_soc.c
284
+
285
STM32F205
286
M: Alistair Francis <alistair@alistair23.me>
287
M: Peter Maydell <peter.maydell@linaro.org>
288
diff --git a/hw/arm/Kconfig b/hw/arm/Kconfig
31
index XXXXXXX..XXXXXXX 100644
289
index XXXXXXX..XXXXXXX 100644
32
--- a/hw/intc/arm_gicv3_kvm.c
290
--- a/hw/arm/Kconfig
33
+++ b/hw/intc/arm_gicv3_kvm.c
291
+++ b/hw/arm/Kconfig
34
@@ -XXX,XX +XXX,XX @@ static void kvm_arm_gicv3_realize(DeviceState *dev, Error **errp)
292
@@ -XXX,XX +XXX,XX @@ config RASPI
35
293
select SDHCI
36
if (kvm_has_gsi_routing()) {
294
select USB_DWC2
37
/* set up irq routing */
295
38
- kvm_init_irq_routing(kvm_state);
296
+config STM32F100_SOC
39
for (i = 0; i < s->num_irq - GIC_INTERNAL; ++i) {
297
+ bool
40
kvm_irqchip_add_irq_route(kvm_state, i, 0, i);
298
+ select ARM_V7M
41
}
299
+ select STM32F2XX_USART
300
+ select STM32F2XX_SPI
301
+
302
config STM32F205_SOC
303
bool
304
select ARM_V7M
305
diff --git a/hw/arm/meson.build b/hw/arm/meson.build
306
index XXXXXXX..XXXXXXX 100644
307
--- a/hw/arm/meson.build
308
+++ b/hw/arm/meson.build
309
@@ -XXX,XX +XXX,XX @@ arm_ss.add(when: 'CONFIG_STRONGARM', if_true: files('strongarm.c'))
310
arm_ss.add(when: 'CONFIG_ALLWINNER_A10', if_true: files('allwinner-a10.c', 'cubieboard.c'))
311
arm_ss.add(when: 'CONFIG_ALLWINNER_H3', if_true: files('allwinner-h3.c', 'orangepi.c'))
312
arm_ss.add(when: 'CONFIG_RASPI', if_true: files('bcm2835_peripherals.c', 'bcm2836.c', 'raspi.c'))
313
+arm_ss.add(when: 'CONFIG_STM32F100_SOC', if_true: files('stm32f100_soc.c'))
314
arm_ss.add(when: 'CONFIG_STM32F205_SOC', if_true: files('stm32f205_soc.c'))
315
arm_ss.add(when: 'CONFIG_STM32F405_SOC', if_true: files('stm32f405_soc.c'))
316
arm_ss.add(when: 'CONFIG_XLNX_ZYNQMP_ARM', if_true: files('xlnx-zynqmp.c', 'xlnx-zcu102.c'))
42
--
317
--
43
2.17.1
318
2.20.1
44
319
45
320
diff view generated by jsdifflib
1
From: Shannon Zhao <zhaoshenglong@huawei.com>
1
From: Alexandre Iooss <erdnaxe@crans.org>
2
2
3
acpi_data_push uses g_array_set_size to resize the memory size. If there
3
This is a Cortex-M3 based machine. Information can be found at:
4
is no enough contiguous memory, the address will be changed. So previous
4
https://www.st.com/en/evaluation-tools/stm32vldiscovery.html
5
pointer could not be used any more. It must update the pointer and use
6
the new one.
7
5
8
Also, previous codes wrongly use le32 conversion of iort->node_offset
6
Signed-off-by: Alexandre Iooss <erdnaxe@crans.org>
9
for subsequent computations that will result incorrect value if host is
7
Reviewed-by: Alistair Francis <alistair.francis@wdc.com>
10
not litlle endian. So use the non-converted one instead.
8
Message-id: 20210617165647.2575955-3-erdnaxe@crans.org
11
12
Signed-off-by: Shannon Zhao <zhaoshenglong@huawei.com>
13
Reviewed-by: Eric Auger <eric.auger@redhat.com>
14
Message-id: 1527663951-14552-1-git-send-email-zhaoshenglong@huawei.com
15
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
9
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
16
---
10
---
17
hw/arm/virt-acpi-build.c | 20 +++++++++++++++-----
11
default-configs/devices/arm-softmmu.mak | 1 +
18
1 file changed, 15 insertions(+), 5 deletions(-)
12
hw/arm/stm32vldiscovery.c | 66 +++++++++++++++++++++++++
13
MAINTAINERS | 6 +++
14
hw/arm/Kconfig | 4 ++
15
hw/arm/meson.build | 1 +
16
5 files changed, 78 insertions(+)
17
create mode 100644 hw/arm/stm32vldiscovery.c
19
18
20
diff --git a/hw/arm/virt-acpi-build.c b/hw/arm/virt-acpi-build.c
19
diff --git a/default-configs/devices/arm-softmmu.mak b/default-configs/devices/arm-softmmu.mak
21
index XXXXXXX..XXXXXXX 100644
20
index XXXXXXX..XXXXXXX 100644
22
--- a/hw/arm/virt-acpi-build.c
21
--- a/default-configs/devices/arm-softmmu.mak
23
+++ b/hw/arm/virt-acpi-build.c
22
+++ b/default-configs/devices/arm-softmmu.mak
24
@@ -XXX,XX +XXX,XX @@ build_iort(GArray *table_data, BIOSLinker *linker, VirtMachineState *vms)
23
@@ -XXX,XX +XXX,XX @@ CONFIG_CHEETAH=y
25
AcpiIortItsGroup *its;
24
CONFIG_SX1=y
26
AcpiIortTable *iort;
25
CONFIG_NSERIES=y
27
AcpiIortSmmu3 *smmu;
26
CONFIG_STELLARIS=y
28
- size_t node_size, iort_length, smmu_offset = 0;
27
+CONFIG_STM32VLDISCOVERY=y
29
+ size_t node_size, iort_node_offset, iort_length, smmu_offset = 0;
28
CONFIG_REALVIEW=y
30
AcpiIortRC *rc;
29
CONFIG_VERSATILE=y
31
30
CONFIG_VEXPRESS=y
32
iort = acpi_data_push(table_data, sizeof(*iort));
31
diff --git a/hw/arm/stm32vldiscovery.c b/hw/arm/stm32vldiscovery.c
33
@@ -XXX,XX +XXX,XX @@ build_iort(GArray *table_data, BIOSLinker *linker, VirtMachineState *vms)
32
new file mode 100644
34
33
index XXXXXXX..XXXXXXX
35
iort_length = sizeof(*iort);
34
--- /dev/null
36
iort->node_count = cpu_to_le32(nb_nodes);
35
+++ b/hw/arm/stm32vldiscovery.c
37
- iort->node_offset = cpu_to_le32(sizeof(*iort));
36
@@ -XXX,XX +XXX,XX @@
37
+/*
38
+ * ST STM32VLDISCOVERY machine
39
+ *
40
+ * Copyright (c) 2021 Alexandre Iooss <erdnaxe@crans.org>
41
+ * Copyright (c) 2014 Alistair Francis <alistair@alistair23.me>
42
+ *
43
+ * Permission is hereby granted, free of charge, to any person obtaining a copy
44
+ * of this software and associated documentation files (the "Software"), to deal
45
+ * in the Software without restriction, including without limitation the rights
46
+ * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
47
+ * copies of the Software, and to permit persons to whom the Software is
48
+ * furnished to do so, subject to the following conditions:
49
+ *
50
+ * The above copyright notice and this permission notice shall be included in
51
+ * all copies or substantial portions of the Software.
52
+ *
53
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
54
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
55
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
56
+ * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
57
+ * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
58
+ * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
59
+ * THE SOFTWARE.
60
+ */
61
+
62
+#include "qemu/osdep.h"
63
+#include "qapi/error.h"
64
+#include "hw/boards.h"
65
+#include "hw/qdev-properties.h"
66
+#include "qemu/error-report.h"
67
+#include "hw/arm/stm32f100_soc.h"
68
+#include "hw/arm/boot.h"
69
+
70
+/* stm32vldiscovery implementation is derived from netduinoplus2 */
71
+
72
+/* Main SYSCLK frequency in Hz (24MHz) */
73
+#define SYSCLK_FRQ 24000000ULL
74
+
75
+static void stm32vldiscovery_init(MachineState *machine)
76
+{
77
+ DeviceState *dev;
78
+
38
+ /*
79
+ /*
39
+ * Use a copy in case table_data->data moves during acpi_data_push
80
+ * TODO: ideally we would model the SoC RCC and let it handle
40
+ * operations.
81
+ * system_clock_scale, including its ability to define different
82
+ * possible SYSCLK sources.
41
+ */
83
+ */
42
+ iort_node_offset = sizeof(*iort);
84
+ system_clock_scale = NANOSECONDS_PER_SECOND / SYSCLK_FRQ;
43
+ iort->node_offset = cpu_to_le32(iort_node_offset);
85
+
44
86
+ dev = qdev_new(TYPE_STM32F100_SOC);
45
/* ITS group node */
87
+ qdev_prop_set_string(dev, "cpu-type", ARM_CPU_TYPE_NAME("cortex-m3"));
46
node_size = sizeof(*its) + sizeof(uint32_t);
88
+ sysbus_realize_and_unref(SYS_BUS_DEVICE(dev), &error_fatal);
47
@@ -XXX,XX +XXX,XX @@ build_iort(GArray *table_data, BIOSLinker *linker, VirtMachineState *vms)
89
+
48
int irq = vms->irqmap[VIRT_SMMU];
90
+ armv7m_load_kernel(ARM_CPU(first_cpu),
49
91
+ machine->kernel_filename,
50
/* SMMUv3 node */
92
+ FLASH_SIZE);
51
- smmu_offset = iort->node_offset + node_size;
93
+}
52
+ smmu_offset = iort_node_offset + node_size;
94
+
53
node_size = sizeof(*smmu) + sizeof(*idmap);
95
+static void stm32vldiscovery_machine_init(MachineClass *mc)
54
iort_length += node_size;
96
+{
55
smmu = acpi_data_push(table_data, node_size);
97
+ mc->desc = "ST STM32VLDISCOVERY (Cortex-M3)";
56
@@ -XXX,XX +XXX,XX @@ build_iort(GArray *table_data, BIOSLinker *linker, VirtMachineState *vms)
98
+ mc->init = stm32vldiscovery_init;
57
idmap->id_count = cpu_to_le32(0xFFFF);
99
+}
58
idmap->output_base = 0;
100
+
59
/* output IORT node is the ITS group node (the first node) */
101
+DEFINE_MACHINE("stm32vldiscovery", stm32vldiscovery_machine_init)
60
- idmap->output_reference = cpu_to_le32(iort->node_offset);
102
+
61
+ idmap->output_reference = cpu_to_le32(iort_node_offset);
103
diff --git a/MAINTAINERS b/MAINTAINERS
62
}
104
index XXXXXXX..XXXXXXX 100644
63
105
--- a/MAINTAINERS
64
/* Root Complex Node */
106
+++ b/MAINTAINERS
65
@@ -XXX,XX +XXX,XX @@ build_iort(GArray *table_data, BIOSLinker *linker, VirtMachineState *vms)
107
@@ -XXX,XX +XXX,XX @@ F: hw/*/stellaris*
66
idmap->output_reference = cpu_to_le32(smmu_offset);
108
F: include/hw/input/gamepad.h
67
} else {
109
F: docs/system/arm/stellaris.rst
68
/* output IORT node is the ITS group node (the first node) */
110
69
- idmap->output_reference = cpu_to_le32(iort->node_offset);
111
+STM32VLDISCOVERY
70
+ idmap->output_reference = cpu_to_le32(iort_node_offset);
112
+M: Alexandre Iooss <erdnaxe@crans.org>
71
}
113
+L: qemu-arm@nongnu.org
72
114
+S: Maintained
73
+ /*
115
+F: hw/arm/stm32vldiscovery.c
74
+ * Update the pointer address in case table_data->data moves during above
116
+
75
+ * acpi_data_push operations.
117
Versatile Express
76
+ */
118
M: Peter Maydell <peter.maydell@linaro.org>
77
+ iort = (AcpiIortTable *)(table_data->data + iort_start);
119
L: qemu-arm@nongnu.org
78
iort->length = cpu_to_le32(iort_length);
120
diff --git a/hw/arm/Kconfig b/hw/arm/Kconfig
79
121
index XXXXXXX..XXXXXXX 100644
80
build_header(linker, table_data, (void *)(table_data->data + iort_start),
122
--- a/hw/arm/Kconfig
123
+++ b/hw/arm/Kconfig
124
@@ -XXX,XX +XXX,XX @@ config STELLARIS
125
select STELLARIS_ENET # ethernet
126
select UNIMP
127
128
+config STM32VLDISCOVERY
129
+ bool
130
+ select STM32F100_SOC
131
+
132
config STRONGARM
133
bool
134
select PXA2XX
135
diff --git a/hw/arm/meson.build b/hw/arm/meson.build
136
index XXXXXXX..XXXXXXX 100644
137
--- a/hw/arm/meson.build
138
+++ b/hw/arm/meson.build
139
@@ -XXX,XX +XXX,XX @@ arm_ss.add(when: 'CONFIG_Z2', if_true: files('z2.c'))
140
arm_ss.add(when: 'CONFIG_REALVIEW', if_true: files('realview.c'))
141
arm_ss.add(when: 'CONFIG_SBSA_REF', if_true: files('sbsa-ref.c'))
142
arm_ss.add(when: 'CONFIG_STELLARIS', if_true: files('stellaris.c'))
143
+arm_ss.add(when: 'CONFIG_STM32VLDISCOVERY', if_true: files('stm32vldiscovery.c'))
144
arm_ss.add(when: 'CONFIG_COLLIE', if_true: files('collie.c'))
145
arm_ss.add(when: 'CONFIG_VERSATILE', if_true: files('versatilepb.c'))
146
arm_ss.add(when: 'CONFIG_VEXPRESS', if_true: files('vexpress.c'))
81
--
147
--
82
2.17.1
148
2.20.1
83
149
84
150
diff view generated by jsdifflib
1
Add entries to MAINTAINERS to cover the newer MPS2 boards and
1
From: Alexandre Iooss <erdnaxe@crans.org>
2
the new devices they use.
3
2
3
This adds the target guide for Netduino 2, Netduino Plus 2 and STM32VLDISCOVERY.
4
5
Signed-off-by: Alexandre Iooss <erdnaxe@crans.org>
6
Reviewed-by: Alistair Francis <alistair.francis@wdc.com>
7
Message-id: 20210617165647.2575955-4-erdnaxe@crans.org
4
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
8
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
5
Message-id: 20180518153157.14899-1-peter.maydell@linaro.org
6
---
9
---
7
MAINTAINERS | 9 +++++++--
10
docs/system/arm/stm32.rst | 66 ++++++++++++++++++++++++++++++++++++++
8
1 file changed, 7 insertions(+), 2 deletions(-)
11
docs/system/target-arm.rst | 1 +
12
MAINTAINERS | 1 +
13
3 files changed, 68 insertions(+)
14
create mode 100644 docs/system/arm/stm32.rst
9
15
16
diff --git a/docs/system/arm/stm32.rst b/docs/system/arm/stm32.rst
17
new file mode 100644
18
index XXXXXXX..XXXXXXX
19
--- /dev/null
20
+++ b/docs/system/arm/stm32.rst
21
@@ -XXX,XX +XXX,XX @@
22
+STMicroelectronics STM32 boards (``netduino2``, ``netduinoplus2``, ``stm32vldiscovery``)
23
+========================================================================================
24
+
25
+The `STM32`_ chips are a family of 32-bit ARM-based microcontroller by
26
+STMicroelectronics.
27
+
28
+.. _STM32: https://www.st.com/en/microcontrollers-microprocessors/stm32-32-bit-arm-cortex-mcus.html
29
+
30
+The STM32F1 series is based on ARM Cortex-M3 core. The following machines are
31
+based on this chip :
32
+
33
+- ``stm32vldiscovery`` STM32VLDISCOVERY board with STM32F100RBT6 microcontroller
34
+
35
+The STM32F2 series is based on ARM Cortex-M3 core. The following machines are
36
+based on this chip :
37
+
38
+- ``netduino2`` Netduino 2 board with STM32F205RFT6 microcontroller
39
+
40
+The STM32F4 series is based on ARM Cortex-M4F core. This series is pin-to-pin
41
+compatible with STM32F2 series. The following machines are based on this chip :
42
+
43
+- ``netduinoplus2`` Netduino Plus 2 board with STM32F405RGT6 microcontroller
44
+
45
+There are many other STM32 series that are currently not supported by QEMU.
46
+
47
+Supported devices
48
+-----------------
49
+
50
+ * ARM Cortex-M3, Cortex M4F
51
+ * Analog to Digital Converter (ADC)
52
+ * EXTI interrupt
53
+ * Serial ports (USART)
54
+ * SPI controller
55
+ * System configuration (SYSCFG)
56
+ * Timer controller (TIMER)
57
+
58
+Missing devices
59
+---------------
60
+
61
+ * Camera interface (DCMI)
62
+ * Controller Area Network (CAN)
63
+ * Cycle Redundancy Check (CRC) calculation unit
64
+ * Digital to Analog Converter (DAC)
65
+ * DMA controller
66
+ * Ethernet controller
67
+ * Flash Interface Unit
68
+ * GPIO controller
69
+ * I2C controller
70
+ * Inter-Integrated Sound (I2S) controller
71
+ * Power supply configuration (PWR)
72
+ * Random Number Generator (RNG)
73
+ * Real-Time Clock (RTC) controller
74
+ * Reset and Clock Controller (RCC)
75
+ * Secure Digital Input/Output (SDIO) interface
76
+ * USB OTG
77
+ * Watchdog controller (IWDG, WWDG)
78
+
79
+Boot options
80
+------------
81
+
82
+The STM32 machines can be started using the ``-kernel`` option to load a
83
+firmware. Example:
84
+
85
+.. code-block:: bash
86
+
87
+ $ qemu-system-arm -M stm32vldiscovery -kernel firmware.bin
88
diff --git a/docs/system/target-arm.rst b/docs/system/target-arm.rst
89
index XXXXXXX..XXXXXXX 100644
90
--- a/docs/system/target-arm.rst
91
+++ b/docs/system/target-arm.rst
92
@@ -XXX,XX +XXX,XX @@ undocumented; you can get a complete list by running
93
arm/collie
94
arm/sx1
95
arm/stellaris
96
+ arm/stm32
97
arm/virt
98
arm/xlnx-versal-virt
99
10
diff --git a/MAINTAINERS b/MAINTAINERS
100
diff --git a/MAINTAINERS b/MAINTAINERS
11
index XXXXXXX..XXXXXXX 100644
101
index XXXXXXX..XXXXXXX 100644
12
--- a/MAINTAINERS
102
--- a/MAINTAINERS
13
+++ b/MAINTAINERS
103
+++ b/MAINTAINERS
14
@@ -XXX,XX +XXX,XX @@ F: hw/timer/cmsdk-apb-timer.c
104
@@ -XXX,XX +XXX,XX @@ M: Alexandre Iooss <erdnaxe@crans.org>
15
F: include/hw/timer/cmsdk-apb-timer.h
16
F: hw/char/cmsdk-apb-uart.c
17
F: include/hw/char/cmsdk-apb-uart.h
18
+F: hw/misc/tz-ppc.c
19
+F: include/hw/misc/tz-ppc.h
20
21
ARM cores
22
M: Peter Maydell <peter.maydell@linaro.org>
23
@@ -XXX,XX +XXX,XX @@ M: Peter Maydell <peter.maydell@linaro.org>
24
L: qemu-arm@nongnu.org
105
L: qemu-arm@nongnu.org
25
S: Maintained
106
S: Maintained
26
F: hw/arm/mps2.c
107
F: hw/arm/stm32vldiscovery.c
27
-F: hw/misc/mps2-scc.c
108
+F: docs/system/arm/stm32.rst
28
-F: include/hw/misc/mps2-scc.h
109
29
+F: hw/arm/mps2-tz.c
110
Versatile Express
30
+F: hw/misc/mps2-*.c
111
M: Peter Maydell <peter.maydell@linaro.org>
31
+F: include/hw/misc/mps2-*.h
32
+F: hw/arm/iotkit.c
33
+F: include/hw/arm/iotkit.h
34
35
Musicpal
36
M: Jan Kiszka <jan.kiszka@web.de>
37
--
112
--
38
2.17.1
113
2.20.1
39
114
40
115
diff view generated by jsdifflib
1
From: Igor Mammedov <imammedo@redhat.com>
1
From: Alexandre Iooss <erdnaxe@crans.org>
2
2
3
When QEMU is started with following CLI
3
New mini-kernel test for STM32VLDISCOVERY USART1.
4
-machine virt,gic-version=3,accel=kvm -cpu host -bios AAVMF_CODE.fd
5
it crashes with abort at
6
accel/kvm/kvm-all.c:2164:
7
KVM_SET_DEVICE_ATTR failed: Group 6 attr 0x000000000000c665: Invalid argument
8
4
9
Which is caused by implicit dependency of kvm_arm_gicv3_reset() on
5
Signed-off-by: Alexandre Iooss <erdnaxe@crans.org>
10
arm_gicv3_icc_reset() where the later is called by CPU reset
6
Acked-by: Thomas Huth <thuth@redhat.com>
11
reset callback.
7
Acked-by: Alistair Francis <alistair.francis@wdc.com>
12
8
Message-id: 20210617165647.2575955-5-erdnaxe@crans.org
13
However commit:
14
3b77f6c arm/boot: split load_dtb() from arm_load_kernel()
15
broke CPU reset callback registration in case
16
17
arm_load_kernel()
18
...
19
if (!info->kernel_filename || info->firmware_loaded)
20
21
branch is taken, i.e. it's sufficient to provide a firmware
22
or do not provide kernel on CLI to skip cpu reset callback
23
registration, where before offending commit the callback
24
has been registered unconditionally.
25
26
Fix it by registering the callback right at the beginning of
27
arm_load_kernel() unconditionally instead of doing it at the end.
28
29
NOTE:
30
we probably should eliminate that dependency anyways as well as
31
separate arch CPU reset parts from arm_load_kernel() into CPU
32
itself, but that refactoring that I probably would have to do
33
anyways later for CPU hotplug to work.
34
35
Reported-by: Auger Eric <eric.auger@redhat.com>
36
Signed-off-by: Igor Mammedov <imammedo@redhat.com>
37
Reviewed-by: Eric Auger <eric.auger@redhat.com>
38
Tested-by: Eric Auger <eric.auger@redhat.com>
39
Message-id: 1527070950-208350-1-git-send-email-imammedo@redhat.com
40
Reviewed-by: Peter Maydell <peter.maydell@linaro.org>
41
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
9
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
42
---
10
---
43
hw/arm/boot.c | 18 +++++++++---------
11
tests/qtest/boot-serial-test.c | 37 ++++++++++++++++++++++++++++++++++
44
1 file changed, 9 insertions(+), 9 deletions(-)
12
1 file changed, 37 insertions(+)
45
13
46
diff --git a/hw/arm/boot.c b/hw/arm/boot.c
14
diff --git a/tests/qtest/boot-serial-test.c b/tests/qtest/boot-serial-test.c
47
index XXXXXXX..XXXXXXX 100644
15
index XXXXXXX..XXXXXXX 100644
48
--- a/hw/arm/boot.c
16
--- a/tests/qtest/boot-serial-test.c
49
+++ b/hw/arm/boot.c
17
+++ b/tests/qtest/boot-serial-test.c
50
@@ -XXX,XX +XXX,XX @@ void arm_load_kernel(ARMCPU *cpu, struct arm_boot_info *info)
18
@@ -XXX,XX +XXX,XX @@ static const uint8_t kernel_nrf51[] = {
51
static const ARMInsnFixup *primary_loader;
19
0x1c, 0x25, 0x00, 0x40 /* 0x4000251c = UART TXD */
52
AddressSpace *as = arm_boot_address_space(cpu, info);
20
};
53
21
54
+ /* CPU objects (unlike devices) are not automatically reset on system
22
+static const uint8_t kernel_stm32vldiscovery[] = {
55
+ * reset, so we must always register a handler to do so. If we're
23
+ 0x00, 0x00, 0x00, 0x00, /* Stack top address */
56
+ * actually loading a kernel, the handler is also responsible for
24
+ 0x1d, 0x00, 0x00, 0x00, /* Reset handler address */
57
+ * arranging that we start it correctly.
25
+ 0x00, 0x00, 0x00, 0x00, /* NMI */
58
+ */
26
+ 0x00, 0x00, 0x00, 0x00, /* Hard fault */
59
+ for (cs = first_cpu; cs; cs = CPU_NEXT(cs)) {
27
+ 0x00, 0x00, 0x00, 0x00, /* Memory management fault */
60
+ qemu_register_reset(do_cpu_reset, ARM_CPU(cs));
28
+ 0x00, 0x00, 0x00, 0x00, /* Bus fault */
61
+ }
29
+ 0x00, 0x00, 0x00, 0x00, /* Usage fault */
30
+ 0x0b, 0x4b, /* ldr r3, [pc, #44] Get RCC */
31
+ 0x44, 0xf2, 0x04, 0x02, /* movw r2, #16388 */
32
+ 0x1a, 0x60, /* str r2, [r3] */
33
+ 0x0a, 0x4b, /* ldr r3, [pc, #40] Get GPIOA */
34
+ 0x1a, 0x68, /* ldr r2, [r3] */
35
+ 0x22, 0xf0, 0xf0, 0x02, /* bic r2, r2, #240 */
36
+ 0x1a, 0x60, /* str r2, [r3] */
37
+ 0x1a, 0x68, /* ldr r2, [r3] */
38
+ 0x42, 0xf0, 0xb0, 0x02, /* orr r2, r2, #176 */
39
+ 0x1a, 0x60, /* str r2, [r3] */
40
+ 0x07, 0x4b, /* ldr r3, [pc, #26] Get BAUD */
41
+ 0x45, 0x22, /* movs r2, #69 */
42
+ 0x1a, 0x60, /* str r2, [r3] */
43
+ 0x06, 0x4b, /* ldr r3, [pc, #24] Get ENABLE */
44
+ 0x42, 0xf2, 0x08, 0x02, /* movw r2, #8200 */
45
+ 0x1a, 0x60, /* str r2, [r3] */
46
+ 0x05, 0x4b, /* ldr r3, [pc, #20] Get TXD */
47
+ 0x54, 0x22, /* movs r2, 'T' */
48
+ 0x1a, 0x60, /* str r2, [r3] */
49
+ 0xfe, 0xe7, /* b . */
50
+ 0x18, 0x10, 0x02, 0x40, /* 0x40021018 = RCC */
51
+ 0x04, 0x08, 0x01, 0x40, /* 0x40010804 = GPIOA */
52
+ 0x08, 0x38, 0x01, 0x40, /* 0x40013808 = USART1 BAUD */
53
+ 0x0c, 0x38, 0x01, 0x40, /* 0x4001380c = USART1 ENABLE */
54
+ 0x04, 0x38, 0x01, 0x40 /* 0x40013804 = USART1 TXD */
55
+};
62
+
56
+
63
/* The board code is not supposed to set secure_board_setup unless
57
typedef struct testdef {
64
* running its code in secure mode is actually possible, and KVM
58
const char *arch; /* Target architecture */
65
* doesn't support secure.
59
const char *machine; /* Name of the machine */
66
@@ -XXX,XX +XXX,XX @@ void arm_load_kernel(ARMCPU *cpu, struct arm_boot_info *info)
60
@@ -XXX,XX +XXX,XX @@ static testdef_t tests[] = {
67
ARM_CPU(cs)->env.boot_info = info;
61
{ "aarch64", "virt", "-cpu max", "TT", sizeof(kernel_aarch64),
68
}
62
kernel_aarch64 },
69
63
{ "arm", "microbit", "", "T", sizeof(kernel_nrf51), kernel_nrf51 },
70
- /* CPU objects (unlike devices) are not automatically reset on system
64
+ { "arm", "stm32vldiscovery", "", "T",
71
- * reset, so we must always register a handler to do so. If we're
65
+ sizeof(kernel_stm32vldiscovery), kernel_stm32vldiscovery },
72
- * actually loading a kernel, the handler is also responsible for
66
73
- * arranging that we start it correctly.
67
{ NULL }
74
- */
68
};
75
- for (cs = first_cpu; cs; cs = CPU_NEXT(cs)) {
76
- qemu_register_reset(do_cpu_reset, ARM_CPU(cs));
77
- }
78
-
79
if (!info->skip_dtb_autoload && have_dtb(info)) {
80
if (arm_load_dtb(info->dtb_start, info, info->dtb_limit, as) < 0) {
81
exit(1);
82
--
69
--
83
2.17.1
70
2.20.1
84
71
85
72
diff view generated by jsdifflib
1
From: Jan Kiszka <jan.kiszka@siemens.com>
1
From: Ricardo Koller <ricarkol@google.com>
2
2
3
There was a nasty flip in identifying which register group an access is
3
icv_eoir_write() and icv_dir_write() ignore invalid virtual IRQ numbers
4
targeting. The issue caused spuriously raised priorities of the guest
4
(like LPIs). The issue is that these functions check against the number
5
when handing CPUs over in the Jailhouse hypervisor.
5
of implemented IRQs (QEMU's default is num_irq=288) which can be lower
6
than the maximum virtual IRQ number (1020 - 1). The consequence is that
7
if a hypervisor creates an LR for an IRQ between 288 and 1020, then the
8
guest is unable to deactivate the resulting IRQ. Note that other
9
functions that deal with large IRQ numbers, like icv_iar_read, check
10
against 1020 and not against num_irq.
6
11
7
Cc: qemu-stable@nongnu.org
12
Fix the checks by using GICV3_MAXIRQ (1020) instead of the number of
8
Signed-off-by: Jan Kiszka <jan.kiszka@siemens.com>
13
implemented IRQs.
9
Message-id: 28b927d3-da58-bce4-cc13-bfec7f9b1cb9@siemens.com
14
15
Signed-off-by: Ricardo Koller <ricarkol@google.com>
16
Message-id: 20210702233701.3369-1-ricarkol@google.com
10
Reviewed-by: Peter Maydell <peter.maydell@linaro.org>
17
Reviewed-by: Peter Maydell <peter.maydell@linaro.org>
11
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
18
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
12
---
19
---
13
hw/intc/arm_gicv3_cpuif.c | 12 ++++++------
20
hw/intc/arm_gicv3_cpuif.c | 4 ++--
14
1 file changed, 6 insertions(+), 6 deletions(-)
21
1 file changed, 2 insertions(+), 2 deletions(-)
15
22
16
diff --git a/hw/intc/arm_gicv3_cpuif.c b/hw/intc/arm_gicv3_cpuif.c
23
diff --git a/hw/intc/arm_gicv3_cpuif.c b/hw/intc/arm_gicv3_cpuif.c
17
index XXXXXXX..XXXXXXX 100644
24
index XXXXXXX..XXXXXXX 100644
18
--- a/hw/intc/arm_gicv3_cpuif.c
25
--- a/hw/intc/arm_gicv3_cpuif.c
19
+++ b/hw/intc/arm_gicv3_cpuif.c
26
+++ b/hw/intc/arm_gicv3_cpuif.c
20
@@ -XXX,XX +XXX,XX @@ static uint64_t icv_ap_read(CPUARMState *env, const ARMCPRegInfo *ri)
27
@@ -XXX,XX +XXX,XX @@ static void icv_dir_write(CPUARMState *env, const ARMCPRegInfo *ri,
21
{
28
22
GICv3CPUState *cs = icc_cs_from_env(env);
29
trace_gicv3_icv_dir_write(gicv3_redist_affid(cs), value);
23
int regno = ri->opc2 & 3;
30
24
- int grp = ri->crm & 1 ? GICV3_G0 : GICV3_G1NS;
31
- if (irq >= cs->gic->num_irq) {
25
+ int grp = (ri->crm & 1) ? GICV3_G1NS : GICV3_G0;
32
+ if (irq >= GICV3_MAXIRQ) {
26
uint64_t value = cs->ich_apr[grp][regno];
33
/* Also catches special interrupt numbers and LPIs */
27
34
return;
28
trace_gicv3_icv_ap_read(ri->crm & 1, regno, gicv3_redist_affid(cs), value);
35
}
29
@@ -XXX,XX +XXX,XX @@ static void icv_ap_write(CPUARMState *env, const ARMCPRegInfo *ri,
36
@@ -XXX,XX +XXX,XX @@ static void icv_eoir_write(CPUARMState *env, const ARMCPRegInfo *ri,
30
{
37
trace_gicv3_icv_eoir_write(ri->crm == 8 ? 0 : 1,
31
GICv3CPUState *cs = icc_cs_from_env(env);
38
gicv3_redist_affid(cs), value);
32
int regno = ri->opc2 & 3;
39
33
- int grp = ri->crm & 1 ? GICV3_G0 : GICV3_G1NS;
40
- if (irq >= cs->gic->num_irq) {
34
+ int grp = (ri->crm & 1) ? GICV3_G1NS : GICV3_G0;
41
+ if (irq >= GICV3_MAXIRQ) {
35
42
/* Also catches special interrupt numbers and LPIs */
36
trace_gicv3_icv_ap_write(ri->crm & 1, regno, gicv3_redist_affid(cs), value);
43
return;
37
44
}
38
@@ -XXX,XX +XXX,XX @@ static uint64_t icc_ap_read(CPUARMState *env, const ARMCPRegInfo *ri)
39
uint64_t value;
40
41
int regno = ri->opc2 & 3;
42
- int grp = ri->crm & 1 ? GICV3_G0 : GICV3_G1;
43
+ int grp = (ri->crm & 1) ? GICV3_G1 : GICV3_G0;
44
45
if (icv_access(env, grp == GICV3_G0 ? HCR_FMO : HCR_IMO)) {
46
return icv_ap_read(env, ri);
47
@@ -XXX,XX +XXX,XX @@ static void icc_ap_write(CPUARMState *env, const ARMCPRegInfo *ri,
48
GICv3CPUState *cs = icc_cs_from_env(env);
49
50
int regno = ri->opc2 & 3;
51
- int grp = ri->crm & 1 ? GICV3_G0 : GICV3_G1;
52
+ int grp = (ri->crm & 1) ? GICV3_G1 : GICV3_G0;
53
54
if (icv_access(env, grp == GICV3_G0 ? HCR_FMO : HCR_IMO)) {
55
icv_ap_write(env, ri, value);
56
@@ -XXX,XX +XXX,XX @@ static uint64_t ich_ap_read(CPUARMState *env, const ARMCPRegInfo *ri)
57
{
58
GICv3CPUState *cs = icc_cs_from_env(env);
59
int regno = ri->opc2 & 3;
60
- int grp = ri->crm & 1 ? GICV3_G0 : GICV3_G1NS;
61
+ int grp = (ri->crm & 1) ? GICV3_G1NS : GICV3_G0;
62
uint64_t value;
63
64
value = cs->ich_apr[grp][regno];
65
@@ -XXX,XX +XXX,XX @@ static void ich_ap_write(CPUARMState *env, const ARMCPRegInfo *ri,
66
{
67
GICv3CPUState *cs = icc_cs_from_env(env);
68
int regno = ri->opc2 & 3;
69
- int grp = ri->crm & 1 ? GICV3_G0 : GICV3_G1NS;
70
+ int grp = (ri->crm & 1) ? GICV3_G1NS : GICV3_G0;
71
72
trace_gicv3_ich_ap_write(ri->crm & 1, regno, gicv3_redist_affid(cs), value);
73
74
--
45
--
75
2.17.1
46
2.20.1
76
47
77
48
diff view generated by jsdifflib
1
As part of plumbing MemTxAttrs down to the IOMMU translate method,
1
Convert the use of the DPRINTF debug macro in the PL061 model to
2
add MemTxAttrs as an argument to the MemoryRegion valid.accepts
2
use tracepoints.
3
callback. We'll need this for subpage_accepts().
4
5
We could take the approach we used with the read and write
6
callbacks and add new a new _with_attrs version, but since there
7
are so few implementations of the accepts hook we just change
8
them all.
9
3
10
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
4
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
11
Reviewed-by: Alex Bennée <alex.bennee@linaro.org>
5
Reviewed-by: Philippe Mathieu-Daudé <f4bug@amsat.org>
12
Reviewed-by: Richard Henderson <richard.henderson@linaro.org>
6
Reviewed-by: Richard Henderson <richard.henderson@linaro.org>
13
Message-id: 20180521140402.23318-9-peter.maydell@linaro.org
14
---
7
---
15
include/exec/memory.h | 3 ++-
8
hw/gpio/pl061.c | 27 +++++++++------------------
16
exec.c | 9 ++++++---
9
hw/gpio/trace-events | 6 ++++++
17
hw/hppa/dino.c | 3 ++-
10
2 files changed, 15 insertions(+), 18 deletions(-)
18
hw/nvram/fw_cfg.c | 12 ++++++++----
19
hw/scsi/esp.c | 3 ++-
20
hw/xen/xen_pt_msi.c | 3 ++-
21
memory.c | 5 +++--
22
7 files changed, 25 insertions(+), 13 deletions(-)
23
11
24
diff --git a/include/exec/memory.h b/include/exec/memory.h
12
diff --git a/hw/gpio/pl061.c b/hw/gpio/pl061.c
25
index XXXXXXX..XXXXXXX 100644
13
index XXXXXXX..XXXXXXX 100644
26
--- a/include/exec/memory.h
14
--- a/hw/gpio/pl061.c
27
+++ b/include/exec/memory.h
15
+++ b/hw/gpio/pl061.c
28
@@ -XXX,XX +XXX,XX @@ struct MemoryRegionOps {
16
@@ -XXX,XX +XXX,XX @@
29
* as a machine check exception).
17
#include "qemu/log.h"
30
*/
18
#include "qemu/module.h"
31
bool (*accepts)(void *opaque, hwaddr addr,
19
#include "qom/object.h"
32
- unsigned size, bool is_write);
20
-
33
+ unsigned size, bool is_write,
21
-//#define DEBUG_PL061 1
34
+ MemTxAttrs attrs);
22
-
35
} valid;
23
-#ifdef DEBUG_PL061
36
/* Internal implementation constraints: */
24
-#define DPRINTF(fmt, ...) \
37
struct {
25
-do { printf("pl061: " fmt , ## __VA_ARGS__); } while (0)
38
diff --git a/exec.c b/exec.c
26
-#define BADF(fmt, ...) \
39
index XXXXXXX..XXXXXXX 100644
27
-do { fprintf(stderr, "pl061: error: " fmt , ## __VA_ARGS__); exit(1);} while (0)
40
--- a/exec.c
28
-#else
41
+++ b/exec.c
29
-#define DPRINTF(fmt, ...) do {} while(0)
42
@@ -XXX,XX +XXX,XX @@ static void notdirty_mem_write(void *opaque, hwaddr ram_addr,
30
-#define BADF(fmt, ...) \
43
}
31
-do { fprintf(stderr, "pl061: error: " fmt , ## __VA_ARGS__);} while (0)
44
32
-#endif
45
static bool notdirty_mem_accepts(void *opaque, hwaddr addr,
33
+#include "trace.h"
46
- unsigned size, bool is_write)
34
47
+ unsigned size, bool is_write,
35
static const uint8_t pl061_id[12] =
48
+ MemTxAttrs attrs)
36
{ 0x00, 0x00, 0x00, 0x00, 0x61, 0x10, 0x04, 0x00, 0x0d, 0xf0, 0x05, 0xb1 };
49
{
37
@@ -XXX,XX +XXX,XX @@ static void pl061_update(PL061State *s)
50
return is_write;
38
uint8_t out;
51
}
39
int i;
52
@@ -XXX,XX +XXX,XX @@ static MemTxResult subpage_write(void *opaque, hwaddr addr,
40
53
}
41
- DPRINTF("dir = %d, data = %d\n", s->dir, s->data);
54
42
+ trace_pl061_update(DEVICE(s)->canonical_path, s->dir, s->data);
55
static bool subpage_accepts(void *opaque, hwaddr addr,
43
56
- unsigned len, bool is_write)
44
/* Outputs float high. */
57
+ unsigned len, bool is_write,
45
/* FIXME: This is board dependent. */
58
+ MemTxAttrs attrs)
46
@@ -XXX,XX +XXX,XX @@ static void pl061_update(PL061State *s)
59
{
47
for (i = 0; i < N_GPIOS; i++) {
60
subpage_t *subpage = opaque;
48
mask = 1 << i;
61
#if defined(DEBUG_SUBPAGE)
49
if (changed & mask) {
62
@@ -XXX,XX +XXX,XX @@ static void readonly_mem_write(void *opaque, hwaddr addr,
50
- DPRINTF("Set output %d = %d\n", i, (out & mask) != 0);
63
}
51
- qemu_set_irq(s->out[i], (out & mask) != 0);
64
52
+ int level = (out & mask) != 0;
65
static bool readonly_mem_accepts(void *opaque, hwaddr addr,
53
+ trace_pl061_set_output(DEVICE(s)->canonical_path, i, level);
66
- unsigned size, bool is_write)
54
+ qemu_set_irq(s->out[i], level);
67
+ unsigned size, bool is_write,
55
}
68
+ MemTxAttrs attrs)
69
{
70
return is_write;
71
}
72
diff --git a/hw/hppa/dino.c b/hw/hppa/dino.c
73
index XXXXXXX..XXXXXXX 100644
74
--- a/hw/hppa/dino.c
75
+++ b/hw/hppa/dino.c
76
@@ -XXX,XX +XXX,XX @@ static void gsc_to_pci_forwarding(DinoState *s)
77
}
78
79
static bool dino_chip_mem_valid(void *opaque, hwaddr addr,
80
- unsigned size, bool is_write)
81
+ unsigned size, bool is_write,
82
+ MemTxAttrs attrs)
83
{
84
switch (addr) {
85
case DINO_IAR0:
86
diff --git a/hw/nvram/fw_cfg.c b/hw/nvram/fw_cfg.c
87
index XXXXXXX..XXXXXXX 100644
88
--- a/hw/nvram/fw_cfg.c
89
+++ b/hw/nvram/fw_cfg.c
90
@@ -XXX,XX +XXX,XX @@ static void fw_cfg_dma_mem_write(void *opaque, hwaddr addr,
91
}
92
93
static bool fw_cfg_dma_mem_valid(void *opaque, hwaddr addr,
94
- unsigned size, bool is_write)
95
+ unsigned size, bool is_write,
96
+ MemTxAttrs attrs)
97
{
98
return !is_write || ((size == 4 && (addr == 0 || addr == 4)) ||
99
(size == 8 && addr == 0));
100
}
101
102
static bool fw_cfg_data_mem_valid(void *opaque, hwaddr addr,
103
- unsigned size, bool is_write)
104
+ unsigned size, bool is_write,
105
+ MemTxAttrs attrs)
106
{
107
return addr == 0;
108
}
109
@@ -XXX,XX +XXX,XX @@ static void fw_cfg_ctl_mem_write(void *opaque, hwaddr addr,
110
}
111
112
static bool fw_cfg_ctl_mem_valid(void *opaque, hwaddr addr,
113
- unsigned size, bool is_write)
114
+ unsigned size, bool is_write,
115
+ MemTxAttrs attrs)
116
{
117
return is_write && size == 2;
118
}
119
@@ -XXX,XX +XXX,XX @@ static void fw_cfg_comb_write(void *opaque, hwaddr addr,
120
}
121
122
static bool fw_cfg_comb_valid(void *opaque, hwaddr addr,
123
- unsigned size, bool is_write)
124
+ unsigned size, bool is_write,
125
+ MemTxAttrs attrs)
126
{
127
return (size == 1) || (is_write && size == 2);
128
}
129
diff --git a/hw/scsi/esp.c b/hw/scsi/esp.c
130
index XXXXXXX..XXXXXXX 100644
131
--- a/hw/scsi/esp.c
132
+++ b/hw/scsi/esp.c
133
@@ -XXX,XX +XXX,XX @@ void esp_reg_write(ESPState *s, uint32_t saddr, uint64_t val)
134
}
135
136
static bool esp_mem_accepts(void *opaque, hwaddr addr,
137
- unsigned size, bool is_write)
138
+ unsigned size, bool is_write,
139
+ MemTxAttrs attrs)
140
{
141
return (size == 1) || (is_write && size == 4);
142
}
143
diff --git a/hw/xen/xen_pt_msi.c b/hw/xen/xen_pt_msi.c
144
index XXXXXXX..XXXXXXX 100644
145
--- a/hw/xen/xen_pt_msi.c
146
+++ b/hw/xen/xen_pt_msi.c
147
@@ -XXX,XX +XXX,XX @@ static uint64_t pci_msix_read(void *opaque, hwaddr addr,
148
}
149
150
static bool pci_msix_accepts(void *opaque, hwaddr addr,
151
- unsigned size, bool is_write)
152
+ unsigned size, bool is_write,
153
+ MemTxAttrs attrs)
154
{
155
return !(addr & (size - 1));
156
}
157
diff --git a/memory.c b/memory.c
158
index XXXXXXX..XXXXXXX 100644
159
--- a/memory.c
160
+++ b/memory.c
161
@@ -XXX,XX +XXX,XX @@ static void unassigned_mem_write(void *opaque, hwaddr addr,
162
}
163
164
static bool unassigned_mem_accepts(void *opaque, hwaddr addr,
165
- unsigned size, bool is_write)
166
+ unsigned size, bool is_write,
167
+ MemTxAttrs attrs)
168
{
169
return false;
170
}
171
@@ -XXX,XX +XXX,XX @@ bool memory_region_access_valid(MemoryRegion *mr,
172
access_size = MAX(MIN(size, access_size_max), access_size_min);
173
for (i = 0; i < size; i += access_size) {
174
if (!mr->ops->valid.accepts(mr->opaque, addr + i, access_size,
175
- is_write)) {
176
+ is_write, attrs)) {
177
return false;
178
}
56
}
179
}
57
}
58
@@ -XXX,XX +XXX,XX @@ static void pl061_update(PL061State *s)
59
for (i = 0; i < N_GPIOS; i++) {
60
mask = 1 << i;
61
if (changed & mask) {
62
- DPRINTF("Changed input %d = %d\n", i, (s->data & mask) != 0);
63
+ trace_pl061_input_change(DEVICE(s)->canonical_path, i,
64
+ (s->data & mask) != 0);
65
66
if (!(s->isense & mask)) {
67
/* Edge interrupt */
68
@@ -XXX,XX +XXX,XX @@ static void pl061_update(PL061State *s)
69
/* Level interrupt */
70
s->istate |= ~(s->data ^ s->iev) & s->isense;
71
72
- DPRINTF("istate = %02X\n", s->istate);
73
+ trace_pl061_update_istate(DEVICE(s)->canonical_path,
74
+ s->istate, s->im, (s->istate & s->im) != 0);
75
76
qemu_set_irq(s->irq, (s->istate & s->im) != 0);
77
}
78
diff --git a/hw/gpio/trace-events b/hw/gpio/trace-events
79
index XXXXXXX..XXXXXXX 100644
80
--- a/hw/gpio/trace-events
81
+++ b/hw/gpio/trace-events
82
@@ -XXX,XX +XXX,XX @@ nrf51_gpio_write(uint64_t offset, uint64_t value) "offset 0x%" PRIx64 " value 0x
83
nrf51_gpio_set(int64_t line, int64_t value) "line %" PRIi64 " value %" PRIi64
84
nrf51_gpio_update_output_irq(int64_t line, int64_t value) "line %" PRIi64 " value %" PRIi64
85
86
+# pl061.c
87
+pl061_update(const char *id, uint32_t dir, uint32_t data) "%s GPIODIR 0x%x GPIODATA 0x%x"
88
+pl061_set_output(const char *id, int gpio, int level) "%s setting output %d to %d"
89
+pl061_input_change(const char *id, int gpio, int level) "%s input %d changed to %d"
90
+pl061_update_istate(const char *id, uint32_t istate, uint32_t im, int level) "%s GPIORIS 0x%x GPIOIE 0x%x interrupt level %d"
91
+
92
# sifive_gpio.c
93
sifive_gpio_read(uint64_t offset, uint64_t r) "offset 0x%" PRIx64 " value 0x%" PRIx64
94
sifive_gpio_write(uint64_t offset, uint64_t value) "offset 0x%" PRIx64 " value 0x%" PRIx64
180
--
95
--
181
2.17.1
96
2.20.1
182
97
183
98
diff view generated by jsdifflib
1
As part of plumbing MemTxAttrs down to the IOMMU translate method,
1
Currently the pl061_read() and pl061_write() functions handle offsets
2
add MemTxAttrs as an argument to tb_invalidate_phys_addr().
2
using a combination of three if() statements and a switch(). Clean
3
Its callers either have an attrs value to hand, or don't care
3
this up to use just a switch, using case ranges.
4
and can use MEMTXATTRS_UNSPECIFIED.
4
5
This requires that instead of catching accesses to the luminary-only
6
registers on a stock PL061 via a check on s->rsvd_start we use
7
an "is this luminary?" check in the cases for each luminary-only
8
register.
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
Reviewed-by: Alex Bennée <alex.bennee@linaro.org>
9
Message-id: 20180521140402.23318-3-peter.maydell@linaro.org
10
---
12
---
11
include/exec/exec-all.h | 5 +++--
13
hw/gpio/pl061.c | 104 ++++++++++++++++++++++++++++++++++++------------
12
accel/tcg/translate-all.c | 2 +-
14
1 file changed, 79 insertions(+), 25 deletions(-)
13
exec.c | 2 +-
15
14
target/xtensa/op_helper.c | 3 ++-
16
diff --git a/hw/gpio/pl061.c b/hw/gpio/pl061.c
15
4 files changed, 7 insertions(+), 5 deletions(-)
16
17
diff --git a/include/exec/exec-all.h b/include/exec/exec-all.h
18
index XXXXXXX..XXXXXXX 100644
17
index XXXXXXX..XXXXXXX 100644
19
--- a/include/exec/exec-all.h
18
--- a/hw/gpio/pl061.c
20
+++ b/include/exec/exec-all.h
19
+++ b/hw/gpio/pl061.c
21
@@ -XXX,XX +XXX,XX @@ void tlb_set_page_with_attrs(CPUState *cpu, target_ulong vaddr,
20
@@ -XXX,XX +XXX,XX @@ struct PL061State {
22
void tlb_set_page(CPUState *cpu, target_ulong vaddr,
21
qemu_irq irq;
23
hwaddr paddr, int prot,
22
qemu_irq out[N_GPIOS];
24
int mmu_idx, target_ulong size);
23
const unsigned char *id;
25
-void tb_invalidate_phys_addr(AddressSpace *as, hwaddr addr);
24
- uint32_t rsvd_start; /* reserved area: [rsvd_start, 0xfcc] */
26
+void tb_invalidate_phys_addr(AddressSpace *as, hwaddr addr, MemTxAttrs attrs);
25
};
27
void probe_write(CPUArchState *env, target_ulong addr, int size, int mmu_idx,
26
28
uintptr_t retaddr);
27
static const VMStateDescription vmstate_pl061 = {
29
#else
28
@@ -XXX,XX +XXX,XX @@ static uint64_t pl061_read(void *opaque, hwaddr offset,
30
@@ -XXX,XX +XXX,XX @@ static inline void tlb_flush_by_mmuidx_all_cpus_synced(CPUState *cpu,
31
uint16_t idxmap)
32
{
29
{
30
PL061State *s = (PL061State *)opaque;
31
32
- if (offset < 0x400) {
33
- return s->data & (offset >> 2);
34
- }
35
- if (offset >= s->rsvd_start && offset <= 0xfcc) {
36
- goto err_out;
37
- }
38
- if (offset >= 0xfd0 && offset < 0x1000) {
39
- return s->id[(offset - 0xfd0) >> 2];
40
- }
41
switch (offset) {
42
+ case 0x0 ... 0x3ff: /* Data */
43
+ return s->data & (offset >> 2);
44
case 0x400: /* Direction */
45
return s->dir;
46
case 0x404: /* Interrupt sense */
47
@@ -XXX,XX +XXX,XX @@ static uint64_t pl061_read(void *opaque, hwaddr offset,
48
case 0x420: /* Alternate function select */
49
return s->afsel;
50
case 0x500: /* 2mA drive */
51
+ if (s->id != pl061_id_luminary) {
52
+ goto bad_offset;
53
+ }
54
return s->dr2r;
55
case 0x504: /* 4mA drive */
56
+ if (s->id != pl061_id_luminary) {
57
+ goto bad_offset;
58
+ }
59
return s->dr4r;
60
case 0x508: /* 8mA drive */
61
+ if (s->id != pl061_id_luminary) {
62
+ goto bad_offset;
63
+ }
64
return s->dr8r;
65
case 0x50c: /* Open drain */
66
+ if (s->id != pl061_id_luminary) {
67
+ goto bad_offset;
68
+ }
69
return s->odr;
70
case 0x510: /* Pull-up */
71
+ if (s->id != pl061_id_luminary) {
72
+ goto bad_offset;
73
+ }
74
return s->pur;
75
case 0x514: /* Pull-down */
76
+ if (s->id != pl061_id_luminary) {
77
+ goto bad_offset;
78
+ }
79
return s->pdr;
80
case 0x518: /* Slew rate control */
81
+ if (s->id != pl061_id_luminary) {
82
+ goto bad_offset;
83
+ }
84
return s->slr;
85
case 0x51c: /* Digital enable */
86
+ if (s->id != pl061_id_luminary) {
87
+ goto bad_offset;
88
+ }
89
return s->den;
90
case 0x520: /* Lock */
91
+ if (s->id != pl061_id_luminary) {
92
+ goto bad_offset;
93
+ }
94
return s->locked;
95
case 0x524: /* Commit */
96
+ if (s->id != pl061_id_luminary) {
97
+ goto bad_offset;
98
+ }
99
return s->cr;
100
case 0x528: /* Analog mode select */
101
+ if (s->id != pl061_id_luminary) {
102
+ goto bad_offset;
103
+ }
104
return s->amsel;
105
+ case 0xfd0 ... 0xfff: /* ID registers */
106
+ return s->id[(offset - 0xfd0) >> 2];
107
default:
108
+ bad_offset:
109
+ qemu_log_mask(LOG_GUEST_ERROR,
110
+ "pl061_read: Bad offset %x\n", (int)offset);
111
break;
112
}
113
-err_out:
114
- qemu_log_mask(LOG_GUEST_ERROR,
115
- "pl061_read: Bad offset %x\n", (int)offset);
116
return 0;
33
}
117
}
34
-static inline void tb_invalidate_phys_addr(AddressSpace *as, hwaddr addr)
118
35
+static inline void tb_invalidate_phys_addr(AddressSpace *as, hwaddr addr,
119
@@ -XXX,XX +XXX,XX @@ static void pl061_write(void *opaque, hwaddr offset,
36
+ MemTxAttrs attrs)
120
PL061State *s = (PL061State *)opaque;
37
{
121
uint8_t mask;
122
123
- if (offset < 0x400) {
124
+ switch (offset) {
125
+ case 0 ... 0x3ff:
126
mask = (offset >> 2) & s->dir;
127
s->data = (s->data & ~mask) | (value & mask);
128
pl061_update(s);
129
return;
130
- }
131
- if (offset >= s->rsvd_start) {
132
- goto err_out;
133
- }
134
- switch (offset) {
135
case 0x400: /* Direction */
136
s->dir = value & 0xff;
137
break;
138
@@ -XXX,XX +XXX,XX @@ static void pl061_write(void *opaque, hwaddr offset,
139
s->afsel = (s->afsel & ~mask) | (value & mask);
140
break;
141
case 0x500: /* 2mA drive */
142
+ if (s->id != pl061_id_luminary) {
143
+ goto bad_offset;
144
+ }
145
s->dr2r = value & 0xff;
146
break;
147
case 0x504: /* 4mA drive */
148
+ if (s->id != pl061_id_luminary) {
149
+ goto bad_offset;
150
+ }
151
s->dr4r = value & 0xff;
152
break;
153
case 0x508: /* 8mA drive */
154
+ if (s->id != pl061_id_luminary) {
155
+ goto bad_offset;
156
+ }
157
s->dr8r = value & 0xff;
158
break;
159
case 0x50c: /* Open drain */
160
+ if (s->id != pl061_id_luminary) {
161
+ goto bad_offset;
162
+ }
163
s->odr = value & 0xff;
164
break;
165
case 0x510: /* Pull-up */
166
+ if (s->id != pl061_id_luminary) {
167
+ goto bad_offset;
168
+ }
169
s->pur = value & 0xff;
170
break;
171
case 0x514: /* Pull-down */
172
+ if (s->id != pl061_id_luminary) {
173
+ goto bad_offset;
174
+ }
175
s->pdr = value & 0xff;
176
break;
177
case 0x518: /* Slew rate control */
178
+ if (s->id != pl061_id_luminary) {
179
+ goto bad_offset;
180
+ }
181
s->slr = value & 0xff;
182
break;
183
case 0x51c: /* Digital enable */
184
+ if (s->id != pl061_id_luminary) {
185
+ goto bad_offset;
186
+ }
187
s->den = value & 0xff;
188
break;
189
case 0x520: /* Lock */
190
+ if (s->id != pl061_id_luminary) {
191
+ goto bad_offset;
192
+ }
193
s->locked = (value != 0xacce551);
194
break;
195
case 0x524: /* Commit */
196
+ if (s->id != pl061_id_luminary) {
197
+ goto bad_offset;
198
+ }
199
if (!s->locked)
200
s->cr = value & 0xff;
201
break;
202
case 0x528:
203
+ if (s->id != pl061_id_luminary) {
204
+ goto bad_offset;
205
+ }
206
s->amsel = value & 0xff;
207
break;
208
default:
209
- goto err_out;
210
+ bad_offset:
211
+ qemu_log_mask(LOG_GUEST_ERROR,
212
+ "pl061_write: Bad offset %x\n", (int)offset);
213
+ return;
214
}
215
pl061_update(s);
216
return;
217
-err_out:
218
- qemu_log_mask(LOG_GUEST_ERROR,
219
- "pl061_write: Bad offset %x\n", (int)offset);
38
}
220
}
39
#endif
221
40
diff --git a/accel/tcg/translate-all.c b/accel/tcg/translate-all.c
222
static void pl061_reset(DeviceState *dev)
41
index XXXXXXX..XXXXXXX 100644
223
@@ -XXX,XX +XXX,XX @@ static void pl061_luminary_init(Object *obj)
42
--- a/accel/tcg/translate-all.c
224
PL061State *s = PL061(obj);
43
+++ b/accel/tcg/translate-all.c
225
44
@@ -XXX,XX +XXX,XX @@ static TranslationBlock *tb_find_pc(uintptr_t tc_ptr)
226
s->id = pl061_id_luminary;
227
- s->rsvd_start = 0x52c;
45
}
228
}
46
229
47
#if !defined(CONFIG_USER_ONLY)
230
static void pl061_init(Object *obj)
48
-void tb_invalidate_phys_addr(AddressSpace *as, hwaddr addr)
231
@@ -XXX,XX +XXX,XX @@ static void pl061_init(Object *obj)
49
+void tb_invalidate_phys_addr(AddressSpace *as, hwaddr addr, MemTxAttrs attrs)
232
SysBusDevice *sbd = SYS_BUS_DEVICE(obj);
50
{
233
51
ram_addr_t ram_addr;
234
s->id = pl061_id;
52
MemoryRegion *mr;
235
- s->rsvd_start = 0x424;
53
diff --git a/exec.c b/exec.c
236
54
index XXXXXXX..XXXXXXX 100644
237
memory_region_init_io(&s->iomem, obj, &pl061_ops, s, "pl061", 0x1000);
55
--- a/exec.c
238
sysbus_init_mmio(sbd, &s->iomem);
56
+++ b/exec.c
57
@@ -XXX,XX +XXX,XX @@ static void breakpoint_invalidate(CPUState *cpu, target_ulong pc)
58
if (phys != -1) {
59
/* Locks grabbed by tb_invalidate_phys_addr */
60
tb_invalidate_phys_addr(cpu->cpu_ases[asidx].as,
61
- phys | (pc & ~TARGET_PAGE_MASK));
62
+ phys | (pc & ~TARGET_PAGE_MASK), attrs);
63
}
64
}
65
#endif
66
diff --git a/target/xtensa/op_helper.c b/target/xtensa/op_helper.c
67
index XXXXXXX..XXXXXXX 100644
68
--- a/target/xtensa/op_helper.c
69
+++ b/target/xtensa/op_helper.c
70
@@ -XXX,XX +XXX,XX @@ static void tb_invalidate_virtual_addr(CPUXtensaState *env, uint32_t vaddr)
71
int ret = xtensa_get_physical_addr(env, false, vaddr, 2, 0,
72
&paddr, &page_size, &access);
73
if (ret == 0) {
74
- tb_invalidate_phys_addr(&address_space_memory, paddr);
75
+ tb_invalidate_phys_addr(&address_space_memory, paddr,
76
+ MEMTXATTRS_UNSPECIFIED);
77
}
78
}
79
80
--
239
--
81
2.17.1
240
2.20.1
82
241
83
242
diff view generated by jsdifflib
1
As part of plumbing MemTxAttrs down to the IOMMU translate method,
1
Add tracepoints for reads and writes to the PL061 registers. This requires
2
add MemTxAttrs as an argument to flatview_translate(); all its
2
restructuring pl061_read() to only return after the tracepoint, rather
3
callers now have attrs available.
3
than having lots of early-returns.
4
4
5
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
5
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
6
Reviewed-by: Alex Bennée <alex.bennee@linaro.org>
6
Reviewed-by: Philippe Mathieu-Daudé <f4bug@amsat.org>
7
Reviewed-by: Richard Henderson <richard.henderson@linaro.org>
7
Reviewed-by: Richard Henderson <richard.henderson@linaro.org>
8
Message-id: 20180521140402.23318-11-peter.maydell@linaro.org
9
---
8
---
10
include/exec/memory.h | 7 ++++---
9
hw/gpio/pl061.c | 70 ++++++++++++++++++++++++++++++--------------
11
exec.c | 17 +++++++++--------
10
hw/gpio/trace-events | 2 ++
12
2 files changed, 13 insertions(+), 11 deletions(-)
11
2 files changed, 50 insertions(+), 22 deletions(-)
13
12
14
diff --git a/include/exec/memory.h b/include/exec/memory.h
13
diff --git a/hw/gpio/pl061.c b/hw/gpio/pl061.c
15
index XXXXXXX..XXXXXXX 100644
14
index XXXXXXX..XXXXXXX 100644
16
--- a/include/exec/memory.h
15
--- a/hw/gpio/pl061.c
17
+++ b/include/exec/memory.h
16
+++ b/hw/gpio/pl061.c
18
@@ -XXX,XX +XXX,XX @@ IOMMUTLBEntry address_space_get_iotlb_entry(AddressSpace *as, hwaddr addr,
17
@@ -XXX,XX +XXX,XX @@ static uint64_t pl061_read(void *opaque, hwaddr offset,
19
*/
18
unsigned size)
20
MemoryRegion *flatview_translate(FlatView *fv,
21
hwaddr addr, hwaddr *xlat,
22
- hwaddr *len, bool is_write);
23
+ hwaddr *len, bool is_write,
24
+ MemTxAttrs attrs);
25
26
static inline MemoryRegion *address_space_translate(AddressSpace *as,
27
hwaddr addr, hwaddr *xlat,
28
@@ -XXX,XX +XXX,XX @@ static inline MemoryRegion *address_space_translate(AddressSpace *as,
29
MemTxAttrs attrs)
30
{
19
{
31
return flatview_translate(address_space_to_flatview(as),
20
PL061State *s = (PL061State *)opaque;
32
- addr, xlat, len, is_write);
21
+ uint64_t r = 0;
33
+ addr, xlat, len, is_write, attrs);
22
23
switch (offset) {
24
case 0x0 ... 0x3ff: /* Data */
25
- return s->data & (offset >> 2);
26
+ r = s->data & (offset >> 2);
27
+ break;
28
case 0x400: /* Direction */
29
- return s->dir;
30
+ r = s->dir;
31
+ break;
32
case 0x404: /* Interrupt sense */
33
- return s->isense;
34
+ r = s->isense;
35
+ break;
36
case 0x408: /* Interrupt both edges */
37
- return s->ibe;
38
+ r = s->ibe;
39
+ break;
40
case 0x40c: /* Interrupt event */
41
- return s->iev;
42
+ r = s->iev;
43
+ break;
44
case 0x410: /* Interrupt mask */
45
- return s->im;
46
+ r = s->im;
47
+ break;
48
case 0x414: /* Raw interrupt status */
49
- return s->istate;
50
+ r = s->istate;
51
+ break;
52
case 0x418: /* Masked interrupt status */
53
- return s->istate & s->im;
54
+ r = s->istate & s->im;
55
+ break;
56
case 0x420: /* Alternate function select */
57
- return s->afsel;
58
+ r = s->afsel;
59
+ break;
60
case 0x500: /* 2mA drive */
61
if (s->id != pl061_id_luminary) {
62
goto bad_offset;
63
}
64
- return s->dr2r;
65
+ r = s->dr2r;
66
+ break;
67
case 0x504: /* 4mA drive */
68
if (s->id != pl061_id_luminary) {
69
goto bad_offset;
70
}
71
- return s->dr4r;
72
+ r = s->dr4r;
73
+ break;
74
case 0x508: /* 8mA drive */
75
if (s->id != pl061_id_luminary) {
76
goto bad_offset;
77
}
78
- return s->dr8r;
79
+ r = s->dr8r;
80
+ break;
81
case 0x50c: /* Open drain */
82
if (s->id != pl061_id_luminary) {
83
goto bad_offset;
84
}
85
- return s->odr;
86
+ r = s->odr;
87
+ break;
88
case 0x510: /* Pull-up */
89
if (s->id != pl061_id_luminary) {
90
goto bad_offset;
91
}
92
- return s->pur;
93
+ r = s->pur;
94
+ break;
95
case 0x514: /* Pull-down */
96
if (s->id != pl061_id_luminary) {
97
goto bad_offset;
98
}
99
- return s->pdr;
100
+ r = s->pdr;
101
+ break;
102
case 0x518: /* Slew rate control */
103
if (s->id != pl061_id_luminary) {
104
goto bad_offset;
105
}
106
- return s->slr;
107
+ r = s->slr;
108
+ break;
109
case 0x51c: /* Digital enable */
110
if (s->id != pl061_id_luminary) {
111
goto bad_offset;
112
}
113
- return s->den;
114
+ r = s->den;
115
+ break;
116
case 0x520: /* Lock */
117
if (s->id != pl061_id_luminary) {
118
goto bad_offset;
119
}
120
- return s->locked;
121
+ r = s->locked;
122
+ break;
123
case 0x524: /* Commit */
124
if (s->id != pl061_id_luminary) {
125
goto bad_offset;
126
}
127
- return s->cr;
128
+ r = s->cr;
129
+ break;
130
case 0x528: /* Analog mode select */
131
if (s->id != pl061_id_luminary) {
132
goto bad_offset;
133
}
134
- return s->amsel;
135
+ r = s->amsel;
136
+ break;
137
case 0xfd0 ... 0xfff: /* ID registers */
138
- return s->id[(offset - 0xfd0) >> 2];
139
+ r = s->id[(offset - 0xfd0) >> 2];
140
+ break;
141
default:
142
bad_offset:
143
qemu_log_mask(LOG_GUEST_ERROR,
144
"pl061_read: Bad offset %x\n", (int)offset);
145
break;
146
}
147
- return 0;
148
+
149
+ trace_pl061_read(DEVICE(s)->canonical_path, offset, r);
150
+ return r;
34
}
151
}
35
152
36
/* address_space_access_valid: check for validity of accessing an address
153
static void pl061_write(void *opaque, hwaddr offset,
37
@@ -XXX,XX +XXX,XX @@ MemTxResult address_space_read(AddressSpace *as, hwaddr addr,
154
@@ -XXX,XX +XXX,XX @@ static void pl061_write(void *opaque, hwaddr offset,
38
rcu_read_lock();
155
PL061State *s = (PL061State *)opaque;
39
fv = address_space_to_flatview(as);
156
uint8_t mask;
40
l = len;
157
41
- mr = flatview_translate(fv, addr, &addr1, &l, false);
158
+ trace_pl061_write(DEVICE(s)->canonical_path, offset, value);
42
+ mr = flatview_translate(fv, addr, &addr1, &l, false, attrs);
159
+
43
if (len == l && memory_access_is_direct(mr, false)) {
160
switch (offset) {
44
ptr = qemu_map_ram_ptr(mr->ram_block, addr1);
161
case 0 ... 0x3ff:
45
memcpy(buf, ptr, len);
162
mask = (offset >> 2) & s->dir;
46
diff --git a/exec.c b/exec.c
163
diff --git a/hw/gpio/trace-events b/hw/gpio/trace-events
47
index XXXXXXX..XXXXXXX 100644
164
index XXXXXXX..XXXXXXX 100644
48
--- a/exec.c
165
--- a/hw/gpio/trace-events
49
+++ b/exec.c
166
+++ b/hw/gpio/trace-events
50
@@ -XXX,XX +XXX,XX @@ iotlb_fail:
167
@@ -XXX,XX +XXX,XX @@ pl061_update(const char *id, uint32_t dir, uint32_t data) "%s GPIODIR 0x%x GPIOD
51
168
pl061_set_output(const char *id, int gpio, int level) "%s setting output %d to %d"
52
/* Called from RCU critical section */
169
pl061_input_change(const char *id, int gpio, int level) "%s input %d changed to %d"
53
MemoryRegion *flatview_translate(FlatView *fv, hwaddr addr, hwaddr *xlat,
170
pl061_update_istate(const char *id, uint32_t istate, uint32_t im, int level) "%s GPIORIS 0x%x GPIOIE 0x%x interrupt level %d"
54
- hwaddr *plen, bool is_write)
171
+pl061_read(const char *id, uint64_t offset, uint64_t r) "%s offset 0x%" PRIx64 " value 0x%" PRIx64
55
+ hwaddr *plen, bool is_write,
172
+pl061_write(const char *id, uint64_t offset, uint64_t value) "%s offset 0x%" PRIx64 " value 0x%" PRIx64
56
+ MemTxAttrs attrs)
173
57
{
174
# sifive_gpio.c
58
MemoryRegion *mr;
175
sifive_gpio_read(uint64_t offset, uint64_t r) "offset 0x%" PRIx64 " value 0x%" PRIx64
59
MemoryRegionSection section;
60
@@ -XXX,XX +XXX,XX @@ static MemTxResult flatview_write_continue(FlatView *fv, hwaddr addr,
61
}
62
63
l = len;
64
- mr = flatview_translate(fv, addr, &addr1, &l, true);
65
+ mr = flatview_translate(fv, addr, &addr1, &l, true, attrs);
66
}
67
68
return result;
69
@@ -XXX,XX +XXX,XX @@ static MemTxResult flatview_write(FlatView *fv, hwaddr addr, MemTxAttrs attrs,
70
MemTxResult result = MEMTX_OK;
71
72
l = len;
73
- mr = flatview_translate(fv, addr, &addr1, &l, true);
74
+ mr = flatview_translate(fv, addr, &addr1, &l, true, attrs);
75
result = flatview_write_continue(fv, addr, attrs, buf, len,
76
addr1, l, mr);
77
78
@@ -XXX,XX +XXX,XX @@ MemTxResult flatview_read_continue(FlatView *fv, hwaddr addr,
79
}
80
81
l = len;
82
- mr = flatview_translate(fv, addr, &addr1, &l, false);
83
+ mr = flatview_translate(fv, addr, &addr1, &l, false, attrs);
84
}
85
86
return result;
87
@@ -XXX,XX +XXX,XX @@ static MemTxResult flatview_read(FlatView *fv, hwaddr addr,
88
MemoryRegion *mr;
89
90
l = len;
91
- mr = flatview_translate(fv, addr, &addr1, &l, false);
92
+ mr = flatview_translate(fv, addr, &addr1, &l, false, attrs);
93
return flatview_read_continue(fv, addr, attrs, buf, len,
94
addr1, l, mr);
95
}
96
@@ -XXX,XX +XXX,XX @@ static bool flatview_access_valid(FlatView *fv, hwaddr addr, int len,
97
98
while (len > 0) {
99
l = len;
100
- mr = flatview_translate(fv, addr, &xlat, &l, is_write);
101
+ mr = flatview_translate(fv, addr, &xlat, &l, is_write, attrs);
102
if (!memory_access_is_direct(mr, is_write)) {
103
l = memory_access_size(mr, l, addr);
104
if (!memory_region_access_valid(mr, xlat, l, is_write, attrs)) {
105
@@ -XXX,XX +XXX,XX @@ flatview_extend_translation(FlatView *fv, hwaddr addr,
106
107
len = target_len;
108
this_mr = flatview_translate(fv, addr, &xlat,
109
- &len, is_write);
110
+ &len, is_write, attrs);
111
if (this_mr != mr || xlat != base + done) {
112
return done;
113
}
114
@@ -XXX,XX +XXX,XX @@ void *address_space_map(AddressSpace *as,
115
l = len;
116
rcu_read_lock();
117
fv = address_space_to_flatview(as);
118
- mr = flatview_translate(fv, addr, &xlat, &l, is_write);
119
+ mr = flatview_translate(fv, addr, &xlat, &l, is_write, attrs);
120
121
if (!memory_access_is_direct(mr, is_write)) {
122
if (atomic_xchg(&bounce.in_use, true)) {
123
--
176
--
124
2.17.1
177
2.20.1
125
178
126
179
diff view generated by jsdifflib
1
The FRECPX instructions should (like most other floating point operations)
1
Add a comment documenting the "QEMU interface" of this device:
2
honour the FPCR.FZ bit which specifies whether input denormals should
2
which MMIO regions, IRQ lines, GPIO lines, etc it exposes.
3
be flushed to zero (or FZ16 for the half-precision version).
4
We forgot to implement this, which doesn't affect the results (since
5
the calculation doesn't actually care about the mantissa bits) but did
6
mean we were failing to set the FPSR.IDC bit.
7
3
8
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
4
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
9
Reviewed-by: Richard Henderson <richard.henderson@linaro.org>
5
Reviewed-by: Richard Henderson <richard.henderson@linaro.org>
10
Message-id: 20180521172712.19930-1-peter.maydell@linaro.org
11
---
6
---
12
target/arm/helper-a64.c | 6 ++++++
7
hw/gpio/pl061.c | 7 +++++++
13
1 file changed, 6 insertions(+)
8
1 file changed, 7 insertions(+)
14
9
15
diff --git a/target/arm/helper-a64.c b/target/arm/helper-a64.c
10
diff --git a/hw/gpio/pl061.c b/hw/gpio/pl061.c
16
index XXXXXXX..XXXXXXX 100644
11
index XXXXXXX..XXXXXXX 100644
17
--- a/target/arm/helper-a64.c
12
--- a/hw/gpio/pl061.c
18
+++ b/target/arm/helper-a64.c
13
+++ b/hw/gpio/pl061.c
19
@@ -XXX,XX +XXX,XX @@ float16 HELPER(frecpx_f16)(float16 a, void *fpstp)
14
@@ -XXX,XX +XXX,XX @@
20
return nan;
15
* Written by Paul Brook
21
}
16
*
22
17
* This code is licensed under the GPL.
23
+ a = float16_squash_input_denormal(a, fpst);
18
+ *
24
+
19
+ * QEMU interface:
25
val16 = float16_val(a);
20
+ * + sysbus MMIO region 0: the device registers
26
sbit = 0x8000 & val16;
21
+ * + sysbus IRQ: the GPIOINTR interrupt line
27
exp = extract32(val16, 10, 5);
22
+ * + unnamed GPIO inputs 0..7: inputs to connect to the emulated GPIO lines
28
@@ -XXX,XX +XXX,XX @@ float32 HELPER(frecpx_f32)(float32 a, void *fpstp)
23
+ * + unnamed GPIO outputs 0..7: the emulated GPIO lines, considered as
29
return nan;
24
+ * outputs
30
}
25
*/
31
26
32
+ a = float32_squash_input_denormal(a, fpst);
27
#include "qemu/osdep.h"
33
+
34
val32 = float32_val(a);
35
sbit = 0x80000000ULL & val32;
36
exp = extract32(val32, 23, 8);
37
@@ -XXX,XX +XXX,XX @@ float64 HELPER(frecpx_f64)(float64 a, void *fpstp)
38
return nan;
39
}
40
41
+ a = float64_squash_input_denormal(a, fpst);
42
+
43
val64 = float64_val(a);
44
sbit = 0x8000000000000000ULL & val64;
45
exp = extract64(float64_val(a), 52, 11);
46
--
28
--
47
2.17.1
29
2.20.1
48
30
49
31
diff view generated by jsdifflib
1
Add more detail to the documentation for memory_region_init_iommu()
1
The Luminary variant of the PL061 has registers GPIOPUR and GPIOPDR
2
and other IOMMU-related functions and data structures.
2
which lets the guest configure whether the GPIO lines are pull-up,
3
pull-down, or truly floating. Instead of assuming all lines are pulled
4
high, honour the PUR and PDR registers.
5
6
For the plain PL061, continue to assume that lines have an external
7
pull-up resistor, as we did before.
8
9
The stellaris board actually relies on this behaviour -- the CD line
10
of the ssd0323 display device is connected to GPIO output C7, and it
11
is only because of a different bug which we're about to fix that we
12
weren't incorrectly driving this line high on reset and putting the
13
ssd0323 into data mode.
3
14
4
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
15
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
5
Reviewed-by: Richard Henderson <richard.henderson@linaro.org>
16
Reviewed-by: Richard Henderson <richard.henderson@linaro.org>
6
Reviewed-by: Alex Bennée <alex.bennee@linaro.org>
7
Reviewed-by: Eric Auger <eric.auger@redhat.com>
8
Message-id: 20180521140402.23318-2-peter.maydell@linaro.org
9
---
17
---
10
include/exec/memory.h | 105 ++++++++++++++++++++++++++++++++++++++----
18
hw/gpio/pl061.c | 58 +++++++++++++++++++++++++++++++++++++++++---
11
1 file changed, 95 insertions(+), 10 deletions(-)
19
hw/gpio/trace-events | 2 +-
20
2 files changed, 55 insertions(+), 5 deletions(-)
12
21
13
diff --git a/include/exec/memory.h b/include/exec/memory.h
22
diff --git a/hw/gpio/pl061.c b/hw/gpio/pl061.c
14
index XXXXXXX..XXXXXXX 100644
23
index XXXXXXX..XXXXXXX 100644
15
--- a/include/exec/memory.h
24
--- a/hw/gpio/pl061.c
16
+++ b/include/exec/memory.h
25
+++ b/hw/gpio/pl061.c
17
@@ -XXX,XX +XXX,XX @@ enum IOMMUMemoryRegionAttr {
26
@@ -XXX,XX +XXX,XX @@ static const VMStateDescription vmstate_pl061 = {
18
IOMMU_ATTR_SPAPR_TCE_FD
27
}
19
};
28
};
20
29
21
+/**
30
+static uint8_t pl061_floating(PL061State *s)
22
+ * IOMMUMemoryRegionClass:
31
+{
23
+ *
32
+ /*
24
+ * All IOMMU implementations need to subclass TYPE_IOMMU_MEMORY_REGION
33
+ * Return mask of bits which correspond to pins configured as inputs
25
+ * and provide an implementation of at least the @translate method here
34
+ * and which are floating (neither pulled up to 1 nor down to 0).
26
+ * to handle requests to the memory region. Other methods are optional.
27
+ *
28
+ * The IOMMU implementation must use the IOMMU notifier infrastructure
29
+ * to report whenever mappings are changed, by calling
30
+ * memory_region_notify_iommu() (or, if necessary, by calling
31
+ * memory_region_notify_one() for each registered notifier).
32
+ */
33
typedef struct IOMMUMemoryRegionClass {
34
/* private */
35
struct DeviceClass parent_class;
36
37
/*
38
- * Return a TLB entry that contains a given address. Flag should
39
- * be the access permission of this translation operation. We can
40
- * set flag to IOMMU_NONE to mean that we don't need any
41
- * read/write permission checks, like, when for region replay.
42
+ * Return a TLB entry that contains a given address.
43
+ *
44
+ * The IOMMUAccessFlags indicated via @flag are optional and may
45
+ * be specified as IOMMU_NONE to indicate that the caller needs
46
+ * the full translation information for both reads and writes. If
47
+ * the access flags are specified then the IOMMU implementation
48
+ * may use this as an optimization, to stop doing a page table
49
+ * walk as soon as it knows that the requested permissions are not
50
+ * allowed. If IOMMU_NONE is passed then the IOMMU must do the
51
+ * full page table walk and report the permissions in the returned
52
+ * IOMMUTLBEntry. (Note that this implies that an IOMMU may not
53
+ * return different mappings for reads and writes.)
54
+ *
55
+ * The returned information remains valid while the caller is
56
+ * holding the big QEMU lock or is inside an RCU critical section;
57
+ * if the caller wishes to cache the mapping beyond that it must
58
+ * register an IOMMU notifier so it can invalidate its cached
59
+ * information when the IOMMU mapping changes.
60
+ *
61
+ * @iommu: the IOMMUMemoryRegion
62
+ * @hwaddr: address to be translated within the memory region
63
+ * @flag: requested access permissions
64
*/
65
IOMMUTLBEntry (*translate)(IOMMUMemoryRegion *iommu, hwaddr addr,
66
IOMMUAccessFlags flag);
67
- /* Returns minimum supported page size */
68
+ /* Returns minimum supported page size in bytes.
69
+ * If this method is not provided then the minimum is assumed to
70
+ * be TARGET_PAGE_SIZE.
71
+ *
72
+ * @iommu: the IOMMUMemoryRegion
73
+ */
35
+ */
74
uint64_t (*get_min_page_size)(IOMMUMemoryRegion *iommu);
36
+ uint8_t floating;
75
- /* Called when IOMMU Notifier flag changed */
37
+
76
+ /* Called when IOMMU Notifier flag changes (ie when the set of
38
+ if (s->id == pl061_id_luminary) {
77
+ * events which IOMMU users are requesting notification for changes).
39
+ /*
78
+ * Optional method -- need not be provided if the IOMMU does not
40
+ * If both PUR and PDR bits are clear, there is neither a pullup
79
+ * need to know exactly which events must be notified.
41
+ * nor a pulldown in place, and the output truly floats.
80
+ *
42
+ */
81
+ * @iommu: the IOMMUMemoryRegion
43
+ floating = ~(s->pur | s->pdr);
82
+ * @old_flags: events which previously needed to be notified
44
+ } else {
83
+ * @new_flags: events which now need to be notified
45
+ /* Assume outputs are pulled high. FIXME: this is board dependent. */
46
+ floating = 0;
47
+ }
48
+ return floating & ~s->dir;
49
+}
50
+
51
+static uint8_t pl061_pullups(PL061State *s)
52
+{
53
+ /*
54
+ * Return mask of bits which correspond to pins configured as inputs
55
+ * and which are pulled up to 1.
84
+ */
56
+ */
85
void (*notify_flag_changed)(IOMMUMemoryRegion *iommu,
57
+ uint8_t pullups;
86
IOMMUNotifierFlag old_flags,
58
+
87
IOMMUNotifierFlag new_flags);
59
+ if (s->id == pl061_id_luminary) {
88
- /* Set this up to provide customized IOMMU replay function */
60
+ /*
89
+ /* Called to handle memory_region_iommu_replay().
61
+ * The Luminary variant of the PL061 has an extra registers which
90
+ *
62
+ * the guest can use to configure whether lines should be pullup
91
+ * The default implementation of memory_region_iommu_replay() is to
63
+ * or pulldown.
92
+ * call the IOMMU translate method for every page in the address space
64
+ */
93
+ * with flag == IOMMU_NONE and then call the notifier if translate
65
+ pullups = s->pur;
94
+ * returns a valid mapping. If this method is implemented then it
66
+ } else {
95
+ * overrides the default behaviour, and must provide the full semantics
67
+ /* Assume outputs are pulled high. FIXME: this is board dependent. */
96
+ * of memory_region_iommu_replay(), by calling @notifier for every
68
+ pullups = 0xff;
97
+ * translation present in the IOMMU.
69
+ }
98
+ *
70
+ return pullups & ~s->dir;
99
+ * Optional method -- an IOMMU only needs to provide this method
71
+}
100
+ * if the default is inefficient or produces undesirable side effects.
72
+
101
+ *
73
static void pl061_update(PL061State *s)
102
+ * Note: this is not related to record-and-replay functionality.
74
{
75
uint8_t changed;
76
uint8_t mask;
77
uint8_t out;
78
int i;
79
+ uint8_t pullups = pl061_pullups(s);
80
+ uint8_t floating = pl061_floating(s);
81
82
- trace_pl061_update(DEVICE(s)->canonical_path, s->dir, s->data);
83
+ trace_pl061_update(DEVICE(s)->canonical_path, s->dir, s->data,
84
+ pullups, floating);
85
86
- /* Outputs float high. */
87
- /* FIXME: This is board dependent. */
88
- out = (s->data & s->dir) | ~s->dir;
89
+ /*
90
+ * Pins configured as output are driven from the data register;
91
+ * otherwise if they're pulled up they're 1, and if they're floating
92
+ * then we give them the same value they had previously, so we don't
93
+ * report any change to the other end.
103
+ */
94
+ */
104
void (*replay)(IOMMUMemoryRegion *iommu, IOMMUNotifier *notifier);
95
+ out = (s->data & s->dir) | pullups | (s->old_out_data & floating);
105
96
changed = s->old_out_data ^ out;
106
- /* Get IOMMU misc attributes */
97
if (changed) {
107
- int (*get_attr)(IOMMUMemoryRegion *iommu, enum IOMMUMemoryRegionAttr,
98
s->old_out_data = out;
108
+ /* Get IOMMU misc attributes. This is an optional method that
99
diff --git a/hw/gpio/trace-events b/hw/gpio/trace-events
109
+ * can be used to allow users of the IOMMU to get implementation-specific
100
index XXXXXXX..XXXXXXX 100644
110
+ * information. The IOMMU implements this method to handle calls
101
--- a/hw/gpio/trace-events
111
+ * by IOMMU users to memory_region_iommu_get_attr() by filling in
102
+++ b/hw/gpio/trace-events
112
+ * the arbitrary data pointer for any IOMMUMemoryRegionAttr values that
103
@@ -XXX,XX +XXX,XX @@ nrf51_gpio_set(int64_t line, int64_t value) "line %" PRIi64 " value %" PRIi64
113
+ * the IOMMU supports. If the method is unimplemented then
104
nrf51_gpio_update_output_irq(int64_t line, int64_t value) "line %" PRIi64 " value %" PRIi64
114
+ * memory_region_iommu_get_attr() will always return -EINVAL.
105
115
+ *
106
# pl061.c
116
+ * @iommu: the IOMMUMemoryRegion
107
-pl061_update(const char *id, uint32_t dir, uint32_t data) "%s GPIODIR 0x%x GPIODATA 0x%x"
117
+ * @attr: attribute being queried
108
+pl061_update(const char *id, uint32_t dir, uint32_t data, uint32_t pullups, uint32_t floating) "%s GPIODIR 0x%x GPIODATA 0x%x pullups 0x%x floating 0x%x"
118
+ * @data: memory to fill in with the attribute data
109
pl061_set_output(const char *id, int gpio, int level) "%s setting output %d to %d"
119
+ *
110
pl061_input_change(const char *id, int gpio, int level) "%s input %d changed to %d"
120
+ * Returns 0 on success, or a negative errno; in particular
111
pl061_update_istate(const char *id, uint32_t istate, uint32_t im, int level) "%s GPIORIS 0x%x GPIOIE 0x%x interrupt level %d"
121
+ * returns -EINVAL for unrecognized or unimplemented attribute types.
122
+ */
123
+ int (*get_attr)(IOMMUMemoryRegion *iommu, enum IOMMUMemoryRegionAttr attr,
124
void *data);
125
} IOMMUMemoryRegionClass;
126
127
@@ -XXX,XX +XXX,XX @@ static inline void memory_region_init_reservation(MemoryRegion *mr,
128
* An IOMMU region translates addresses and forwards accesses to a target
129
* memory region.
130
*
131
+ * The IOMMU implementation must define a subclass of TYPE_IOMMU_MEMORY_REGION.
132
+ * @_iommu_mr should be a pointer to enough memory for an instance of
133
+ * that subclass, @instance_size is the size of that subclass, and
134
+ * @mrtypename is its name. This function will initialize @_iommu_mr as an
135
+ * instance of the subclass, and its methods will then be called to handle
136
+ * accesses to the memory region. See the documentation of
137
+ * #IOMMUMemoryRegionClass for further details.
138
+ *
139
* @_iommu_mr: the #IOMMUMemoryRegion to be initialized
140
* @instance_size: the IOMMUMemoryRegion subclass instance size
141
* @mrtypename: the type name of the #IOMMUMemoryRegion
142
@@ -XXX,XX +XXX,XX @@ void memory_region_register_iommu_notifier(MemoryRegion *mr,
143
* a notifier with the minimum page granularity returned by
144
* mr->iommu_ops->get_page_size().
145
*
146
+ * Note: this is not related to record-and-replay functionality.
147
+ *
148
* @iommu_mr: the memory region to observe
149
* @n: the notifier to which to replay iommu mappings
150
*/
151
@@ -XXX,XX +XXX,XX @@ void memory_region_iommu_replay(IOMMUMemoryRegion *iommu_mr, IOMMUNotifier *n);
152
* memory_region_iommu_replay_all: replay existing IOMMU translations
153
* to all the notifiers registered.
154
*
155
+ * Note: this is not related to record-and-replay functionality.
156
+ *
157
* @iommu_mr: the memory region to observe
158
*/
159
void memory_region_iommu_replay_all(IOMMUMemoryRegion *iommu_mr);
160
@@ -XXX,XX +XXX,XX @@ void memory_region_unregister_iommu_notifier(MemoryRegion *mr,
161
* memory_region_iommu_get_attr: return an IOMMU attr if get_attr() is
162
* defined on the IOMMU.
163
*
164
- * Returns 0 if succeded, error code otherwise.
165
+ * Returns 0 on success, or a negative errno otherwise. In particular,
166
+ * -EINVAL indicates that the IOMMU does not support the requested
167
+ * attribute.
168
*
169
* @iommu_mr: the memory region
170
* @attr: the requested attribute
171
--
112
--
172
2.17.1
113
2.20.1
173
114
174
115
diff view generated by jsdifflib
1
As part of plumbing MemTxAttrs down to the IOMMU translate method,
1
The PL061 GPIO does not itself include pullup or pulldown resistors
2
add MemTxAttrs as an argument to address_space_map().
2
to set the value of a GPIO line treated as an output when it is
3
Its callers either have an attrs value to hand, or don't care
3
configured as an input (ie when the PL061 itself is not driving it).
4
and can use MEMTXATTRS_UNSPECIFIED.
4
In real hardware it is up to the board to add suitable pullups or
5
pulldowns. Currently our implementation hardwires this to "outputs
6
pulled high", which is correct for some boards (eg the realview ones:
7
see figure 3-29 in the "RealView Platform Baseboard for ARM926EJ-S
8
User Guide" DUI0224I), but wrong for others.
9
10
In particular, the wiring in the 'virt' board and the gpio-pwr device
11
assumes that wires should be pulled low, because otherwise the
12
pull-to-high will trigger a shutdown or reset action. (The only
13
reason this doesn't happen immediately on startup is due to another
14
bug in the PL061, where we don't assert the GPIOs to the correct
15
value on reset, but will do so as soon as the guest touches a
16
register and pl061_update() gets called.)
17
18
Add properties to the pl061 so the board can configure whether it
19
wants GPIO lines to have pullup, pulldown, or neither.
5
20
6
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
21
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
7
Reviewed-by: Alex Bennée <alex.bennee@linaro.org>
8
Reviewed-by: Richard Henderson <richard.henderson@linaro.org>
22
Reviewed-by: Richard Henderson <richard.henderson@linaro.org>
9
Message-id: 20180521140402.23318-5-peter.maydell@linaro.org
10
---
23
---
11
include/exec/memory.h | 3 ++-
24
hw/gpio/pl061.c | 51 +++++++++++++++++++++++++++++++++++++++++++++----
12
include/sysemu/dma.h | 3 ++-
25
1 file changed, 47 insertions(+), 4 deletions(-)
13
exec.c | 6 ++++--
14
target/ppc/mmu-hash64.c | 3 ++-
15
4 files changed, 10 insertions(+), 5 deletions(-)
16
26
17
diff --git a/include/exec/memory.h b/include/exec/memory.h
27
diff --git a/hw/gpio/pl061.c b/hw/gpio/pl061.c
18
index XXXXXXX..XXXXXXX 100644
28
index XXXXXXX..XXXXXXX 100644
19
--- a/include/exec/memory.h
29
--- a/hw/gpio/pl061.c
20
+++ b/include/exec/memory.h
30
+++ b/hw/gpio/pl061.c
21
@@ -XXX,XX +XXX,XX @@ bool address_space_access_valid(AddressSpace *as, hwaddr addr, int len, bool is_
31
@@ -XXX,XX +XXX,XX @@
22
* @addr: address within that address space
32
* + unnamed GPIO inputs 0..7: inputs to connect to the emulated GPIO lines
23
* @plen: pointer to length of buffer; updated on return
33
* + unnamed GPIO outputs 0..7: the emulated GPIO lines, considered as
24
* @is_write: indicates the transfer direction
34
* outputs
25
+ * @attrs: memory attributes
35
+ * + QOM property "pullups": an integer defining whether non-floating lines
36
+ * configured as inputs should be pulled up to logical 1 (ie whether in
37
+ * real hardware they have a pullup resistor on the line out of the PL061).
38
+ * This should be an 8-bit value, where bit 0 is 1 if GPIO line 0 should
39
+ * be pulled high, bit 1 configures line 1, and so on. The default is 0xff,
40
+ * indicating that all GPIO lines are pulled up to logical 1.
41
+ * + QOM property "pulldowns": an integer defining whether non-floating lines
42
+ * configured as inputs should be pulled down to logical 0 (ie whether in
43
+ * real hardware they have a pulldown resistor on the line out of the PL061).
44
+ * This should be an 8-bit value, where bit 0 is 1 if GPIO line 0 should
45
+ * be pulled low, bit 1 configures line 1, and so on. The default is 0x0.
46
+ * It is an error to set a bit in both "pullups" and "pulldowns". If a bit
47
+ * is 0 in both, then the line is considered to be floating, and it will
48
+ * not have qemu_set_irq() called on it when it is configured as an input.
26
*/
49
*/
27
void *address_space_map(AddressSpace *as, hwaddr addr,
50
28
- hwaddr *plen, bool is_write);
51
#include "qemu/osdep.h"
29
+ hwaddr *plen, bool is_write, MemTxAttrs attrs);
52
#include "hw/irq.h"
30
53
#include "hw/sysbus.h"
31
/* address_space_unmap: Unmaps a memory region previously mapped by address_space_map()
54
+#include "hw/qdev-properties.h"
32
*
55
#include "migration/vmstate.h"
33
diff --git a/include/sysemu/dma.h b/include/sysemu/dma.h
56
+#include "qapi/error.h"
34
index XXXXXXX..XXXXXXX 100644
57
#include "qemu/log.h"
35
--- a/include/sysemu/dma.h
58
#include "qemu/module.h"
36
+++ b/include/sysemu/dma.h
59
#include "qom/object.h"
37
@@ -XXX,XX +XXX,XX @@ static inline void *dma_memory_map(AddressSpace *as,
60
@@ -XXX,XX +XXX,XX @@ struct PL061State {
38
hwaddr xlen = *len;
61
qemu_irq irq;
39
void *p;
62
qemu_irq out[N_GPIOS];
40
63
const unsigned char *id;
41
- p = address_space_map(as, addr, &xlen, dir == DMA_DIRECTION_FROM_DEVICE);
64
+ /* Properties, for non-Luminary PL061 */
42
+ p = address_space_map(as, addr, &xlen, dir == DMA_DIRECTION_FROM_DEVICE,
65
+ uint32_t pullups;
43
+ MEMTXATTRS_UNSPECIFIED);
66
+ uint32_t pulldowns;
44
*len = xlen;
67
};
45
return p;
68
69
static const VMStateDescription vmstate_pl061 = {
70
@@ -XXX,XX +XXX,XX @@ static uint8_t pl061_floating(PL061State *s)
71
*/
72
floating = ~(s->pur | s->pdr);
73
} else {
74
- /* Assume outputs are pulled high. FIXME: this is board dependent. */
75
- floating = 0;
76
+ floating = ~(s->pullups | s->pulldowns);
77
}
78
return floating & ~s->dir;
46
}
79
}
47
diff --git a/exec.c b/exec.c
80
@@ -XXX,XX +XXX,XX @@ static uint8_t pl061_pullups(PL061State *s)
48
index XXXXXXX..XXXXXXX 100644
81
*/
49
--- a/exec.c
82
pullups = s->pur;
50
+++ b/exec.c
83
} else {
51
@@ -XXX,XX +XXX,XX @@ flatview_extend_translation(FlatView *fv, hwaddr addr,
84
- /* Assume outputs are pulled high. FIXME: this is board dependent. */
52
void *address_space_map(AddressSpace *as,
85
- pullups = 0xff;
53
hwaddr addr,
86
+ pullups = s->pullups;
54
hwaddr *plen,
87
}
55
- bool is_write)
88
return pullups & ~s->dir;
56
+ bool is_write,
89
}
57
+ MemTxAttrs attrs)
90
@@ -XXX,XX +XXX,XX @@ static void pl061_init(Object *obj)
91
qdev_init_gpio_out(dev, s->out, N_GPIOS);
92
}
93
94
+static void pl061_realize(DeviceState *dev, Error **errp)
95
+{
96
+ PL061State *s = PL061(dev);
97
+
98
+ if (s->pullups > 0xff) {
99
+ error_setg(errp, "pullups property must be between 0 and 0xff");
100
+ return;
101
+ }
102
+ if (s->pulldowns > 0xff) {
103
+ error_setg(errp, "pulldowns property must be between 0 and 0xff");
104
+ return;
105
+ }
106
+ if (s->pullups & s->pulldowns) {
107
+ error_setg(errp, "no bit may be set both in pullups and pulldowns");
108
+ return;
109
+ }
110
+}
111
+
112
+static Property pl061_props[] = {
113
+ DEFINE_PROP_UINT32("pullups", PL061State, pullups, 0xff),
114
+ DEFINE_PROP_UINT32("pulldowns", PL061State, pulldowns, 0x0),
115
+ DEFINE_PROP_END_OF_LIST()
116
+};
117
+
118
static void pl061_class_init(ObjectClass *klass, void *data)
58
{
119
{
59
hwaddr len = *plen;
120
DeviceClass *dc = DEVICE_CLASS(klass);
60
hwaddr l, xlat;
121
61
@@ -XXX,XX +XXX,XX @@ void *cpu_physical_memory_map(hwaddr addr,
122
dc->vmsd = &vmstate_pl061;
62
hwaddr *plen,
123
dc->reset = &pl061_reset;
63
int is_write)
124
+ dc->realize = pl061_realize;
64
{
125
+ device_class_set_props(dc, pl061_props);
65
- return address_space_map(&address_space_memory, addr, plen, is_write);
66
+ return address_space_map(&address_space_memory, addr, plen, is_write,
67
+ MEMTXATTRS_UNSPECIFIED);
68
}
126
}
69
127
70
void cpu_physical_memory_unmap(void *buffer, hwaddr len,
128
static const TypeInfo pl061_info = {
71
diff --git a/target/ppc/mmu-hash64.c b/target/ppc/mmu-hash64.c
72
index XXXXXXX..XXXXXXX 100644
73
--- a/target/ppc/mmu-hash64.c
74
+++ b/target/ppc/mmu-hash64.c
75
@@ -XXX,XX +XXX,XX @@ const ppc_hash_pte64_t *ppc_hash64_map_hptes(PowerPCCPU *cpu,
76
return NULL;
77
}
78
79
- hptes = address_space_map(CPU(cpu)->as, base + pte_offset, &plen, false);
80
+ hptes = address_space_map(CPU(cpu)->as, base + pte_offset, &plen, false,
81
+ MEMTXATTRS_UNSPECIFIED);
82
if (plen < (n * HASH_PTE_SIZE_64)) {
83
hw_error("%s: Unable to map all requested HPTEs\n", __func__);
84
}
85
--
129
--
86
2.17.1
130
2.20.1
87
131
88
132
diff view generated by jsdifflib
1
Provide a VMSTATE_BOOL_SUB_ARRAY to go with VMSTATE_UINT8_SUB_ARRAY
1
For the virt board we have two PL061 devices -- one for NonSecure which
2
and friends.
2
is inputs only, and one for Secure which is outputs only. For the former,
3
we don't care whether its outputs are pulled low or high when the line is
4
configured as an input, because we don't connect them. For the latter,
5
we do care, because we wire the lines up to the gpio-pwr device, which
6
assumes that level 1 means "do the action" and 1 means "do nothing".
7
For consistency in case we add more outputs in future, configure both
8
PL061s to pull GPIO lines down to 0.
3
9
10
Reported-by: Maxim Uvarov <maxim.uvarov@linaro.org>
4
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
11
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
5
Reviewed-by: Alex Bennée <alex.bennee@linaro.org>
12
Reviewed-by: Richard Henderson <richard.henderson@linaro.org>
6
Message-id: 20180521140402.23318-23-peter.maydell@linaro.org
7
---
13
---
8
include/migration/vmstate.h | 3 +++
14
hw/arm/virt.c | 3 +++
9
1 file changed, 3 insertions(+)
15
1 file changed, 3 insertions(+)
10
16
11
diff --git a/include/migration/vmstate.h b/include/migration/vmstate.h
17
diff --git a/hw/arm/virt.c b/hw/arm/virt.c
12
index XXXXXXX..XXXXXXX 100644
18
index XXXXXXX..XXXXXXX 100644
13
--- a/include/migration/vmstate.h
19
--- a/hw/arm/virt.c
14
+++ b/include/migration/vmstate.h
20
+++ b/hw/arm/virt.c
15
@@ -XXX,XX +XXX,XX @@ extern const VMStateInfo vmstate_info_qtailq;
21
@@ -XXX,XX +XXX,XX @@ static void create_gpio_devices(const VirtMachineState *vms, int gpio,
16
#define VMSTATE_BOOL_ARRAY(_f, _s, _n) \
22
MachineState *ms = MACHINE(vms);
17
VMSTATE_BOOL_ARRAY_V(_f, _s, _n, 0)
23
18
24
pl061_dev = qdev_new("pl061");
19
+#define VMSTATE_BOOL_SUB_ARRAY(_f, _s, _start, _num) \
25
+ /* Pull lines down to 0 if not driven by the PL061 */
20
+ VMSTATE_SUB_ARRAY(_f, _s, _start, _num, 0, vmstate_info_bool, bool)
26
+ qdev_prop_set_uint32(pl061_dev, "pullups", 0);
21
+
27
+ qdev_prop_set_uint32(pl061_dev, "pulldowns", 0xff);
22
#define VMSTATE_UINT16_ARRAY_V(_f, _s, _n, _v) \
28
s = SYS_BUS_DEVICE(pl061_dev);
23
VMSTATE_ARRAY(_f, _s, _n, _v, vmstate_info_uint16, uint16_t)
29
sysbus_realize_and_unref(s, &error_fatal);
24
30
memory_region_add_subregion(mem, base, sysbus_mmio_get_region(s, 0));
25
--
31
--
26
2.17.1
32
2.20.1
27
33
28
34
diff view generated by jsdifflib
1
As part of plumbing MemTxAttrs down to the IOMMU translate method,
1
The PL061 comes out of reset with all its lines configured as input,
2
add MemTxAttrs as an argument to flatview_access_valid().
2
which means they might need to be pulled to 0 or 1 depending on the
3
Its callers now all have an attrs value to hand, so we can
3
'pullups' and 'pulldowns' properties. Currently we do not assert
4
correct our earlier temporary use of MEMTXATTRS_UNSPECIFIED.
4
these lines on reset; they will only be set whenever the guest first
5
touches a register that triggers a call to pl061_update().
6
7
Convert the device to three-phase reset so we have a place where we
8
can safely call qemu_set_irq() to set the floating lines to their
9
correct values.
5
10
6
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
11
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
7
Reviewed-by: Alex Bennée <alex.bennee@linaro.org>
12
Reviewed-by: Philippe Mathieu-Daudé <f4bug@amsat.org>
8
Reviewed-by: Richard Henderson <richard.henderson@linaro.org>
13
Reviewed-by: Richard Henderson <richard.henderson@linaro.org>
9
Message-id: 20180521140402.23318-10-peter.maydell@linaro.org
10
---
14
---
11
exec.c | 12 +++++-------
15
hw/gpio/pl061.c | 29 +++++++++++++++++++++++++----
12
1 file changed, 5 insertions(+), 7 deletions(-)
16
hw/gpio/trace-events | 1 +
17
2 files changed, 26 insertions(+), 4 deletions(-)
13
18
14
diff --git a/exec.c b/exec.c
19
diff --git a/hw/gpio/pl061.c b/hw/gpio/pl061.c
15
index XXXXXXX..XXXXXXX 100644
20
index XXXXXXX..XXXXXXX 100644
16
--- a/exec.c
21
--- a/hw/gpio/pl061.c
17
+++ b/exec.c
22
+++ b/hw/gpio/pl061.c
18
@@ -XXX,XX +XXX,XX @@ static MemTxResult flatview_read(FlatView *fv, hwaddr addr,
23
@@ -XXX,XX +XXX,XX @@ static void pl061_write(void *opaque, hwaddr offset,
19
static MemTxResult flatview_write(FlatView *fv, hwaddr addr, MemTxAttrs attrs,
24
return;
20
const uint8_t *buf, int len);
21
static bool flatview_access_valid(FlatView *fv, hwaddr addr, int len,
22
- bool is_write);
23
+ bool is_write, MemTxAttrs attrs);
24
25
static MemTxResult subpage_read(void *opaque, hwaddr addr, uint64_t *data,
26
unsigned len, MemTxAttrs attrs)
27
@@ -XXX,XX +XXX,XX @@ static bool subpage_accepts(void *opaque, hwaddr addr,
28
#endif
29
30
return flatview_access_valid(subpage->fv, addr + subpage->base,
31
- len, is_write);
32
+ len, is_write, attrs);
33
}
25
}
34
26
35
static const MemoryRegionOps subpage_ops = {
27
-static void pl061_reset(DeviceState *dev)
36
@@ -XXX,XX +XXX,XX @@ static void cpu_notify_map_clients(void)
28
+static void pl061_enter_reset(Object *obj, ResetType type)
29
{
30
- PL061State *s = PL061(dev);
31
+ PL061State *s = PL061(obj);
32
+
33
+ trace_pl061_reset(DEVICE(s)->canonical_path);
34
35
/* reset values from PL061 TRM, Stellaris LM3S5P31 & LM3S8962 Data Sheet */
36
s->data = 0;
37
- s->old_out_data = 0;
38
s->old_in_data = 0;
39
s->dir = 0;
40
s->isense = 0;
41
@@ -XXX,XX +XXX,XX @@ static void pl061_reset(DeviceState *dev)
42
s->amsel = 0;
37
}
43
}
38
44
39
static bool flatview_access_valid(FlatView *fv, hwaddr addr, int len,
45
+static void pl061_hold_reset(Object *obj)
40
- bool is_write)
46
+{
41
+ bool is_write, MemTxAttrs attrs)
47
+ PL061State *s = PL061(obj);
48
+ int i, level;
49
+ uint8_t floating = pl061_floating(s);
50
+ uint8_t pullups = pl061_pullups(s);
51
+
52
+ for (i = 0; i < N_GPIOS; i++) {
53
+ if (extract32(floating, i, 1)) {
54
+ continue;
55
+ }
56
+ level = extract32(pullups, i, 1);
57
+ trace_pl061_set_output(DEVICE(s)->canonical_path, i, level);
58
+ qemu_set_irq(s->out[i], level);
59
+ }
60
+ s->old_out_data = pullups;
61
+}
62
+
63
static void pl061_set_irq(void * opaque, int irq, int level)
42
{
64
{
43
MemoryRegion *mr;
65
PL061State *s = (PL061State *)opaque;
44
hwaddr l, xlat;
66
@@ -XXX,XX +XXX,XX @@ static Property pl061_props[] = {
45
@@ -XXX,XX +XXX,XX @@ static bool flatview_access_valid(FlatView *fv, hwaddr addr, int len,
67
static void pl061_class_init(ObjectClass *klass, void *data)
46
mr = flatview_translate(fv, addr, &xlat, &l, is_write);
68
{
47
if (!memory_access_is_direct(mr, is_write)) {
69
DeviceClass *dc = DEVICE_CLASS(klass);
48
l = memory_access_size(mr, l, addr);
70
+ ResettableClass *rc = RESETTABLE_CLASS(klass);
49
- /* When our callers all have attrs we'll pass them through here */
71
50
- if (!memory_region_access_valid(mr, xlat, l, is_write,
72
dc->vmsd = &vmstate_pl061;
51
- MEMTXATTRS_UNSPECIFIED)) {
73
- dc->reset = &pl061_reset;
52
+ if (!memory_region_access_valid(mr, xlat, l, is_write, attrs)) {
74
dc->realize = pl061_realize;
53
return false;
75
device_class_set_props(dc, pl061_props);
54
}
76
+ rc->phases.enter = pl061_enter_reset;
55
}
77
+ rc->phases.hold = pl061_hold_reset;
56
@@ -XXX,XX +XXX,XX @@ bool address_space_access_valid(AddressSpace *as, hwaddr addr,
57
58
rcu_read_lock();
59
fv = address_space_to_flatview(as);
60
- result = flatview_access_valid(fv, addr, len, is_write);
61
+ result = flatview_access_valid(fv, addr, len, is_write, attrs);
62
rcu_read_unlock();
63
return result;
64
}
78
}
79
80
static const TypeInfo pl061_info = {
81
diff --git a/hw/gpio/trace-events b/hw/gpio/trace-events
82
index XXXXXXX..XXXXXXX 100644
83
--- a/hw/gpio/trace-events
84
+++ b/hw/gpio/trace-events
85
@@ -XXX,XX +XXX,XX @@ pl061_input_change(const char *id, int gpio, int level) "%s input %d changed to
86
pl061_update_istate(const char *id, uint32_t istate, uint32_t im, int level) "%s GPIORIS 0x%x GPIOIE 0x%x interrupt level %d"
87
pl061_read(const char *id, uint64_t offset, uint64_t r) "%s offset 0x%" PRIx64 " value 0x%" PRIx64
88
pl061_write(const char *id, uint64_t offset, uint64_t value) "%s offset 0x%" PRIx64 " value 0x%" PRIx64
89
+pl061_reset(const char *id) "%s reset"
90
91
# sifive_gpio.c
92
sifive_gpio_read(uint64_t offset, uint64_t r) "offset 0x%" PRIx64 " value 0x%" PRIx64
65
--
93
--
66
2.17.1
94
2.20.1
67
95
68
96
diff view generated by jsdifflib
1
As part of plumbing MemTxAttrs down to the IOMMU translate method,
1
The Luminary PL061s in the Stellaris LM3S9695 don't all have the same
2
add MemTxAttrs as an argument to flatview_do_translate().
2
reset value for GPIOPUR. We can get away with not letting the board
3
configure the PUR reset value because we don't actually wire anything
4
up to the lines which should reset to pull-up. Add a comment noting
5
this omission.
3
6
4
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
7
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
5
Reviewed-by: Alex Bennée <alex.bennee@linaro.org>
8
Reviewed-by: Philippe Mathieu-Daudé <f4bug@amsat.org>
6
Reviewed-by: Richard Henderson <richard.henderson@linaro.org>
7
Message-id: 20180521140402.23318-13-peter.maydell@linaro.org
8
---
9
---
9
exec.c | 9 ++++++---
10
hw/gpio/pl061.c | 9 +++++++++
10
1 file changed, 6 insertions(+), 3 deletions(-)
11
1 file changed, 9 insertions(+)
11
12
12
diff --git a/exec.c b/exec.c
13
diff --git a/hw/gpio/pl061.c b/hw/gpio/pl061.c
13
index XXXXXXX..XXXXXXX 100644
14
index XXXXXXX..XXXXXXX 100644
14
--- a/exec.c
15
--- a/hw/gpio/pl061.c
15
+++ b/exec.c
16
+++ b/hw/gpio/pl061.c
16
@@ -XXX,XX +XXX,XX @@ unassigned:
17
@@ -XXX,XX +XXX,XX @@ static void pl061_enter_reset(Object *obj, ResetType type)
17
* @is_write: whether the translation operation is for write
18
trace_pl061_reset(DEVICE(s)->canonical_path);
18
* @is_mmio: whether this can be MMIO, set true if it can
19
19
* @target_as: the address space targeted by the IOMMU
20
/* reset values from PL061 TRM, Stellaris LM3S5P31 & LM3S8962 Data Sheet */
20
+ * @attrs: memory transaction attributes
21
+
21
*
22
+ /*
22
* This function is called from RCU critical section
23
+ * FIXME: For the LM3S6965, not all of the PL061 instances have the
23
*/
24
+ * same reset values for GPIOPUR, GPIOAFSEL and GPIODEN, so in theory
24
@@ -XXX,XX +XXX,XX @@ static MemoryRegionSection flatview_do_translate(FlatView *fv,
25
+ * we should allow the board to configure these via properties.
25
hwaddr *page_mask_out,
26
+ * In practice, we don't wire anything up to the affected GPIO lines
26
bool is_write,
27
+ * (PB7, PC0, PC1, PC2, PC3 -- they're used for JTAG), so we can
27
bool is_mmio,
28
+ * get away with this inaccuracy.
28
- AddressSpace **target_as)
29
+ */
29
+ AddressSpace **target_as,
30
s->data = 0;
30
+ MemTxAttrs attrs)
31
s->old_in_data = 0;
31
{
32
s->dir = 0;
32
MemoryRegionSection *section;
33
IOMMUMemoryRegion *iommu_mr;
34
@@ -XXX,XX +XXX,XX @@ IOMMUTLBEntry address_space_get_iotlb_entry(AddressSpace *as, hwaddr addr,
35
* but page mask.
36
*/
37
section = flatview_do_translate(address_space_to_flatview(as), addr, &xlat,
38
- NULL, &page_mask, is_write, false, &as);
39
+ NULL, &page_mask, is_write, false, &as,
40
+ attrs);
41
42
/* Illegal translation */
43
if (section.mr == &io_mem_unassigned) {
44
@@ -XXX,XX +XXX,XX @@ MemoryRegion *flatview_translate(FlatView *fv, hwaddr addr, hwaddr *xlat,
45
46
/* This can be MMIO, so setup MMIO bit. */
47
section = flatview_do_translate(fv, addr, xlat, plen, NULL,
48
- is_write, true, &as);
49
+ is_write, true, &as, attrs);
50
mr = section.mr;
51
52
if (xen_enabled() && memory_access_is_direct(mr, is_write)) {
53
--
33
--
54
2.17.1
34
2.20.1
55
35
56
36
diff view generated by jsdifflib
1
As part of plumbing MemTxAttrs down to the IOMMU translate method,
1
The stellaris board doesn't emulate the handling of the OLED
2
add MemTxAttrs as an argument to address_space_translate_iommu().
2
chipselect line correctly. Expand the comment describing this,
3
including a sketch of the theoretical correct way to do it.
3
4
4
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
5
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
5
Reviewed-by: Alex Bennée <alex.bennee@linaro.org>
6
Reviewed-by: Richard Henderson <richard.henderson@linaro.org>
7
Message-id: 20180521140402.23318-14-peter.maydell@linaro.org
8
---
6
---
9
exec.c | 8 +++++---
7
hw/arm/stellaris.c | 56 +++++++++++++++++++++++++++++++++++++++++++++-
10
1 file changed, 5 insertions(+), 3 deletions(-)
8
1 file changed, 55 insertions(+), 1 deletion(-)
11
9
12
diff --git a/exec.c b/exec.c
10
diff --git a/hw/arm/stellaris.c b/hw/arm/stellaris.c
13
index XXXXXXX..XXXXXXX 100644
11
index XXXXXXX..XXXXXXX 100644
14
--- a/exec.c
12
--- a/hw/arm/stellaris.c
15
+++ b/exec.c
13
+++ b/hw/arm/stellaris.c
16
@@ -XXX,XX +XXX,XX @@ address_space_translate_internal(AddressSpaceDispatch *d, hwaddr addr, hwaddr *x
14
@@ -XXX,XX +XXX,XX @@ static void stellaris_init(MachineState *ms, stellaris_board_info *board)
17
* @is_write: whether the translation operation is for write
15
DeviceState *sddev;
18
* @is_mmio: whether this can be MMIO, set true if it can
16
DeviceState *ssddev;
19
* @target_as: the address space targeted by the IOMMU
17
20
+ * @attrs: transaction attributes
18
- /* Some boards have both an OLED controller and SD card connected to
21
*
19
+ /*
22
* This function is called from RCU critical section. It is the common
20
+ * Some boards have both an OLED controller and SD card connected to
23
* part of flatview_do_translate and address_space_translate_cached.
21
* the same SSI port, with the SD card chip select connected to a
24
@@ -XXX,XX +XXX,XX @@ static MemoryRegionSection address_space_translate_iommu(IOMMUMemoryRegion *iomm
22
* GPIO pin. Technically the OLED chip select is connected to the
25
hwaddr *page_mask_out,
23
* SSI Fss pin. We do not bother emulating that as both devices
26
bool is_write,
24
* should never be selected simultaneously, and our OLED controller
27
bool is_mmio,
25
* ignores stray 0xff commands that occur when deselecting the SD
28
- AddressSpace **target_as)
26
* card.
29
+ AddressSpace **target_as,
27
+ *
30
+ MemTxAttrs attrs)
28
+ * The h/w wiring is:
31
{
29
+ * - GPIO pin D0 is wired to the active-low SD card chip select
32
MemoryRegionSection *section;
30
+ * - GPIO pin A3 is wired to the active-low OLED chip select
33
hwaddr page_mask = (hwaddr)-1;
31
+ * - The SoC wiring of the PL061 "auxiliary function" for A3 is
34
@@ -XXX,XX +XXX,XX @@ static MemoryRegionSection flatview_do_translate(FlatView *fv,
32
+ * SSI0Fss ("frame signal"), which is an output from the SoC's
35
return address_space_translate_iommu(iommu_mr, xlat,
33
+ * SSI controller. The SSI controller takes SSI0Fss low when it
36
plen_out, page_mask_out,
34
+ * transmits a frame, so it can work as a chip-select signal.
37
is_write, is_mmio,
35
+ * - GPIO A4 is aux-function SSI0Rx, and wired to the SD card Tx
38
- target_as);
36
+ * (the OLED never sends data to the CPU, so no wiring needed)
39
+ target_as, attrs);
37
+ * - GPIO A5 is aux-function SSI0Tx, and wired to the SD card Rx
40
}
38
+ * and the OLED display-data-in
41
if (page_mask_out) {
39
+ * - GPIO A2 is aux-function SSI0Clk, wired to SD card and OLED
42
/* Not behind an IOMMU, use default page size. */
40
+ * serial-clock input
43
@@ -XXX,XX +XXX,XX @@ static inline MemoryRegion *address_space_translate_cached(
41
+ * So a guest that wants to use the OLED can configure the PL061
44
42
+ * to make pins A2, A3, A5 aux-function, so they are connected
45
section = address_space_translate_iommu(iommu_mr, xlat, plen,
43
+ * directly to the SSI controller. When the SSI controller sends
46
NULL, is_write, true,
44
+ * data it asserts SSI0Fss which selects the OLED.
47
- &target_as);
45
+ * A guest that wants to use the SD card configures A2, A4 and A5
48
+ &target_as, attrs);
46
+ * as aux-function, but leaves A3 as a software-controlled GPIO
49
return section.mr;
47
+ * line. It asserts the SD card chip-select by using the PL061
50
}
48
+ * to control pin D0, and lets the SSI controller handle Clk, Tx
49
+ * and Rx. (The SSI controller asserts Fss during tx cycles as
50
+ * usual, but because A3 is not set to aux-function this is not
51
+ * forwarded to the OLED, and so the OLED stays unselected.)
52
+ *
53
+ * The QEMU implementation instead is:
54
+ * - GPIO pin D0 is wired to the active-low SD card chip select,
55
+ * and also to the OLED chip-select which is implemented
56
+ * as *active-high*
57
+ * - SSI controller signals go to the devices regardless of
58
+ * whether the guest programs A2, A4, A5 as aux-function or not
59
+ *
60
+ * The problem with this implementation is if the guest doesn't
61
+ * care about the SD card and only uses the OLED. In that case it
62
+ * may choose never to do anything with D0 (leaving it in its
63
+ * default floating state, which reliably leaves the card disabled
64
+ * because an SD card has a pullup on CS within the card itself),
65
+ * and only set up A2, A3, A5. This for us would mean the OLED
66
+ * never gets the chip-select assert it needs. We work around
67
+ * this with a manual raise of D0 here (despite board creation
68
+ * code being the wrong place to raise IRQ lines) to put the OLED
69
+ * into an initially selected state.
70
+ *
71
+ * In theory the right way to model this would be:
72
+ * - Implement aux-function support in the PL061, with an
73
+ * extra set of AFIN and AFOUT GPIO lines (set up so that
74
+ * if a GPIO line is in auxfn mode the main GPIO in and out
75
+ * track the AFIN and AFOUT lines)
76
+ * - Wire the AFOUT for D0 up to either a line from the
77
+ * SSI controller that's pulled low around every transmit,
78
+ * or at least to an always-0 line here on the board
79
+ * - Make the ssd0323 OLED controller chipselect active-low
80
*/
81
bus = qdev_get_child_bus(dev, "ssi");
51
82
52
--
83
--
53
2.17.1
84
2.20.1
54
85
55
86
diff view generated by jsdifflib
1
From: Richard Henderson <richard.henderson@linaro.org>
1
From: "hnick@vmware.com" <hnick@vmware.com>
2
2
3
Depending on the host abi, float16, aka uint16_t, values are
3
Signed-off-by: Nick Hudson <hnick@vmware.com>
4
passed and returned either zero-extended in the host register
5
or with garbage at the top of the host register.
6
7
The tcg code generator has so far been assuming garbage, as that
8
matches the x86 abi, but this is incorrect for other host abis.
9
Further, target/arm has so far been assuming zero-extended results,
10
so that it may store the 16-bit value into a 32-bit slot with the
11
high 16-bits already clear.
12
13
Rectify both problems by mapping "f16" in the helper definition
14
to uint32_t instead of (a typedef for) uint16_t. This forces
15
the host compiler to assume garbage in the upper 16 bits on input
16
and to zero-extend the result on output.
17
18
Cc: qemu-stable@nongnu.org
19
Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
20
Reviewed-by: Philippe Mathieu-Daudé <f4bug@amsat.org>
21
Tested-by: Laurent Desnogues <laurent.desnogues@gmail.com>
22
Message-id: 20180522175629.24932-1-richard.henderson@linaro.org
23
Reviewed-by: Peter Maydell <peter.maydell@linaro.org>
4
Reviewed-by: Peter Maydell <peter.maydell@linaro.org>
24
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
5
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
25
---
6
---
26
include/exec/helper-head.h | 2 +-
7
target/arm/helper.c | 16 +++++++++++++---
27
target/arm/helper-a64.c | 35 +++++++++--------
8
1 file changed, 13 insertions(+), 3 deletions(-)
28
target/arm/helper.c | 80 +++++++++++++++++++-------------------
29
3 files changed, 59 insertions(+), 58 deletions(-)
30
9
31
diff --git a/include/exec/helper-head.h b/include/exec/helper-head.h
32
index XXXXXXX..XXXXXXX 100644
33
--- a/include/exec/helper-head.h
34
+++ b/include/exec/helper-head.h
35
@@ -XXX,XX +XXX,XX @@
36
#define dh_ctype_int int
37
#define dh_ctype_i64 uint64_t
38
#define dh_ctype_s64 int64_t
39
-#define dh_ctype_f16 float16
40
+#define dh_ctype_f16 uint32_t
41
#define dh_ctype_f32 float32
42
#define dh_ctype_f64 float64
43
#define dh_ctype_ptr void *
44
diff --git a/target/arm/helper-a64.c b/target/arm/helper-a64.c
45
index XXXXXXX..XXXXXXX 100644
46
--- a/target/arm/helper-a64.c
47
+++ b/target/arm/helper-a64.c
48
@@ -XXX,XX +XXX,XX @@ static inline uint32_t float_rel_to_flags(int res)
49
return flags;
50
}
51
52
-uint64_t HELPER(vfp_cmph_a64)(float16 x, float16 y, void *fp_status)
53
+uint64_t HELPER(vfp_cmph_a64)(uint32_t x, uint32_t y, void *fp_status)
54
{
55
return float_rel_to_flags(float16_compare_quiet(x, y, fp_status));
56
}
57
58
-uint64_t HELPER(vfp_cmpeh_a64)(float16 x, float16 y, void *fp_status)
59
+uint64_t HELPER(vfp_cmpeh_a64)(uint32_t x, uint32_t y, void *fp_status)
60
{
61
return float_rel_to_flags(float16_compare(x, y, fp_status));
62
}
63
@@ -XXX,XX +XXX,XX @@ uint64_t HELPER(neon_cgt_f64)(float64 a, float64 b, void *fpstp)
64
#define float64_three make_float64(0x4008000000000000ULL)
65
#define float64_one_point_five make_float64(0x3FF8000000000000ULL)
66
67
-float16 HELPER(recpsf_f16)(float16 a, float16 b, void *fpstp)
68
+uint32_t HELPER(recpsf_f16)(uint32_t a, uint32_t b, void *fpstp)
69
{
70
float_status *fpst = fpstp;
71
72
@@ -XXX,XX +XXX,XX @@ float64 HELPER(recpsf_f64)(float64 a, float64 b, void *fpstp)
73
return float64_muladd(a, b, float64_two, 0, fpst);
74
}
75
76
-float16 HELPER(rsqrtsf_f16)(float16 a, float16 b, void *fpstp)
77
+uint32_t HELPER(rsqrtsf_f16)(uint32_t a, uint32_t b, void *fpstp)
78
{
79
float_status *fpst = fpstp;
80
81
@@ -XXX,XX +XXX,XX @@ uint64_t HELPER(neon_addlp_u16)(uint64_t a)
82
}
83
84
/* Floating-point reciprocal exponent - see FPRecpX in ARM ARM */
85
-float16 HELPER(frecpx_f16)(float16 a, void *fpstp)
86
+uint32_t HELPER(frecpx_f16)(uint32_t a, void *fpstp)
87
{
88
float_status *fpst = fpstp;
89
uint16_t val16, sbit;
90
@@ -XXX,XX +XXX,XX @@ void HELPER(casp_be_parallel)(CPUARMState *env, uint32_t rs, uint64_t addr,
91
#define ADVSIMD_HELPER(name, suffix) HELPER(glue(glue(advsimd_, name), suffix))
92
93
#define ADVSIMD_HALFOP(name) \
94
-float16 ADVSIMD_HELPER(name, h)(float16 a, float16 b, void *fpstp) \
95
+uint32_t ADVSIMD_HELPER(name, h)(uint32_t a, uint32_t b, void *fpstp) \
96
{ \
97
float_status *fpst = fpstp; \
98
return float16_ ## name(a, b, fpst); \
99
@@ -XXX,XX +XXX,XX @@ ADVSIMD_HALFOP(mulx)
100
ADVSIMD_TWOHALFOP(mulx)
101
102
/* fused multiply-accumulate */
103
-float16 HELPER(advsimd_muladdh)(float16 a, float16 b, float16 c, void *fpstp)
104
+uint32_t HELPER(advsimd_muladdh)(uint32_t a, uint32_t b, uint32_t c,
105
+ void *fpstp)
106
{
107
float_status *fpst = fpstp;
108
return float16_muladd(a, b, c, 0, fpst);
109
@@ -XXX,XX +XXX,XX @@ uint32_t HELPER(advsimd_muladd2h)(uint32_t two_a, uint32_t two_b,
110
111
#define ADVSIMD_CMPRES(test) (test) ? 0xffff : 0
112
113
-uint32_t HELPER(advsimd_ceq_f16)(float16 a, float16 b, void *fpstp)
114
+uint32_t HELPER(advsimd_ceq_f16)(uint32_t a, uint32_t b, void *fpstp)
115
{
116
float_status *fpst = fpstp;
117
int compare = float16_compare_quiet(a, b, fpst);
118
return ADVSIMD_CMPRES(compare == float_relation_equal);
119
}
120
121
-uint32_t HELPER(advsimd_cge_f16)(float16 a, float16 b, void *fpstp)
122
+uint32_t HELPER(advsimd_cge_f16)(uint32_t a, uint32_t b, void *fpstp)
123
{
124
float_status *fpst = fpstp;
125
int compare = float16_compare(a, b, fpst);
126
@@ -XXX,XX +XXX,XX @@ uint32_t HELPER(advsimd_cge_f16)(float16 a, float16 b, void *fpstp)
127
compare == float_relation_equal);
128
}
129
130
-uint32_t HELPER(advsimd_cgt_f16)(float16 a, float16 b, void *fpstp)
131
+uint32_t HELPER(advsimd_cgt_f16)(uint32_t a, uint32_t b, void *fpstp)
132
{
133
float_status *fpst = fpstp;
134
int compare = float16_compare(a, b, fpst);
135
return ADVSIMD_CMPRES(compare == float_relation_greater);
136
}
137
138
-uint32_t HELPER(advsimd_acge_f16)(float16 a, float16 b, void *fpstp)
139
+uint32_t HELPER(advsimd_acge_f16)(uint32_t a, uint32_t b, void *fpstp)
140
{
141
float_status *fpst = fpstp;
142
float16 f0 = float16_abs(a);
143
@@ -XXX,XX +XXX,XX @@ uint32_t HELPER(advsimd_acge_f16)(float16 a, float16 b, void *fpstp)
144
compare == float_relation_equal);
145
}
146
147
-uint32_t HELPER(advsimd_acgt_f16)(float16 a, float16 b, void *fpstp)
148
+uint32_t HELPER(advsimd_acgt_f16)(uint32_t a, uint32_t b, void *fpstp)
149
{
150
float_status *fpst = fpstp;
151
float16 f0 = float16_abs(a);
152
@@ -XXX,XX +XXX,XX @@ uint32_t HELPER(advsimd_acgt_f16)(float16 a, float16 b, void *fpstp)
153
}
154
155
/* round to integral */
156
-float16 HELPER(advsimd_rinth_exact)(float16 x, void *fp_status)
157
+uint32_t HELPER(advsimd_rinth_exact)(uint32_t x, void *fp_status)
158
{
159
return float16_round_to_int(x, fp_status);
160
}
161
162
-float16 HELPER(advsimd_rinth)(float16 x, void *fp_status)
163
+uint32_t HELPER(advsimd_rinth)(uint32_t x, void *fp_status)
164
{
165
int old_flags = get_float_exception_flags(fp_status), new_flags;
166
float16 ret;
167
@@ -XXX,XX +XXX,XX @@ float16 HELPER(advsimd_rinth)(float16 x, void *fp_status)
168
* setting the mode appropriately before calling the helper.
169
*/
170
171
-uint32_t HELPER(advsimd_f16tosinth)(float16 a, void *fpstp)
172
+uint32_t HELPER(advsimd_f16tosinth)(uint32_t a, void *fpstp)
173
{
174
float_status *fpst = fpstp;
175
176
@@ -XXX,XX +XXX,XX @@ uint32_t HELPER(advsimd_f16tosinth)(float16 a, void *fpstp)
177
return float16_to_int16(a, fpst);
178
}
179
180
-uint32_t HELPER(advsimd_f16touinth)(float16 a, void *fpstp)
181
+uint32_t HELPER(advsimd_f16touinth)(uint32_t a, void *fpstp)
182
{
183
float_status *fpst = fpstp;
184
185
@@ -XXX,XX +XXX,XX @@ uint32_t HELPER(advsimd_f16touinth)(float16 a, void *fpstp)
186
* Square Root and Reciprocal square root
187
*/
188
189
-float16 HELPER(sqrt_f16)(float16 a, void *fpstp)
190
+uint32_t HELPER(sqrt_f16)(uint32_t a, void *fpstp)
191
{
192
float_status *s = fpstp;
193
194
diff --git a/target/arm/helper.c b/target/arm/helper.c
10
diff --git a/target/arm/helper.c b/target/arm/helper.c
195
index XXXXXXX..XXXXXXX 100644
11
index XXXXXXX..XXXXXXX 100644
196
--- a/target/arm/helper.c
12
--- a/target/arm/helper.c
197
+++ b/target/arm/helper.c
13
+++ b/target/arm/helper.c
198
@@ -XXX,XX +XXX,XX @@ DO_VFP_cmp(d, float64)
14
@@ -XXX,XX +XXX,XX @@ static const ARMCPRegInfo debug_cp_reginfo[] = {
199
15
.access = PL1_RW, .accessfn = access_tda,
200
/* Integer to float and float to integer conversions */
16
.fieldoffset = offsetof(CPUARMState, cp15.mdscr_el1),
201
17
.resetvalue = 0 },
202
-#define CONV_ITOF(name, fsz, sign) \
18
- /* MDCCSR_EL0, aka DBGDSCRint. This is a read-only mirror of MDSCR_EL1.
203
- float##fsz HELPER(name)(uint32_t x, void *fpstp) \
19
+ /*
204
-{ \
20
+ * MDCCSR_EL0[30:29] map to EDSCR[30:29]. Simply RAZ as the external
205
- float_status *fpst = fpstp; \
21
+ * Debug Communication Channel is not implemented.
206
- return sign##int32_to_##float##fsz((sign##int32_t)x, fpst); \
22
+ */
207
+#define CONV_ITOF(name, ftype, fsz, sign) \
23
+ { .name = "MDCCSR_EL0", .state = ARM_CP_STATE_AA64,
208
+ftype HELPER(name)(uint32_t x, void *fpstp) \
24
+ .opc0 = 2, .opc1 = 3, .crn = 0, .crm = 1, .opc2 = 0,
209
+{ \
25
+ .access = PL0_R, .accessfn = access_tda,
210
+ float_status *fpst = fpstp; \
26
+ .type = ARM_CP_CONST, .resetvalue = 0 },
211
+ return sign##int32_to_##float##fsz((sign##int32_t)x, fpst); \
27
+ /*
212
}
28
+ * DBGDSCRint[15,12,5:2] map to MDSCR_EL1[15,12,5:2]. Map all bits as
213
29
+ * it is unlikely a guest will care.
214
-#define CONV_FTOI(name, fsz, sign, round) \
30
* We don't implement the configurable EL0 access.
215
-uint32_t HELPER(name)(float##fsz x, void *fpstp) \
31
*/
216
-{ \
32
- { .name = "MDCCSR_EL0", .state = ARM_CP_STATE_BOTH,
217
- float_status *fpst = fpstp; \
33
- .cp = 14, .opc0 = 2, .opc1 = 0, .crn = 0, .crm = 1, .opc2 = 0,
218
- if (float##fsz##_is_any_nan(x)) { \
34
+ { .name = "DBGDSCRint", .state = ARM_CP_STATE_AA32,
219
- float_raise(float_flag_invalid, fpst); \
35
+ .cp = 14, .opc1 = 0, .crn = 0, .crm = 1, .opc2 = 0,
220
- return 0; \
36
.type = ARM_CP_ALIAS,
221
- } \
37
.access = PL1_R, .accessfn = access_tda,
222
- return float##fsz##_to_##sign##int32##round(x, fpst); \
38
.fieldoffset = offsetof(CPUARMState, cp15.mdscr_el1), },
223
+#define CONV_FTOI(name, ftype, fsz, sign, round) \
224
+uint32_t HELPER(name)(ftype x, void *fpstp) \
225
+{ \
226
+ float_status *fpst = fpstp; \
227
+ if (float##fsz##_is_any_nan(x)) { \
228
+ float_raise(float_flag_invalid, fpst); \
229
+ return 0; \
230
+ } \
231
+ return float##fsz##_to_##sign##int32##round(x, fpst); \
232
}
233
234
-#define FLOAT_CONVS(name, p, fsz, sign) \
235
-CONV_ITOF(vfp_##name##to##p, fsz, sign) \
236
-CONV_FTOI(vfp_to##name##p, fsz, sign, ) \
237
-CONV_FTOI(vfp_to##name##z##p, fsz, sign, _round_to_zero)
238
+#define FLOAT_CONVS(name, p, ftype, fsz, sign) \
239
+ CONV_ITOF(vfp_##name##to##p, ftype, fsz, sign) \
240
+ CONV_FTOI(vfp_to##name##p, ftype, fsz, sign, ) \
241
+ CONV_FTOI(vfp_to##name##z##p, ftype, fsz, sign, _round_to_zero)
242
243
-FLOAT_CONVS(si, h, 16, )
244
-FLOAT_CONVS(si, s, 32, )
245
-FLOAT_CONVS(si, d, 64, )
246
-FLOAT_CONVS(ui, h, 16, u)
247
-FLOAT_CONVS(ui, s, 32, u)
248
-FLOAT_CONVS(ui, d, 64, u)
249
+FLOAT_CONVS(si, h, uint32_t, 16, )
250
+FLOAT_CONVS(si, s, float32, 32, )
251
+FLOAT_CONVS(si, d, float64, 64, )
252
+FLOAT_CONVS(ui, h, uint32_t, 16, u)
253
+FLOAT_CONVS(ui, s, float32, 32, u)
254
+FLOAT_CONVS(ui, d, float64, 64, u)
255
256
#undef CONV_ITOF
257
#undef CONV_FTOI
258
@@ -XXX,XX +XXX,XX @@ static float16 do_postscale_fp16(float64 f, int shift, float_status *fpst)
259
return float64_to_float16(float64_scalbn(f, -shift, fpst), true, fpst);
260
}
261
262
-float16 HELPER(vfp_sltoh)(uint32_t x, uint32_t shift, void *fpst)
263
+uint32_t HELPER(vfp_sltoh)(uint32_t x, uint32_t shift, void *fpst)
264
{
265
return do_postscale_fp16(int32_to_float64(x, fpst), shift, fpst);
266
}
267
268
-float16 HELPER(vfp_ultoh)(uint32_t x, uint32_t shift, void *fpst)
269
+uint32_t HELPER(vfp_ultoh)(uint32_t x, uint32_t shift, void *fpst)
270
{
271
return do_postscale_fp16(uint32_to_float64(x, fpst), shift, fpst);
272
}
273
274
-float16 HELPER(vfp_sqtoh)(uint64_t x, uint32_t shift, void *fpst)
275
+uint32_t HELPER(vfp_sqtoh)(uint64_t x, uint32_t shift, void *fpst)
276
{
277
return do_postscale_fp16(int64_to_float64(x, fpst), shift, fpst);
278
}
279
280
-float16 HELPER(vfp_uqtoh)(uint64_t x, uint32_t shift, void *fpst)
281
+uint32_t HELPER(vfp_uqtoh)(uint64_t x, uint32_t shift, void *fpst)
282
{
283
return do_postscale_fp16(uint64_to_float64(x, fpst), shift, fpst);
284
}
285
@@ -XXX,XX +XXX,XX @@ static float64 do_prescale_fp16(float16 f, int shift, float_status *fpst)
286
}
287
}
288
289
-uint32_t HELPER(vfp_toshh)(float16 x, uint32_t shift, void *fpst)
290
+uint32_t HELPER(vfp_toshh)(uint32_t x, uint32_t shift, void *fpst)
291
{
292
return float64_to_int16(do_prescale_fp16(x, shift, fpst), fpst);
293
}
294
295
-uint32_t HELPER(vfp_touhh)(float16 x, uint32_t shift, void *fpst)
296
+uint32_t HELPER(vfp_touhh)(uint32_t x, uint32_t shift, void *fpst)
297
{
298
return float64_to_uint16(do_prescale_fp16(x, shift, fpst), fpst);
299
}
300
301
-uint32_t HELPER(vfp_toslh)(float16 x, uint32_t shift, void *fpst)
302
+uint32_t HELPER(vfp_toslh)(uint32_t x, uint32_t shift, void *fpst)
303
{
304
return float64_to_int32(do_prescale_fp16(x, shift, fpst), fpst);
305
}
306
307
-uint32_t HELPER(vfp_toulh)(float16 x, uint32_t shift, void *fpst)
308
+uint32_t HELPER(vfp_toulh)(uint32_t x, uint32_t shift, void *fpst)
309
{
310
return float64_to_uint32(do_prescale_fp16(x, shift, fpst), fpst);
311
}
312
313
-uint64_t HELPER(vfp_tosqh)(float16 x, uint32_t shift, void *fpst)
314
+uint64_t HELPER(vfp_tosqh)(uint32_t x, uint32_t shift, void *fpst)
315
{
316
return float64_to_int64(do_prescale_fp16(x, shift, fpst), fpst);
317
}
318
319
-uint64_t HELPER(vfp_touqh)(float16 x, uint32_t shift, void *fpst)
320
+uint64_t HELPER(vfp_touqh)(uint32_t x, uint32_t shift, void *fpst)
321
{
322
return float64_to_uint64(do_prescale_fp16(x, shift, fpst), fpst);
323
}
324
@@ -XXX,XX +XXX,XX @@ uint32_t HELPER(set_neon_rmode)(uint32_t rmode, CPUARMState *env)
325
}
326
327
/* Half precision conversions. */
328
-float32 HELPER(vfp_fcvt_f16_to_f32)(float16 a, void *fpstp, uint32_t ahp_mode)
329
+float32 HELPER(vfp_fcvt_f16_to_f32)(uint32_t a, void *fpstp, uint32_t ahp_mode)
330
{
331
/* Squash FZ16 to 0 for the duration of conversion. In this case,
332
* it would affect flushing input denormals.
333
@@ -XXX,XX +XXX,XX @@ float32 HELPER(vfp_fcvt_f16_to_f32)(float16 a, void *fpstp, uint32_t ahp_mode)
334
return r;
335
}
336
337
-float16 HELPER(vfp_fcvt_f32_to_f16)(float32 a, void *fpstp, uint32_t ahp_mode)
338
+uint32_t HELPER(vfp_fcvt_f32_to_f16)(float32 a, void *fpstp, uint32_t ahp_mode)
339
{
340
/* Squash FZ16 to 0 for the duration of conversion. In this case,
341
* it would affect flushing output denormals.
342
@@ -XXX,XX +XXX,XX @@ float16 HELPER(vfp_fcvt_f32_to_f16)(float32 a, void *fpstp, uint32_t ahp_mode)
343
return r;
344
}
345
346
-float64 HELPER(vfp_fcvt_f16_to_f64)(float16 a, void *fpstp, uint32_t ahp_mode)
347
+float64 HELPER(vfp_fcvt_f16_to_f64)(uint32_t a, void *fpstp, uint32_t ahp_mode)
348
{
349
/* Squash FZ16 to 0 for the duration of conversion. In this case,
350
* it would affect flushing input denormals.
351
@@ -XXX,XX +XXX,XX @@ float64 HELPER(vfp_fcvt_f16_to_f64)(float16 a, void *fpstp, uint32_t ahp_mode)
352
return r;
353
}
354
355
-float16 HELPER(vfp_fcvt_f64_to_f16)(float64 a, void *fpstp, uint32_t ahp_mode)
356
+uint32_t HELPER(vfp_fcvt_f64_to_f16)(float64 a, void *fpstp, uint32_t ahp_mode)
357
{
358
/* Squash FZ16 to 0 for the duration of conversion. In this case,
359
* it would affect flushing output denormals.
360
@@ -XXX,XX +XXX,XX @@ static bool round_to_inf(float_status *fpst, bool sign_bit)
361
g_assert_not_reached();
362
}
363
364
-float16 HELPER(recpe_f16)(float16 input, void *fpstp)
365
+uint32_t HELPER(recpe_f16)(uint32_t input, void *fpstp)
366
{
367
float_status *fpst = fpstp;
368
float16 f16 = float16_squash_input_denormal(input, fpst);
369
@@ -XXX,XX +XXX,XX @@ static uint64_t recip_sqrt_estimate(int *exp , int exp_off, uint64_t frac)
370
return extract64(estimate, 0, 8) << 44;
371
}
372
373
-float16 HELPER(rsqrte_f16)(float16 input, void *fpstp)
374
+uint32_t HELPER(rsqrte_f16)(uint32_t input, void *fpstp)
375
{
376
float_status *s = fpstp;
377
float16 f16 = float16_squash_input_denormal(input, s);
378
--
39
--
379
2.17.1
40
2.20.1
380
41
381
42
diff view generated by jsdifflib
1
From: Shannon Zhao <zhaoshenglong@huawei.com>
1
From: Rebecca Cran <rebecca@nuviainc.com>
2
2
3
It forgot to increase clroffset during the loop. So it only clear the
3
Add a space in the message printed when gicr_read*/gicr_write* returns
4
first 4 bytes.
4
MEMTX_ERROR in arm_gicv3_redist.c.
5
5
6
Fixes: 367b9f527becdd20ddf116e17a3c0c2bbc486920
6
Signed-off-by: Rebecca Cran <rebecca@nuviainc.com>
7
Cc: qemu-stable@nongnu.org
7
Reviewed-by: Philippe Mathieu-Daudé <f4bug@amsat.org>
8
Signed-off-by: Shannon Zhao <zhaoshenglong@huawei.com>
8
Message-id: 20210706211432.31902-1-rebecca@nuviainc.com
9
Reviewed-by: Eric Auger <eric.auger@redhat.com>
10
Message-id: 1527047633-12368-1-git-send-email-zhaoshenglong@huawei.com
11
Reviewed-by: Peter Maydell <peter.maydell@linaro.org>
12
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
9
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
13
---
10
---
14
hw/intc/arm_gicv3_kvm.c | 1 +
11
hw/intc/arm_gicv3_redist.c | 4 ++--
15
1 file changed, 1 insertion(+)
12
1 file changed, 2 insertions(+), 2 deletions(-)
16
13
17
diff --git a/hw/intc/arm_gicv3_kvm.c b/hw/intc/arm_gicv3_kvm.c
14
diff --git a/hw/intc/arm_gicv3_redist.c b/hw/intc/arm_gicv3_redist.c
18
index XXXXXXX..XXXXXXX 100644
15
index XXXXXXX..XXXXXXX 100644
19
--- a/hw/intc/arm_gicv3_kvm.c
16
--- a/hw/intc/arm_gicv3_redist.c
20
+++ b/hw/intc/arm_gicv3_kvm.c
17
+++ b/hw/intc/arm_gicv3_redist.c
21
@@ -XXX,XX +XXX,XX @@ static void kvm_dist_putbmp(GICv3State *s, uint32_t offset,
18
@@ -XXX,XX +XXX,XX @@ MemTxResult gicv3_redist_read(void *opaque, hwaddr offset, uint64_t *data,
22
if (clroffset != 0) {
19
if (r == MEMTX_ERROR) {
23
reg = 0;
20
qemu_log_mask(LOG_GUEST_ERROR,
24
kvm_gicd_access(s, clroffset, &reg, true);
21
"%s: invalid guest read at offset " TARGET_FMT_plx
25
+ clroffset += 4;
22
- "size %u\n", __func__, offset, size);
26
}
23
+ " size %u\n", __func__, offset, size);
27
reg = *gic_bmp_ptr32(bmp, irq);
24
trace_gicv3_redist_badread(gicv3_redist_affid(cs), offset,
28
kvm_gicd_access(s, offset, &reg, true);
25
size, attrs.secure);
26
/* The spec requires that reserved registers are RAZ/WI;
27
@@ -XXX,XX +XXX,XX @@ MemTxResult gicv3_redist_write(void *opaque, hwaddr offset, uint64_t data,
28
if (r == MEMTX_ERROR) {
29
qemu_log_mask(LOG_GUEST_ERROR,
30
"%s: invalid guest write at offset " TARGET_FMT_plx
31
- "size %u\n", __func__, offset, size);
32
+ " size %u\n", __func__, offset, size);
33
trace_gicv3_redist_badwrite(gicv3_redist_affid(cs), offset, data,
34
size, attrs.secure);
35
/* The spec requires that reserved registers are RAZ/WI;
29
--
36
--
30
2.17.1
37
2.20.1
31
38
32
39
diff view generated by jsdifflib
Deleted patch
1
From: Paolo Bonzini <pbonzini@redhat.com>
2
1
3
cpregs_keys is an uint32_t* so the allocation should use uint32_t.
4
g_new is even better because it is type-safe.
5
6
Signed-off-by: Paolo Bonzini <pbonzini@redhat.com>
7
Reviewed-by: Peter Maydell <peter.maydell@linaro.org>
8
Reviewed-by: Philippe Mathieu-Daudé <f4bug@amsat.org>
9
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
10
---
11
target/arm/gdbstub.c | 3 +--
12
1 file changed, 1 insertion(+), 2 deletions(-)
13
14
diff --git a/target/arm/gdbstub.c b/target/arm/gdbstub.c
15
index XXXXXXX..XXXXXXX 100644
16
--- a/target/arm/gdbstub.c
17
+++ b/target/arm/gdbstub.c
18
@@ -XXX,XX +XXX,XX @@ int arm_gen_dynamic_xml(CPUState *cs)
19
RegisterSysregXmlParam param = {cs, s};
20
21
cpu->dyn_xml.num_cpregs = 0;
22
- cpu->dyn_xml.cpregs_keys = g_malloc(sizeof(uint32_t *) *
23
- g_hash_table_size(cpu->cp_regs));
24
+ cpu->dyn_xml.cpregs_keys = g_new(uint32_t, g_hash_table_size(cpu->cp_regs));
25
g_string_printf(s, "<?xml version=\"1.0\"?>");
26
g_string_append_printf(s, "<!DOCTYPE target SYSTEM \"gdb-target.dtd\">");
27
g_string_append_printf(s, "<feature name=\"org.qemu.gdb.arm.sys.regs\">");
28
--
29
2.17.1
30
31
diff view generated by jsdifflib
Deleted patch
1
From: Francisco Iglesias <frasse.iglesias@gmail.com>
2
1
3
Coverity found that the string return by 'object_get_canonical_path' was not
4
being freed at two locations in the model (CID 1391294 and CID 1391293) and
5
also that a memset was being called with a value greater than the max of a byte
6
on the second argument (CID 1391286). This patch corrects this by adding the
7
freeing of the strings and also changing to memset to zero instead on
8
descriptor unaligned errors.
9
10
Signed-off-by: Francisco Iglesias <frasse.iglesias@gmail.com>
11
Reviewed-by: Edgar E. Iglesias <edgar.iglesias@xilinx.com>
12
Reviewed-by: Philippe Mathieu-Daudé <f4bug@amsat.org>
13
Message-id: 20180528184859.3530-1-frasse.iglesias@gmail.com
14
Reviewed-by: Peter Maydell <peter.maydell@linaro.org>
15
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
16
---
17
hw/dma/xlnx-zdma.c | 10 +++++++---
18
1 file changed, 7 insertions(+), 3 deletions(-)
19
20
diff --git a/hw/dma/xlnx-zdma.c b/hw/dma/xlnx-zdma.c
21
index XXXXXXX..XXXXXXX 100644
22
--- a/hw/dma/xlnx-zdma.c
23
+++ b/hw/dma/xlnx-zdma.c
24
@@ -XXX,XX +XXX,XX @@ static bool zdma_load_descriptor(XlnxZDMA *s, uint64_t addr, void *buf)
25
qemu_log_mask(LOG_GUEST_ERROR,
26
"zdma: unaligned descriptor at %" PRIx64,
27
addr);
28
- memset(buf, 0xdeadbeef, sizeof(XlnxZDMADescr));
29
+ memset(buf, 0x0, sizeof(XlnxZDMADescr));
30
s->error = true;
31
return false;
32
}
33
@@ -XXX,XX +XXX,XX @@ static uint64_t zdma_read(void *opaque, hwaddr addr, unsigned size)
34
RegisterInfo *r = &s->regs_info[addr / 4];
35
36
if (!r->data) {
37
+ gchar *path = object_get_canonical_path(OBJECT(s));
38
qemu_log("%s: Decode error: read from %" HWADDR_PRIx "\n",
39
- object_get_canonical_path(OBJECT(s)),
40
+ path,
41
addr);
42
+ g_free(path);
43
ARRAY_FIELD_DP32(s->regs, ZDMA_CH_ISR, INV_APB, true);
44
zdma_ch_imr_update_irq(s);
45
return 0;
46
@@ -XXX,XX +XXX,XX @@ static void zdma_write(void *opaque, hwaddr addr, uint64_t value,
47
RegisterInfo *r = &s->regs_info[addr / 4];
48
49
if (!r->data) {
50
+ gchar *path = object_get_canonical_path(OBJECT(s));
51
qemu_log("%s: Decode error: write to %" HWADDR_PRIx "=%" PRIx64 "\n",
52
- object_get_canonical_path(OBJECT(s)),
53
+ path,
54
addr, value);
55
+ g_free(path);
56
ARRAY_FIELD_DP32(s->regs, ZDMA_CH_ISR, INV_APB, true);
57
zdma_ch_imr_update_irq(s);
58
return;
59
--
60
2.17.1
61
62
diff view generated by jsdifflib
Deleted patch
1
In commit f0aff255700 we made cpacr_write() enforce that some CPACR
2
bits are RAZ/WI and some are RAO/WI for ARMv7 cores. Unfortunately
3
we forgot to also update the register's reset value. The effect
4
was that (a) a guest that read CPACR on reset would not see ones in
5
the RAO bits, and (b) if you did a migration before the guest did
6
a write to the CPACR then the migration would fail because the
7
destination would enforce the RAO bits and then complain that they
8
didn't match the zero value from the source.
9
1
10
Implement reset for the CPACR using a custom reset function
11
that just calls cpacr_write(), to avoid having to duplicate
12
the logic for which bits are RAO.
13
14
This bug would affect migration for TCG CPUs which are ARMv7
15
with VFP but without one of Neon or VFPv3.
16
17
Reported-by: Cédric Le Goater <clg@kaod.org>
18
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
19
Tested-by: Cédric Le Goater <clg@kaod.org>
20
Message-id: 20180522173713.26282-1-peter.maydell@linaro.org
21
---
22
target/arm/helper.c | 10 +++++++++-
23
1 file changed, 9 insertions(+), 1 deletion(-)
24
25
diff --git a/target/arm/helper.c b/target/arm/helper.c
26
index XXXXXXX..XXXXXXX 100644
27
--- a/target/arm/helper.c
28
+++ b/target/arm/helper.c
29
@@ -XXX,XX +XXX,XX @@ static void cpacr_write(CPUARMState *env, const ARMCPRegInfo *ri,
30
env->cp15.cpacr_el1 = value;
31
}
32
33
+static void cpacr_reset(CPUARMState *env, const ARMCPRegInfo *ri)
34
+{
35
+ /* Call cpacr_write() so that we reset with the correct RAO bits set
36
+ * for our CPU features.
37
+ */
38
+ cpacr_write(env, ri, 0);
39
+}
40
+
41
static CPAccessResult cpacr_access(CPUARMState *env, const ARMCPRegInfo *ri,
42
bool isread)
43
{
44
@@ -XXX,XX +XXX,XX @@ static const ARMCPRegInfo v6_cp_reginfo[] = {
45
{ .name = "CPACR", .state = ARM_CP_STATE_BOTH, .opc0 = 3,
46
.crn = 1, .crm = 0, .opc1 = 0, .opc2 = 2, .accessfn = cpacr_access,
47
.access = PL1_RW, .fieldoffset = offsetof(CPUARMState, cp15.cpacr_el1),
48
- .resetvalue = 0, .writefn = cpacr_write },
49
+ .resetfn = cpacr_reset, .writefn = cpacr_write },
50
REGINFO_SENTINEL
51
};
52
53
--
54
2.17.1
55
56
diff view generated by jsdifflib
Deleted patch
1
As part of plumbing MemTxAttrs down to the IOMMU translate method,
2
add MemTxAttrs as an argument to address_space_translate()
3
and address_space_translate_cached(). Callers either have an
4
attrs value to hand, or don't care and can use MEMTXATTRS_UNSPECIFIED.
5
1
6
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
7
Reviewed-by: Alex Bennée <alex.bennee@linaro.org>
8
Reviewed-by: Richard Henderson <richard.henderson@linaro.org>
9
Message-id: 20180521140402.23318-4-peter.maydell@linaro.org
10
---
11
include/exec/memory.h | 4 +++-
12
accel/tcg/translate-all.c | 2 +-
13
exec.c | 14 +++++++++-----
14
hw/vfio/common.c | 3 ++-
15
memory_ldst.inc.c | 18 +++++++++---------
16
target/riscv/helper.c | 2 +-
17
6 files changed, 25 insertions(+), 18 deletions(-)
18
19
diff --git a/include/exec/memory.h b/include/exec/memory.h
20
index XXXXXXX..XXXXXXX 100644
21
--- a/include/exec/memory.h
22
+++ b/include/exec/memory.h
23
@@ -XXX,XX +XXX,XX @@ IOMMUTLBEntry address_space_get_iotlb_entry(AddressSpace *as, hwaddr addr,
24
* #MemoryRegion.
25
* @len: pointer to length
26
* @is_write: indicates the transfer direction
27
+ * @attrs: memory attributes
28
*/
29
MemoryRegion *flatview_translate(FlatView *fv,
30
hwaddr addr, hwaddr *xlat,
31
@@ -XXX,XX +XXX,XX @@ MemoryRegion *flatview_translate(FlatView *fv,
32
33
static inline MemoryRegion *address_space_translate(AddressSpace *as,
34
hwaddr addr, hwaddr *xlat,
35
- hwaddr *len, bool is_write)
36
+ hwaddr *len, bool is_write,
37
+ MemTxAttrs attrs)
38
{
39
return flatview_translate(address_space_to_flatview(as),
40
addr, xlat, len, is_write);
41
diff --git a/accel/tcg/translate-all.c b/accel/tcg/translate-all.c
42
index XXXXXXX..XXXXXXX 100644
43
--- a/accel/tcg/translate-all.c
44
+++ b/accel/tcg/translate-all.c
45
@@ -XXX,XX +XXX,XX @@ void tb_invalidate_phys_addr(AddressSpace *as, hwaddr addr, MemTxAttrs attrs)
46
hwaddr l = 1;
47
48
rcu_read_lock();
49
- mr = address_space_translate(as, addr, &addr, &l, false);
50
+ mr = address_space_translate(as, addr, &addr, &l, false, attrs);
51
if (!(memory_region_is_ram(mr)
52
|| memory_region_is_romd(mr))) {
53
rcu_read_unlock();
54
diff --git a/exec.c b/exec.c
55
index XXXXXXX..XXXXXXX 100644
56
--- a/exec.c
57
+++ b/exec.c
58
@@ -XXX,XX +XXX,XX @@ static inline void cpu_physical_memory_write_rom_internal(AddressSpace *as,
59
rcu_read_lock();
60
while (len > 0) {
61
l = len;
62
- mr = address_space_translate(as, addr, &addr1, &l, true);
63
+ mr = address_space_translate(as, addr, &addr1, &l, true,
64
+ MEMTXATTRS_UNSPECIFIED);
65
66
if (!(memory_region_is_ram(mr) ||
67
memory_region_is_romd(mr))) {
68
@@ -XXX,XX +XXX,XX @@ void address_space_cache_destroy(MemoryRegionCache *cache)
69
*/
70
static inline MemoryRegion *address_space_translate_cached(
71
MemoryRegionCache *cache, hwaddr addr, hwaddr *xlat,
72
- hwaddr *plen, bool is_write)
73
+ hwaddr *plen, bool is_write, MemTxAttrs attrs)
74
{
75
MemoryRegionSection section;
76
MemoryRegion *mr;
77
@@ -XXX,XX +XXX,XX @@ address_space_read_cached_slow(MemoryRegionCache *cache, hwaddr addr,
78
MemoryRegion *mr;
79
80
l = len;
81
- mr = address_space_translate_cached(cache, addr, &addr1, &l, false);
82
+ mr = address_space_translate_cached(cache, addr, &addr1, &l, false,
83
+ MEMTXATTRS_UNSPECIFIED);
84
flatview_read_continue(cache->fv,
85
addr, MEMTXATTRS_UNSPECIFIED, buf, len,
86
addr1, l, mr);
87
@@ -XXX,XX +XXX,XX @@ address_space_write_cached_slow(MemoryRegionCache *cache, hwaddr addr,
88
MemoryRegion *mr;
89
90
l = len;
91
- mr = address_space_translate_cached(cache, addr, &addr1, &l, true);
92
+ mr = address_space_translate_cached(cache, addr, &addr1, &l, true,
93
+ MEMTXATTRS_UNSPECIFIED);
94
flatview_write_continue(cache->fv,
95
addr, MEMTXATTRS_UNSPECIFIED, buf, len,
96
addr1, l, mr);
97
@@ -XXX,XX +XXX,XX @@ bool cpu_physical_memory_is_io(hwaddr phys_addr)
98
99
rcu_read_lock();
100
mr = address_space_translate(&address_space_memory,
101
- phys_addr, &phys_addr, &l, false);
102
+ phys_addr, &phys_addr, &l, false,
103
+ MEMTXATTRS_UNSPECIFIED);
104
105
res = !(memory_region_is_ram(mr) || memory_region_is_romd(mr));
106
rcu_read_unlock();
107
diff --git a/hw/vfio/common.c b/hw/vfio/common.c
108
index XXXXXXX..XXXXXXX 100644
109
--- a/hw/vfio/common.c
110
+++ b/hw/vfio/common.c
111
@@ -XXX,XX +XXX,XX @@ static bool vfio_get_vaddr(IOMMUTLBEntry *iotlb, void **vaddr,
112
*/
113
mr = address_space_translate(&address_space_memory,
114
iotlb->translated_addr,
115
- &xlat, &len, writable);
116
+ &xlat, &len, writable,
117
+ MEMTXATTRS_UNSPECIFIED);
118
if (!memory_region_is_ram(mr)) {
119
error_report("iommu map to non memory area %"HWADDR_PRIx"",
120
xlat);
121
diff --git a/memory_ldst.inc.c b/memory_ldst.inc.c
122
index XXXXXXX..XXXXXXX 100644
123
--- a/memory_ldst.inc.c
124
+++ b/memory_ldst.inc.c
125
@@ -XXX,XX +XXX,XX @@ static inline uint32_t glue(address_space_ldl_internal, SUFFIX)(ARG1_DECL,
126
bool release_lock = false;
127
128
RCU_READ_LOCK();
129
- mr = TRANSLATE(addr, &addr1, &l, false);
130
+ mr = TRANSLATE(addr, &addr1, &l, false, attrs);
131
if (l < 4 || !IS_DIRECT(mr, false)) {
132
release_lock |= prepare_mmio_access(mr);
133
134
@@ -XXX,XX +XXX,XX @@ static inline uint64_t glue(address_space_ldq_internal, SUFFIX)(ARG1_DECL,
135
bool release_lock = false;
136
137
RCU_READ_LOCK();
138
- mr = TRANSLATE(addr, &addr1, &l, false);
139
+ mr = TRANSLATE(addr, &addr1, &l, false, attrs);
140
if (l < 8 || !IS_DIRECT(mr, false)) {
141
release_lock |= prepare_mmio_access(mr);
142
143
@@ -XXX,XX +XXX,XX @@ uint32_t glue(address_space_ldub, SUFFIX)(ARG1_DECL,
144
bool release_lock = false;
145
146
RCU_READ_LOCK();
147
- mr = TRANSLATE(addr, &addr1, &l, false);
148
+ mr = TRANSLATE(addr, &addr1, &l, false, attrs);
149
if (!IS_DIRECT(mr, false)) {
150
release_lock |= prepare_mmio_access(mr);
151
152
@@ -XXX,XX +XXX,XX @@ static inline uint32_t glue(address_space_lduw_internal, SUFFIX)(ARG1_DECL,
153
bool release_lock = false;
154
155
RCU_READ_LOCK();
156
- mr = TRANSLATE(addr, &addr1, &l, false);
157
+ mr = TRANSLATE(addr, &addr1, &l, false, attrs);
158
if (l < 2 || !IS_DIRECT(mr, false)) {
159
release_lock |= prepare_mmio_access(mr);
160
161
@@ -XXX,XX +XXX,XX @@ void glue(address_space_stl_notdirty, SUFFIX)(ARG1_DECL,
162
bool release_lock = false;
163
164
RCU_READ_LOCK();
165
- mr = TRANSLATE(addr, &addr1, &l, true);
166
+ mr = TRANSLATE(addr, &addr1, &l, true, attrs);
167
if (l < 4 || !IS_DIRECT(mr, true)) {
168
release_lock |= prepare_mmio_access(mr);
169
170
@@ -XXX,XX +XXX,XX @@ static inline void glue(address_space_stl_internal, SUFFIX)(ARG1_DECL,
171
bool release_lock = false;
172
173
RCU_READ_LOCK();
174
- mr = TRANSLATE(addr, &addr1, &l, true);
175
+ mr = TRANSLATE(addr, &addr1, &l, true, attrs);
176
if (l < 4 || !IS_DIRECT(mr, true)) {
177
release_lock |= prepare_mmio_access(mr);
178
179
@@ -XXX,XX +XXX,XX @@ void glue(address_space_stb, SUFFIX)(ARG1_DECL,
180
bool release_lock = false;
181
182
RCU_READ_LOCK();
183
- mr = TRANSLATE(addr, &addr1, &l, true);
184
+ mr = TRANSLATE(addr, &addr1, &l, true, attrs);
185
if (!IS_DIRECT(mr, true)) {
186
release_lock |= prepare_mmio_access(mr);
187
r = memory_region_dispatch_write(mr, addr1, val, 1, attrs);
188
@@ -XXX,XX +XXX,XX @@ static inline void glue(address_space_stw_internal, SUFFIX)(ARG1_DECL,
189
bool release_lock = false;
190
191
RCU_READ_LOCK();
192
- mr = TRANSLATE(addr, &addr1, &l, true);
193
+ mr = TRANSLATE(addr, &addr1, &l, true, attrs);
194
if (l < 2 || !IS_DIRECT(mr, true)) {
195
release_lock |= prepare_mmio_access(mr);
196
197
@@ -XXX,XX +XXX,XX @@ static void glue(address_space_stq_internal, SUFFIX)(ARG1_DECL,
198
bool release_lock = false;
199
200
RCU_READ_LOCK();
201
- mr = TRANSLATE(addr, &addr1, &l, true);
202
+ mr = TRANSLATE(addr, &addr1, &l, true, attrs);
203
if (l < 8 || !IS_DIRECT(mr, true)) {
204
release_lock |= prepare_mmio_access(mr);
205
206
diff --git a/target/riscv/helper.c b/target/riscv/helper.c
207
index XXXXXXX..XXXXXXX 100644
208
--- a/target/riscv/helper.c
209
+++ b/target/riscv/helper.c
210
@@ -XXX,XX +XXX,XX @@ restart:
211
MemoryRegion *mr;
212
hwaddr l = sizeof(target_ulong), addr1;
213
mr = address_space_translate(cs->as, pte_addr,
214
- &addr1, &l, false);
215
+ &addr1, &l, false, MEMTXATTRS_UNSPECIFIED);
216
if (memory_access_is_direct(mr, true)) {
217
target_ulong *pte_pa =
218
qemu_map_ram_ptr(mr->ram_block, addr1);
219
--
220
2.17.1
221
222
diff view generated by jsdifflib
Deleted patch
1
As part of plumbing MemTxAttrs down to the IOMMU translate method,
2
add MemTxAttrs as an argument to address_space_access_valid().
3
Its callers either have an attrs value to hand, or don't care
4
and can use MEMTXATTRS_UNSPECIFIED.
5
1
6
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
7
Reviewed-by: Alex Bennée <alex.bennee@linaro.org>
8
Reviewed-by: Richard Henderson <richard.henderson@linaro.org>
9
Message-id: 20180521140402.23318-6-peter.maydell@linaro.org
10
---
11
include/exec/memory.h | 4 +++-
12
include/sysemu/dma.h | 3 ++-
13
exec.c | 3 ++-
14
target/s390x/diag.c | 6 ++++--
15
target/s390x/excp_helper.c | 3 ++-
16
target/s390x/mmu_helper.c | 3 ++-
17
target/s390x/sigp.c | 3 ++-
18
7 files changed, 17 insertions(+), 8 deletions(-)
19
20
diff --git a/include/exec/memory.h b/include/exec/memory.h
21
index XXXXXXX..XXXXXXX 100644
22
--- a/include/exec/memory.h
23
+++ b/include/exec/memory.h
24
@@ -XXX,XX +XXX,XX @@ static inline MemoryRegion *address_space_translate(AddressSpace *as,
25
* @addr: address within that address space
26
* @len: length of the area to be checked
27
* @is_write: indicates the transfer direction
28
+ * @attrs: memory attributes
29
*/
30
-bool address_space_access_valid(AddressSpace *as, hwaddr addr, int len, bool is_write);
31
+bool address_space_access_valid(AddressSpace *as, hwaddr addr, int len,
32
+ bool is_write, MemTxAttrs attrs);
33
34
/* address_space_map: map a physical memory region into a host virtual address
35
*
36
diff --git a/include/sysemu/dma.h b/include/sysemu/dma.h
37
index XXXXXXX..XXXXXXX 100644
38
--- a/include/sysemu/dma.h
39
+++ b/include/sysemu/dma.h
40
@@ -XXX,XX +XXX,XX @@ static inline bool dma_memory_valid(AddressSpace *as,
41
DMADirection dir)
42
{
43
return address_space_access_valid(as, addr, len,
44
- dir == DMA_DIRECTION_FROM_DEVICE);
45
+ dir == DMA_DIRECTION_FROM_DEVICE,
46
+ MEMTXATTRS_UNSPECIFIED);
47
}
48
49
static inline int dma_memory_rw_relaxed(AddressSpace *as, dma_addr_t addr,
50
diff --git a/exec.c b/exec.c
51
index XXXXXXX..XXXXXXX 100644
52
--- a/exec.c
53
+++ b/exec.c
54
@@ -XXX,XX +XXX,XX @@ static bool flatview_access_valid(FlatView *fv, hwaddr addr, int len,
55
}
56
57
bool address_space_access_valid(AddressSpace *as, hwaddr addr,
58
- int len, bool is_write)
59
+ int len, bool is_write,
60
+ MemTxAttrs attrs)
61
{
62
FlatView *fv;
63
bool result;
64
diff --git a/target/s390x/diag.c b/target/s390x/diag.c
65
index XXXXXXX..XXXXXXX 100644
66
--- a/target/s390x/diag.c
67
+++ b/target/s390x/diag.c
68
@@ -XXX,XX +XXX,XX @@ void handle_diag_308(CPUS390XState *env, uint64_t r1, uint64_t r3, uintptr_t ra)
69
return;
70
}
71
if (!address_space_access_valid(&address_space_memory, addr,
72
- sizeof(IplParameterBlock), false)) {
73
+ sizeof(IplParameterBlock), false,
74
+ MEMTXATTRS_UNSPECIFIED)) {
75
s390_program_interrupt(env, PGM_ADDRESSING, ILEN_AUTO, ra);
76
return;
77
}
78
@@ -XXX,XX +XXX,XX @@ out:
79
return;
80
}
81
if (!address_space_access_valid(&address_space_memory, addr,
82
- sizeof(IplParameterBlock), true)) {
83
+ sizeof(IplParameterBlock), true,
84
+ MEMTXATTRS_UNSPECIFIED)) {
85
s390_program_interrupt(env, PGM_ADDRESSING, ILEN_AUTO, ra);
86
return;
87
}
88
diff --git a/target/s390x/excp_helper.c b/target/s390x/excp_helper.c
89
index XXXXXXX..XXXXXXX 100644
90
--- a/target/s390x/excp_helper.c
91
+++ b/target/s390x/excp_helper.c
92
@@ -XXX,XX +XXX,XX @@ int s390_cpu_handle_mmu_fault(CPUState *cs, vaddr orig_vaddr, int size,
93
94
/* check out of RAM access */
95
if (!address_space_access_valid(&address_space_memory, raddr,
96
- TARGET_PAGE_SIZE, rw)) {
97
+ TARGET_PAGE_SIZE, rw,
98
+ MEMTXATTRS_UNSPECIFIED)) {
99
DPRINTF("%s: raddr %" PRIx64 " > ram_size %" PRIx64 "\n", __func__,
100
(uint64_t)raddr, (uint64_t)ram_size);
101
trigger_pgm_exception(env, PGM_ADDRESSING, ILEN_AUTO);
102
diff --git a/target/s390x/mmu_helper.c b/target/s390x/mmu_helper.c
103
index XXXXXXX..XXXXXXX 100644
104
--- a/target/s390x/mmu_helper.c
105
+++ b/target/s390x/mmu_helper.c
106
@@ -XXX,XX +XXX,XX @@ static int translate_pages(S390CPU *cpu, vaddr addr, int nr_pages,
107
return ret;
108
}
109
if (!address_space_access_valid(&address_space_memory, pages[i],
110
- TARGET_PAGE_SIZE, is_write)) {
111
+ TARGET_PAGE_SIZE, is_write,
112
+ MEMTXATTRS_UNSPECIFIED)) {
113
trigger_access_exception(env, PGM_ADDRESSING, ILEN_AUTO, 0);
114
return -EFAULT;
115
}
116
diff --git a/target/s390x/sigp.c b/target/s390x/sigp.c
117
index XXXXXXX..XXXXXXX 100644
118
--- a/target/s390x/sigp.c
119
+++ b/target/s390x/sigp.c
120
@@ -XXX,XX +XXX,XX @@ static void sigp_set_prefix(CPUState *cs, run_on_cpu_data arg)
121
cpu_synchronize_state(cs);
122
123
if (!address_space_access_valid(&address_space_memory, addr,
124
- sizeof(struct LowCore), false)) {
125
+ sizeof(struct LowCore), false,
126
+ MEMTXATTRS_UNSPECIFIED)) {
127
set_sigp_status(si, SIGP_STAT_INVALID_PARAMETER);
128
return;
129
}
130
--
131
2.17.1
132
133
diff view generated by jsdifflib
Deleted patch
1
As part of plumbing MemTxAttrs down to the IOMMU translate method,
2
add MemTxAttrs as an argument to flatview_extend_translation().
3
Its callers either have an attrs value to hand, or don't care
4
and can use MEMTXATTRS_UNSPECIFIED.
5
1
6
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
7
Reviewed-by: Alex Bennée <alex.bennee@linaro.org>
8
Reviewed-by: Richard Henderson <richard.henderson@linaro.org>
9
Message-id: 20180521140402.23318-7-peter.maydell@linaro.org
10
---
11
exec.c | 15 ++++++++++-----
12
1 file changed, 10 insertions(+), 5 deletions(-)
13
14
diff --git a/exec.c b/exec.c
15
index XXXXXXX..XXXXXXX 100644
16
--- a/exec.c
17
+++ b/exec.c
18
@@ -XXX,XX +XXX,XX @@ bool address_space_access_valid(AddressSpace *as, hwaddr addr,
19
20
static hwaddr
21
flatview_extend_translation(FlatView *fv, hwaddr addr,
22
- hwaddr target_len,
23
- MemoryRegion *mr, hwaddr base, hwaddr len,
24
- bool is_write)
25
+ hwaddr target_len,
26
+ MemoryRegion *mr, hwaddr base, hwaddr len,
27
+ bool is_write, MemTxAttrs attrs)
28
{
29
hwaddr done = 0;
30
hwaddr xlat;
31
@@ -XXX,XX +XXX,XX @@ void *address_space_map(AddressSpace *as,
32
33
memory_region_ref(mr);
34
*plen = flatview_extend_translation(fv, addr, len, mr, xlat,
35
- l, is_write);
36
+ l, is_write, attrs);
37
ptr = qemu_ram_ptr_length(mr->ram_block, xlat, plen, true);
38
rcu_read_unlock();
39
40
@@ -XXX,XX +XXX,XX @@ int64_t address_space_cache_init(MemoryRegionCache *cache,
41
mr = cache->mrs.mr;
42
memory_region_ref(mr);
43
if (memory_access_is_direct(mr, is_write)) {
44
+ /* We don't care about the memory attributes here as we're only
45
+ * doing this if we found actual RAM, which behaves the same
46
+ * regardless of attributes; so UNSPECIFIED is fine.
47
+ */
48
l = flatview_extend_translation(cache->fv, addr, len, mr,
49
- cache->xlat, l, is_write);
50
+ cache->xlat, l, is_write,
51
+ MEMTXATTRS_UNSPECIFIED);
52
cache->ptr = qemu_ram_ptr_length(mr->ram_block, cache->xlat, &l, true);
53
} else {
54
cache->ptr = NULL;
55
--
56
2.17.1
57
58
diff view generated by jsdifflib
Deleted patch
1
As part of plumbing MemTxAttrs down to the IOMMU translate method,
2
add MemTxAttrs as an argument to memory_region_access_valid().
3
Its callers either have an attrs value to hand, or don't care
4
and can use MEMTXATTRS_UNSPECIFIED.
5
1
6
The callsite in flatview_access_valid() is part of a recursive
7
loop flatview_access_valid() -> memory_region_access_valid() ->
8
subpage_accepts() -> flatview_access_valid(); we make it pass
9
MEMTXATTRS_UNSPECIFIED for now, until the next several commits
10
have plumbed an attrs parameter through the rest of the loop
11
and we can add an attrs parameter to flatview_access_valid().
12
13
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
14
Reviewed-by: Alex Bennée <alex.bennee@linaro.org>
15
Reviewed-by: Richard Henderson <richard.henderson@linaro.org>
16
Message-id: 20180521140402.23318-8-peter.maydell@linaro.org
17
---
18
include/exec/memory-internal.h | 3 ++-
19
exec.c | 4 +++-
20
hw/s390x/s390-pci-inst.c | 3 ++-
21
memory.c | 7 ++++---
22
4 files changed, 11 insertions(+), 6 deletions(-)
23
24
diff --git a/include/exec/memory-internal.h b/include/exec/memory-internal.h
25
index XXXXXXX..XXXXXXX 100644
26
--- a/include/exec/memory-internal.h
27
+++ b/include/exec/memory-internal.h
28
@@ -XXX,XX +XXX,XX @@ void flatview_unref(FlatView *view);
29
extern const MemoryRegionOps unassigned_mem_ops;
30
31
bool memory_region_access_valid(MemoryRegion *mr, hwaddr addr,
32
- unsigned size, bool is_write);
33
+ unsigned size, bool is_write,
34
+ MemTxAttrs attrs);
35
36
void flatview_add_to_dispatch(FlatView *fv, MemoryRegionSection *section);
37
AddressSpaceDispatch *address_space_dispatch_new(FlatView *fv);
38
diff --git a/exec.c b/exec.c
39
index XXXXXXX..XXXXXXX 100644
40
--- a/exec.c
41
+++ b/exec.c
42
@@ -XXX,XX +XXX,XX @@ static bool flatview_access_valid(FlatView *fv, hwaddr addr, int len,
43
mr = flatview_translate(fv, addr, &xlat, &l, is_write);
44
if (!memory_access_is_direct(mr, is_write)) {
45
l = memory_access_size(mr, l, addr);
46
- if (!memory_region_access_valid(mr, xlat, l, is_write)) {
47
+ /* When our callers all have attrs we'll pass them through here */
48
+ if (!memory_region_access_valid(mr, xlat, l, is_write,
49
+ MEMTXATTRS_UNSPECIFIED)) {
50
return false;
51
}
52
}
53
diff --git a/hw/s390x/s390-pci-inst.c b/hw/s390x/s390-pci-inst.c
54
index XXXXXXX..XXXXXXX 100644
55
--- a/hw/s390x/s390-pci-inst.c
56
+++ b/hw/s390x/s390-pci-inst.c
57
@@ -XXX,XX +XXX,XX @@ int pcistb_service_call(S390CPU *cpu, uint8_t r1, uint8_t r3, uint64_t gaddr,
58
mr = s390_get_subregion(mr, offset, len);
59
offset -= mr->addr;
60
61
- if (!memory_region_access_valid(mr, offset, len, true)) {
62
+ if (!memory_region_access_valid(mr, offset, len, true,
63
+ MEMTXATTRS_UNSPECIFIED)) {
64
s390_program_interrupt(env, PGM_OPERAND, 6, ra);
65
return 0;
66
}
67
diff --git a/memory.c b/memory.c
68
index XXXXXXX..XXXXXXX 100644
69
--- a/memory.c
70
+++ b/memory.c
71
@@ -XXX,XX +XXX,XX @@ static const MemoryRegionOps ram_device_mem_ops = {
72
bool memory_region_access_valid(MemoryRegion *mr,
73
hwaddr addr,
74
unsigned size,
75
- bool is_write)
76
+ bool is_write,
77
+ MemTxAttrs attrs)
78
{
79
int access_size_min, access_size_max;
80
int access_size, i;
81
@@ -XXX,XX +XXX,XX @@ MemTxResult memory_region_dispatch_read(MemoryRegion *mr,
82
{
83
MemTxResult r;
84
85
- if (!memory_region_access_valid(mr, addr, size, false)) {
86
+ if (!memory_region_access_valid(mr, addr, size, false, attrs)) {
87
*pval = unassigned_mem_read(mr, addr, size);
88
return MEMTX_DECODE_ERROR;
89
}
90
@@ -XXX,XX +XXX,XX @@ MemTxResult memory_region_dispatch_write(MemoryRegion *mr,
91
unsigned size,
92
MemTxAttrs attrs)
93
{
94
- if (!memory_region_access_valid(mr, addr, size, true)) {
95
+ if (!memory_region_access_valid(mr, addr, size, true, attrs)) {
96
unassigned_mem_write(mr, addr, data, size);
97
return MEMTX_DECODE_ERROR;
98
}
99
--
100
2.17.1
101
102
diff view generated by jsdifflib
Deleted patch
1
As part of plumbing MemTxAttrs down to the IOMMU translate method,
2
add MemTxAttrs as an argument to address_space_get_iotlb_entry().
3
1
4
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
5
Reviewed-by: Alex Bennée <alex.bennee@linaro.org>
6
Reviewed-by: Richard Henderson <richard.henderson@linaro.org>
7
Message-id: 20180521140402.23318-12-peter.maydell@linaro.org
8
---
9
include/exec/memory.h | 2 +-
10
exec.c | 2 +-
11
hw/virtio/vhost.c | 3 ++-
12
3 files changed, 4 insertions(+), 3 deletions(-)
13
14
diff --git a/include/exec/memory.h b/include/exec/memory.h
15
index XXXXXXX..XXXXXXX 100644
16
--- a/include/exec/memory.h
17
+++ b/include/exec/memory.h
18
@@ -XXX,XX +XXX,XX @@ void address_space_cache_destroy(MemoryRegionCache *cache);
19
* entry. Should be called from an RCU critical section.
20
*/
21
IOMMUTLBEntry address_space_get_iotlb_entry(AddressSpace *as, hwaddr addr,
22
- bool is_write);
23
+ bool is_write, MemTxAttrs attrs);
24
25
/* address_space_translate: translate an address range into an address space
26
* into a MemoryRegion and an address range into that section. Should be
27
diff --git a/exec.c b/exec.c
28
index XXXXXXX..XXXXXXX 100644
29
--- a/exec.c
30
+++ b/exec.c
31
@@ -XXX,XX +XXX,XX @@ static MemoryRegionSection flatview_do_translate(FlatView *fv,
32
33
/* Called from RCU critical section */
34
IOMMUTLBEntry address_space_get_iotlb_entry(AddressSpace *as, hwaddr addr,
35
- bool is_write)
36
+ bool is_write, MemTxAttrs attrs)
37
{
38
MemoryRegionSection section;
39
hwaddr xlat, page_mask;
40
diff --git a/hw/virtio/vhost.c b/hw/virtio/vhost.c
41
index XXXXXXX..XXXXXXX 100644
42
--- a/hw/virtio/vhost.c
43
+++ b/hw/virtio/vhost.c
44
@@ -XXX,XX +XXX,XX @@ int vhost_device_iotlb_miss(struct vhost_dev *dev, uint64_t iova, int write)
45
trace_vhost_iotlb_miss(dev, 1);
46
47
iotlb = address_space_get_iotlb_entry(dev->vdev->dma_as,
48
- iova, write);
49
+ iova, write,
50
+ MEMTXATTRS_UNSPECIFIED);
51
if (iotlb.target_as != NULL) {
52
ret = vhost_memory_region_lookup(dev, iotlb.translated_addr,
53
&uaddr, &len);
54
--
55
2.17.1
56
57
diff view generated by jsdifflib