@samitouri / QOSamiQemu / commits / dd6bee2707

hppa: Introduce HPPACPUDef

Restructures the CPU class heirarchy to clarify model names and allow for per-model configuration options via HPPACPUDef. 32-bit HPPA is assumed to run a PA-7300LC, and 64-bit assumed to run a PA-8700. A new PA-8500 model is added, which will later be used by the A400 machine. All CPU models are made into children of the now abstract TYPE_HPPA_CPU base class. Two fields are added to HPPACPUDef describing the size of the physical address space, and whether or not the CPU uses the PA-RISC 2.0 architecture. The latter was previously a field in CPUHPPAState. phys_addr_bits is currently set but unused, and will be used in the following commit. Likewise, PA-8700 is moved to use 44 bit physical addresses in a followup commit to not break bisection. References to "hppa/hppa64" models in test cases are also updated. Reviewed-by: Helge Deller <deller@gmx.de> Signed-off-by: Anton Johansson <anjo@rev.ng> Reviewed-by: Philippe Mathieu-Daudé <philmd@linaro.org> Message-ID: <20260305-hppa-c3600-v6-1-d51526e5269c@rev.ng> Signed-off-by: Philippe Mathieu-Daudé <philmd@linaro.org>

Anton Johansson committed Mar 5, 2026 at 23:54 UTC dd6bee2707c9f34271ec666d52e0086c77a6d813
6 files changed +80 -27
hw/hppa/machine.c
+13 -8
@@ -801,13 +801,13 @@ static void hppa_machine_common_class_init(ObjectClass *oc, const void *data)
801 static void HP_B160L_machine_init_class_init(ObjectClass *oc, const void *data)
802 {
803 static const char * const valid_cpu_types[] = {
804 - TYPE_HPPA_CPU,
804 + TYPE_HPPA_CPU_PA_7300LC,
805 NULL
806 };
807 MachineClass *mc = MACHINE_CLASS(oc);
808
809 mc->desc = "HP B160L workstation";
810 - mc->default_cpu_type = TYPE_HPPA_CPU;
810 + mc->default_cpu_type = TYPE_HPPA_CPU_PA_7300LC;
811 mc->valid_cpu_types = valid_cpu_types;
812 mc->init = machine_HP_B160L_init;
813 mc->is_default = true;
@@ -817,13 +817,13 @@ static void HP_B160L_machine_init_class_init(ObjectClass *oc, const void *data)
817 static void HP_C3700_machine_init_class_init(ObjectClass *oc, const void *data)
818 {
819 static const char * const valid_cpu_types[] = {
820 - TYPE_HPPA64_CPU,
820 + TYPE_HPPA_CPU_PA_8700,
821 NULL
822 };
823 MachineClass *mc = MACHINE_CLASS(oc);
824
825 mc->desc = "HP C3700 workstation";
826 - mc->default_cpu_type = TYPE_HPPA64_CPU;
826 + mc->default_cpu_type = TYPE_HPPA_CPU_PA_8700;
827 mc->valid_cpu_types = valid_cpu_types;
828 mc->init = machine_HP_C3700_init;
829 mc->max_cpus = HPPA_MAX_CPUS;
@@ -833,13 +833,13 @@ static void HP_C3700_machine_init_class_init(ObjectClass *oc, const void *data)
833 static void HP_A400_machine_init_class_init(ObjectClass *oc, const void *data)
834 {
835 static const char * const valid_cpu_types[] = {
836 - TYPE_HPPA64_CPU,
836 + TYPE_HPPA_CPU_PA_8500,
837 NULL
838 };
839 MachineClass *mc = MACHINE_CLASS(oc);
840
841 mc->desc = "HP A400-44 workstation";
842 - mc->default_cpu_type = TYPE_HPPA64_CPU;
842 + mc->default_cpu_type = TYPE_HPPA_CPU_PA_8500;
843 mc->valid_cpu_types = valid_cpu_types;
844 mc->init = machine_HP_A400_init;
845 mc->max_cpus = HPPA_MAX_CPUS;
@@ -849,13 +849,18 @@ static void HP_A400_machine_init_class_init(ObjectClass *oc, const void *data)
849 static void HP_715_machine_init_class_init(ObjectClass *oc, const void *data)
850 {
851 static const char * const valid_cpu_types[] = {
852 - TYPE_HPPA_CPU,
852 + TYPE_HPPA_CPU_PA_7300LC,
853 NULL
854 };
855 MachineClass *mc = MACHINE_CLASS(oc);
856
857 mc->desc = "HP 715/64 workstation";
858 - mc->default_cpu_type = TYPE_HPPA_CPU;
858 + /*
859 + * Although the 715 workstation should use a 7100LC, it can be safely
860 + * modeled as a 7300LC as the difference is a moving of the L1 data cache
861 + * to on-chip.
862 + */
863 + mc->default_cpu_type = TYPE_HPPA_CPU_PA_7300LC;
864 mc->valid_cpu_types = valid_cpu_types;
865 mc->init = machine_HP_715_init;
866 /* can only support up to max. 8 CPUs due inventory major numbers */
linux-user/hppa/elfload.c
+1 -1
@@ -8,7 +8,7 @@
8
9 const char *get_elf_cpu_model(uint32_t eflags)
10 {
11 - return "hppa";
11 + return "pa-7300lc";
12 }
13
14 const char *get_elf_platform(CPUState *cs)
target/hppa/cpu-qom.h
+7 -1
@@ -23,7 +23,13 @@
23 #include "hw/core/cpu.h"
24
25 #define TYPE_HPPA_CPU "hppa-cpu"
26 -#define TYPE_HPPA64_CPU "hppa64-cpu"
26 +
27 +#define HPPA_CPU_TYPE_SUFFIX "-" TYPE_HPPA_CPU
28 +#define HPPA_CPU_TYPE_NAME(name) (name HPPA_CPU_TYPE_SUFFIX)
29 +
30 +#define TYPE_HPPA_CPU_PA_7300LC HPPA_CPU_TYPE_NAME("pa-7300lc")
31 +#define TYPE_HPPA_CPU_PA_8500 HPPA_CPU_TYPE_NAME("pa-8500")
32 +#define TYPE_HPPA_CPU_PA_8700 HPPA_CPU_TYPE_NAME("pa-8700")
33
34 OBJECT_DECLARE_CPU_TYPE(HPPACPU, HPPACPUClass, HPPA_CPU)
35
target/hppa/cpu.c
+38 -12
@@ -203,13 +203,6 @@ static void hppa_cpu_realizefn(DeviceState *dev, Error **errp)
203 tcg_cflags_set(cs, CF_PCREL);
204 }
205
206 -static void hppa_cpu_initfn(Object *obj)
207 -{
208 - CPUHPPAState *env = cpu_env(CPU(obj));
209 -
210 - env->is_pa20 = !!object_dynamic_cast(obj, TYPE_HPPA64_CPU);
211 -}
212 -
206 static void hppa_cpu_reset_hold(Object *obj, ResetType type)
207 {
208 HPPACPUClass *scc = HPPA_CPU_GET_CLASS(obj);
@@ -236,9 +229,14 @@ static void hppa_cpu_reset_hold(Object *obj, ResetType type)
229
230 static ObjectClass *hppa_cpu_class_by_name(const char *cpu_model)
231 {
239 - g_autofree char *typename = g_strconcat(cpu_model, "-cpu", NULL);
232 + ObjectClass *oc;
233 + char *typename;
234
241 - return object_class_by_name(typename);
235 + typename = g_strdup_printf(HPPA_CPU_TYPE_NAME("%s"), cpu_model);
236 + oc = object_class_by_name(typename);
237 + g_free(typename);
238 +
239 + return oc;
240 }
241
242 #ifndef CONFIG_USER_ONLY
@@ -279,6 +277,14 @@ static const TCGCPUOps hppa_tcg_ops = {
277 #endif /* !CONFIG_USER_ONLY */
278 };
279
280 +static void hppa_cpu_class_base_init(ObjectClass *oc, const void *data)
281 +{
282 + HPPACPUClass *acc = HPPA_CPU_CLASS(oc);
283 + /* Make sure all CPU models define a HPPACPUDef */
284 + g_assert(!object_class_is_abstract(oc) && data != NULL);
285 + acc->def = data;
286 +}
287 +
288 static void hppa_cpu_class_init(ObjectClass *oc, const void *data)
289 {
290 DeviceClass *dc = DEVICE_CLASS(oc);
@@ -313,14 +319,34 @@ static const TypeInfo hppa_cpu_type_infos[] = {
319 .parent = TYPE_CPU,
320 .instance_size = sizeof(HPPACPU),
321 .instance_align = __alignof(HPPACPU),
316 - .instance_init = hppa_cpu_initfn,
317 - .abstract = false,
322 + .abstract = true,
323 .class_size = sizeof(HPPACPUClass),
324 .class_init = hppa_cpu_class_init,
325 + .class_base_init = hppa_cpu_class_base_init,
326 + },
327 + {
328 + .name = TYPE_HPPA_CPU_PA_7300LC,
329 + .parent = TYPE_HPPA_CPU,
330 + .class_data = &(const HPPACPUDef) {
331 + .phys_addr_bits = 32,
332 + .is_pa20 = false,
333 + },
334 + },
335 + {
336 + .name = TYPE_HPPA_CPU_PA_8500,
337 + .parent = TYPE_HPPA_CPU,
338 + .class_data = &(const HPPACPUDef) {
339 + .phys_addr_bits = 40,
340 + .is_pa20 = true,
341 + },
342 },
343 {
322 - .name = TYPE_HPPA64_CPU,
344 + .name = TYPE_HPPA_CPU_PA_8700,
345 .parent = TYPE_HPPA_CPU,
346 + .class_data = &(const HPPACPUDef) {
347 + .phys_addr_bits = 40,
348 + .is_pa20 = true,
349 + },
350 },
351 };
352
target/hppa/cpu.h
+20 -4
@@ -270,8 +270,6 @@ typedef struct CPUArchState {
270 /* Fields up to this point are cleared by a CPU reset */
271 struct {} end_reset_fields;
272
273 - bool is_pa20;
274 -
273 target_ulong kernel_entry; /* Linux kernel was loaded here */
274 target_ulong cmdline_or_bootorder;
275 target_ulong initrd_base, initrd_end;
@@ -290,6 +288,18 @@ struct ArchCPU {
288 QEMUTimer *alarm_timer;
289 };
290
291 +/**
292 + * HPPACPUDef:
293 + * @phys_addr_bits: Number of bits in the physical address space.
294 + * @is_pa20: Whether the CPU model follows the PA-RISC 2.0 or 1.1 spec.
295 + *
296 + * Configuration options for a HPPA CPU model.
297 + */
298 +typedef struct HPPACPUDef {
299 + uint8_t phys_addr_bits;
300 + bool is_pa20;
301 +} HPPACPUDef;
302 +
303 /**
304 * HPPACPUClass:
305 * @parent_realize: The parent class' realize handler.
@@ -302,11 +312,17 @@ struct HPPACPUClass {
312
313 DeviceRealize parent_realize;
314 ResettablePhases parent_phases;
315 + const HPPACPUDef *def;
316 };
317
307 -static inline bool hppa_is_pa20(const CPUHPPAState *env)
318 +static inline const HPPACPUDef *hppa_def(CPUHPPAState *env)
319 +{
320 + return HPPA_CPU_GET_CLASS(env_cpu(env))->def;
321 +}
322 +
323 +static inline bool hppa_is_pa20(CPUHPPAState *env)
324 {
309 - return env->is_pa20;
325 + return hppa_def(env)->is_pa20;
326 }
327
328 static inline int HPPA_BTLB_ENTRIES(CPUHPPAState *env)
tests/qtest/machine-none-test.c
+1 -1
@@ -47,7 +47,7 @@ static struct arch2cpu cpus_map[] = {
47 { "tricore", "tc1796" },
48 { "xtensa", "dc233c" },
49 { "xtensaeb", "fsf" },
50 - { "hppa", "hppa" },
50 + { "hppa", "pa-7300lc" },
51 { "riscv64", "rv64" },
52 { "riscv32", "rv32" },
53 { "rx", "rx62n" },