1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17#include "qemu/osdep.h"
18
19#include "hw/arm/npcm7xx.h"
20#include "hw/core/cpu.h"
21#include "hw/i2c/i2c_mux_pca954x.h"
22#include "hw/i2c/smbus_eeprom.h"
23#include "hw/loader.h"
24#include "hw/qdev-core.h"
25#include "hw/qdev-properties.h"
26#include "qapi/error.h"
27#include "qemu-common.h"
28#include "qemu/datadir.h"
29#include "qemu/units.h"
30#include "sysemu/blockdev.h"
31#include "sysemu/sysemu.h"
32#include "sysemu/block-backend.h"
33
34#define NPCM750_EVB_POWER_ON_STRAPS 0x00001ff7
35#define QUANTA_GSJ_POWER_ON_STRAPS 0x00001fff
36#define QUANTA_GBS_POWER_ON_STRAPS 0x000017ff
37#define KUDO_BMC_POWER_ON_STRAPS 0x00001fff
38
39static const char npcm7xx_default_bootrom[] = "npcm7xx_bootrom.bin";
40
41static void npcm7xx_load_bootrom(MachineState *machine, NPCM7xxState *soc)
42{
43 const char *bios_name = machine->firmware ?: npcm7xx_default_bootrom;
44 g_autofree char *filename = NULL;
45 int ret;
46
47 filename = qemu_find_file(QEMU_FILE_TYPE_BIOS, bios_name);
48 if (!filename) {
49 error_report("Could not find ROM image '%s'", bios_name);
50 if (!machine->kernel_filename) {
51
52 exit(1);
53 }
54 return;
55 }
56 ret = load_image_mr(filename, &soc->irom);
57 if (ret < 0) {
58 error_report("Failed to load ROM image '%s'", filename);
59 exit(1);
60 }
61}
62
63static void npcm7xx_connect_flash(NPCM7xxFIUState *fiu, int cs_no,
64 const char *flash_type, DriveInfo *dinfo)
65{
66 DeviceState *flash;
67 qemu_irq flash_cs;
68
69 flash = qdev_new(flash_type);
70 if (dinfo) {
71 qdev_prop_set_drive(flash, "drive", blk_by_legacy_dinfo(dinfo));
72 }
73 qdev_realize_and_unref(flash, BUS(fiu->spi), &error_fatal);
74
75 flash_cs = qdev_get_gpio_in_named(flash, SSI_GPIO_CS, 0);
76 qdev_connect_gpio_out_named(DEVICE(fiu), "cs", cs_no, flash_cs);
77}
78
79static void npcm7xx_connect_dram(NPCM7xxState *soc, MemoryRegion *dram)
80{
81 memory_region_add_subregion(get_system_memory(), NPCM7XX_DRAM_BA, dram);
82
83 object_property_set_link(OBJECT(soc), "dram-mr", OBJECT(dram),
84 &error_abort);
85}
86
87static void sdhci_attach_drive(SDHCIState *sdhci)
88{
89 DriveInfo *di = drive_get_next(IF_SD);
90 BlockBackend *blk = di ? blk_by_legacy_dinfo(di) : NULL;
91
92 BusState *bus = qdev_get_child_bus(DEVICE(sdhci), "sd-bus");
93 if (bus == NULL) {
94 error_report("No SD bus found in SOC object");
95 exit(1);
96 }
97
98 DeviceState *carddev = qdev_new(TYPE_SD_CARD);
99 qdev_prop_set_drive_err(carddev, "drive", blk, &error_fatal);
100 qdev_realize_and_unref(carddev, bus, &error_fatal);
101}
102
103static NPCM7xxState *npcm7xx_create_soc(MachineState *machine,
104 uint32_t hw_straps)
105{
106 NPCM7xxMachineClass *nmc = NPCM7XX_MACHINE_GET_CLASS(machine);
107 MachineClass *mc = MACHINE_CLASS(nmc);
108 Object *obj;
109
110 if (strcmp(machine->cpu_type, mc->default_cpu_type) != 0) {
111 error_report("This board can only be used with %s",
112 mc->default_cpu_type);
113 exit(1);
114 }
115
116 obj = object_new_with_props(nmc->soc_type, OBJECT(machine), "soc",
117 &error_abort, NULL);
118 object_property_set_uint(obj, "power-on-straps", hw_straps, &error_abort);
119
120 return NPCM7XX(obj);
121}
122
123static I2CBus *npcm7xx_i2c_get_bus(NPCM7xxState *soc, uint32_t num)
124{
125 g_assert(num < ARRAY_SIZE(soc->smbus));
126 return I2C_BUS(qdev_get_child_bus(DEVICE(&soc->smbus[num]), "i2c-bus"));
127}
128
129static void at24c_eeprom_init(NPCM7xxState *soc, int bus, uint8_t addr,
130 uint32_t rsize)
131{
132 I2CBus *i2c_bus = npcm7xx_i2c_get_bus(soc, bus);
133 I2CSlave *i2c_dev = i2c_slave_new("at24c-eeprom", addr);
134 DeviceState *dev = DEVICE(i2c_dev);
135
136 qdev_prop_set_uint32(dev, "rom-size", rsize);
137 i2c_slave_realize_and_unref(i2c_dev, i2c_bus, &error_abort);
138}
139
140static void npcm7xx_init_pwm_splitter(NPCM7xxMachine *machine,
141 NPCM7xxState *soc, const int *fan_counts)
142{
143 SplitIRQ *splitters = machine->fan_splitter;
144
145
146
147
148
149 for (int i = 0; i < NPCM7XX_NR_PWM_MODULES; ++i) {
150 for (int j = 0; j < NPCM7XX_PWM_PER_MODULE; ++j) {
151 int splitter_no = i * NPCM7XX_PWM_PER_MODULE + j;
152 DeviceState *splitter;
153
154 if (fan_counts[splitter_no] < 1) {
155 continue;
156 }
157 object_initialize_child(OBJECT(machine), "fan-splitter[*]",
158 &splitters[splitter_no], TYPE_SPLIT_IRQ);
159 splitter = DEVICE(&splitters[splitter_no]);
160 qdev_prop_set_uint16(splitter, "num-lines",
161 fan_counts[splitter_no]);
162 qdev_realize(splitter, NULL, &error_abort);
163 qdev_connect_gpio_out_named(DEVICE(&soc->pwm[i]), "duty-gpio-out",
164 j, qdev_get_gpio_in(splitter, 0));
165 }
166 }
167}
168
169static void npcm7xx_connect_pwm_fan(NPCM7xxState *soc, SplitIRQ *splitter,
170 int fan_no, int output_no)
171{
172 DeviceState *fan;
173 int fan_input;
174 qemu_irq fan_duty_gpio;
175
176 g_assert(fan_no >= 0 && fan_no <= NPCM7XX_MFT_MAX_FAN_INPUT);
177
178
179
180
181
182
183
184
185 if (fan_no < 16) {
186 fan = DEVICE(&soc->mft[fan_no / 2]);
187 fan_input = fan_no % 2;
188 } else {
189 fan = DEVICE(&soc->mft[(fan_no - 16) / 2]);
190 fan_input = fan_no % 2 + 2;
191 }
192
193
194 fan_duty_gpio = qdev_get_gpio_in_named(fan, "duty", fan_input);
195 qdev_connect_gpio_out(DEVICE(splitter), output_no, fan_duty_gpio);
196}
197
198static void npcm750_evb_i2c_init(NPCM7xxState *soc)
199{
200
201 i2c_slave_create_simple(npcm7xx_i2c_get_bus(soc, 0), "tmp105", 0x48);
202
203 i2c_slave_create_simple(npcm7xx_i2c_get_bus(soc, 1), "tmp105", 0x48);
204
205 i2c_slave_create_simple(npcm7xx_i2c_get_bus(soc, 2), "tmp105", 0x48);
206
207 i2c_slave_create_simple(npcm7xx_i2c_get_bus(soc, 6), "tmp105", 0x48);
208}
209
210static void npcm750_evb_fan_init(NPCM7xxMachine *machine, NPCM7xxState *soc)
211{
212 SplitIRQ *splitter = machine->fan_splitter;
213 static const int fan_counts[] = {2, 2, 2, 2, 2, 2, 2, 2};
214
215 npcm7xx_init_pwm_splitter(machine, soc, fan_counts);
216 npcm7xx_connect_pwm_fan(soc, &splitter[0], 0x00, 0);
217 npcm7xx_connect_pwm_fan(soc, &splitter[0], 0x01, 1);
218 npcm7xx_connect_pwm_fan(soc, &splitter[1], 0x02, 0);
219 npcm7xx_connect_pwm_fan(soc, &splitter[1], 0x03, 1);
220 npcm7xx_connect_pwm_fan(soc, &splitter[2], 0x04, 0);
221 npcm7xx_connect_pwm_fan(soc, &splitter[2], 0x05, 1);
222 npcm7xx_connect_pwm_fan(soc, &splitter[3], 0x06, 0);
223 npcm7xx_connect_pwm_fan(soc, &splitter[3], 0x07, 1);
224 npcm7xx_connect_pwm_fan(soc, &splitter[4], 0x08, 0);
225 npcm7xx_connect_pwm_fan(soc, &splitter[4], 0x09, 1);
226 npcm7xx_connect_pwm_fan(soc, &splitter[5], 0x0a, 0);
227 npcm7xx_connect_pwm_fan(soc, &splitter[5], 0x0b, 1);
228 npcm7xx_connect_pwm_fan(soc, &splitter[6], 0x0c, 0);
229 npcm7xx_connect_pwm_fan(soc, &splitter[6], 0x0d, 1);
230 npcm7xx_connect_pwm_fan(soc, &splitter[7], 0x0e, 0);
231 npcm7xx_connect_pwm_fan(soc, &splitter[7], 0x0f, 1);
232}
233
234static void quanta_gsj_i2c_init(NPCM7xxState *soc)
235{
236
237 i2c_slave_create_simple(npcm7xx_i2c_get_bus(soc, 1), "tmp105", 0x5c);
238 i2c_slave_create_simple(npcm7xx_i2c_get_bus(soc, 2), "tmp105", 0x5c);
239 i2c_slave_create_simple(npcm7xx_i2c_get_bus(soc, 3), "tmp105", 0x5c);
240 i2c_slave_create_simple(npcm7xx_i2c_get_bus(soc, 4), "tmp105", 0x5c);
241
242 at24c_eeprom_init(soc, 9, 0x55, 8192);
243 at24c_eeprom_init(soc, 10, 0x55, 8192);
244
245
246
247
248
249
250
251
252
253
254
255
256 i2c_slave_create_simple(npcm7xx_i2c_get_bus(soc, 15), "pca9548", 0x75);
257}
258
259static void quanta_gsj_fan_init(NPCM7xxMachine *machine, NPCM7xxState *soc)
260{
261 SplitIRQ *splitter = machine->fan_splitter;
262 static const int fan_counts[] = {2, 2, 2, 0, 0, 0, 0, 0};
263
264 npcm7xx_init_pwm_splitter(machine, soc, fan_counts);
265 npcm7xx_connect_pwm_fan(soc, &splitter[0], 0x00, 0);
266 npcm7xx_connect_pwm_fan(soc, &splitter[0], 0x01, 1);
267 npcm7xx_connect_pwm_fan(soc, &splitter[1], 0x02, 0);
268 npcm7xx_connect_pwm_fan(soc, &splitter[1], 0x03, 1);
269 npcm7xx_connect_pwm_fan(soc, &splitter[2], 0x04, 0);
270 npcm7xx_connect_pwm_fan(soc, &splitter[2], 0x05, 1);
271}
272
273static void quanta_gbs_i2c_init(NPCM7xxState *soc)
274{
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330}
331
332static void npcm750_evb_init(MachineState *machine)
333{
334 NPCM7xxState *soc;
335
336 soc = npcm7xx_create_soc(machine, NPCM750_EVB_POWER_ON_STRAPS);
337 npcm7xx_connect_dram(soc, machine->ram);
338 qdev_realize(DEVICE(soc), NULL, &error_fatal);
339
340 npcm7xx_load_bootrom(machine, soc);
341 npcm7xx_connect_flash(&soc->fiu[0], 0, "w25q256", drive_get(IF_MTD, 0, 0));
342 npcm750_evb_i2c_init(soc);
343 npcm750_evb_fan_init(NPCM7XX_MACHINE(machine), soc);
344 npcm7xx_load_kernel(machine, soc);
345}
346
347static void quanta_gsj_init(MachineState *machine)
348{
349 NPCM7xxState *soc;
350
351 soc = npcm7xx_create_soc(machine, QUANTA_GSJ_POWER_ON_STRAPS);
352 npcm7xx_connect_dram(soc, machine->ram);
353 qdev_realize(DEVICE(soc), NULL, &error_fatal);
354
355 npcm7xx_load_bootrom(machine, soc);
356 npcm7xx_connect_flash(&soc->fiu[0], 0, "mx25l25635e",
357 drive_get(IF_MTD, 0, 0));
358 quanta_gsj_i2c_init(soc);
359 quanta_gsj_fan_init(NPCM7XX_MACHINE(machine), soc);
360 npcm7xx_load_kernel(machine, soc);
361}
362
363static void quanta_gbs_init(MachineState *machine)
364{
365 NPCM7xxState *soc;
366
367 soc = npcm7xx_create_soc(machine, QUANTA_GBS_POWER_ON_STRAPS);
368 npcm7xx_connect_dram(soc, machine->ram);
369 qdev_realize(DEVICE(soc), NULL, &error_fatal);
370
371 npcm7xx_load_bootrom(machine, soc);
372
373 npcm7xx_connect_flash(&soc->fiu[0], 0, "mx66u51235f",
374 drive_get(IF_MTD, 0, 0));
375
376 quanta_gbs_i2c_init(soc);
377 sdhci_attach_drive(&soc->mmc.sdhci);
378 npcm7xx_load_kernel(machine, soc);
379}
380
381static void kudo_bmc_init(MachineState *machine)
382{
383 NPCM7xxState *soc;
384
385 soc = npcm7xx_create_soc(machine, KUDO_BMC_POWER_ON_STRAPS);
386 npcm7xx_connect_dram(soc, machine->ram);
387 qdev_realize(DEVICE(soc), NULL, &error_fatal);
388
389 npcm7xx_load_bootrom(machine, soc);
390 npcm7xx_connect_flash(&soc->fiu[0], 0, "mx66u51235f",
391 drive_get(IF_MTD, 0, 0));
392 npcm7xx_connect_flash(&soc->fiu[1], 0, "mx66u51235f",
393 drive_get(IF_MTD, 3, 0));
394
395 npcm7xx_load_kernel(machine, soc);
396}
397
398static void npcm7xx_set_soc_type(NPCM7xxMachineClass *nmc, const char *type)
399{
400 NPCM7xxClass *sc = NPCM7XX_CLASS(object_class_by_name(type));
401 MachineClass *mc = MACHINE_CLASS(nmc);
402
403 nmc->soc_type = type;
404 mc->default_cpus = mc->min_cpus = mc->max_cpus = sc->num_cpus;
405}
406
407static void npcm7xx_machine_class_init(ObjectClass *oc, void *data)
408{
409 MachineClass *mc = MACHINE_CLASS(oc);
410
411 mc->no_floppy = 1;
412 mc->no_cdrom = 1;
413 mc->no_parallel = 1;
414 mc->default_ram_id = "ram";
415 mc->default_cpu_type = ARM_CPU_TYPE_NAME("cortex-a9");
416}
417
418
419
420
421
422static void npcm750_evb_machine_class_init(ObjectClass *oc, void *data)
423{
424 NPCM7xxMachineClass *nmc = NPCM7XX_MACHINE_CLASS(oc);
425 MachineClass *mc = MACHINE_CLASS(oc);
426
427 npcm7xx_set_soc_type(nmc, TYPE_NPCM750);
428
429 mc->desc = "Nuvoton NPCM750 Evaluation Board (Cortex-A9)";
430 mc->init = npcm750_evb_init;
431 mc->default_ram_size = 512 * MiB;
432};
433
434static void gsj_machine_class_init(ObjectClass *oc, void *data)
435{
436 NPCM7xxMachineClass *nmc = NPCM7XX_MACHINE_CLASS(oc);
437 MachineClass *mc = MACHINE_CLASS(oc);
438
439 npcm7xx_set_soc_type(nmc, TYPE_NPCM730);
440
441 mc->desc = "Quanta GSJ (Cortex-A9)";
442 mc->init = quanta_gsj_init;
443 mc->default_ram_size = 512 * MiB;
444};
445
446static void gbs_bmc_machine_class_init(ObjectClass *oc, void *data)
447{
448 NPCM7xxMachineClass *nmc = NPCM7XX_MACHINE_CLASS(oc);
449 MachineClass *mc = MACHINE_CLASS(oc);
450
451 npcm7xx_set_soc_type(nmc, TYPE_NPCM730);
452
453 mc->desc = "Quanta GBS (Cortex-A9)";
454 mc->init = quanta_gbs_init;
455 mc->default_ram_size = 1 * GiB;
456}
457
458static void kudo_bmc_machine_class_init(ObjectClass *oc, void *data)
459{
460 NPCM7xxMachineClass *nmc = NPCM7XX_MACHINE_CLASS(oc);
461 MachineClass *mc = MACHINE_CLASS(oc);
462
463 npcm7xx_set_soc_type(nmc, TYPE_NPCM730);
464
465 mc->desc = "Kudo BMC (Cortex-A9)";
466 mc->init = kudo_bmc_init;
467 mc->default_ram_size = 1 * GiB;
468};
469
470static const TypeInfo npcm7xx_machine_types[] = {
471 {
472 .name = TYPE_NPCM7XX_MACHINE,
473 .parent = TYPE_MACHINE,
474 .instance_size = sizeof(NPCM7xxMachine),
475 .class_size = sizeof(NPCM7xxMachineClass),
476 .class_init = npcm7xx_machine_class_init,
477 .abstract = true,
478 }, {
479 .name = MACHINE_TYPE_NAME("npcm750-evb"),
480 .parent = TYPE_NPCM7XX_MACHINE,
481 .class_init = npcm750_evb_machine_class_init,
482 }, {
483 .name = MACHINE_TYPE_NAME("quanta-gsj"),
484 .parent = TYPE_NPCM7XX_MACHINE,
485 .class_init = gsj_machine_class_init,
486 }, {
487 .name = MACHINE_TYPE_NAME("quanta-gbs-bmc"),
488 .parent = TYPE_NPCM7XX_MACHINE,
489 .class_init = gbs_bmc_machine_class_init,
490 }, {
491 .name = MACHINE_TYPE_NAME("kudo-bmc"),
492 .parent = TYPE_NPCM7XX_MACHINE,
493 .class_init = kudo_bmc_machine_class_init,
494 },
495};
496
497DEFINE_TYPES(npcm7xx_machine_types)
498