[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
Re: [PATCH V16 5/6] hw/mips: Add Loongson-3 machine support
From: |
Philippe Mathieu-Daudé |
Subject: |
Re: [PATCH V16 5/6] hw/mips: Add Loongson-3 machine support |
Date: |
Tue, 3 Nov 2020 21:23:30 +0100 |
User-agent: |
Mozilla/5.0 (X11; Linux x86_64; rv:78.0) Gecko/20100101 Thunderbird/78.3.1 |
Hi Huacai,
On 10/30/20 11:25 AM, Huacai Chen wrote:
> Add Loongson-3 based machine support, it use liointc as the interrupt
> controler and use GPEX as the pci controller. Currently it can work with
> both TCG and KVM.
>
> As the machine model is not based on any exiting physical hardware, the
> name of the machine is "loongson3-virt". It may be superseded in future
> by a real machine model. If this happens, then a regular deprecation
> procedure shall occur for "loongson3-virt" machine.
>
> We now already have a full functional Linux kernel (based on Linux-5.4.x
> LTS, the kvm host side and guest side have both been upstream for Linux-
> 5.9, but Linux-5.9 has not been released yet) here:
>
> https://github.com/chenhuacai/linux
>
> Of course the upstream kernel is also usable (though it is "unstable"
> now):
>
> https://git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
>
> How to use QEMU/Loongson-3?
> 1, Download kernel source from the above URL;
> 2, Build a kernel with arch/mips/configs/loongson3_defconfig;
> 3, Boot a Loongson-3A4000 host with this kernel (for KVM mode);
> 4, Build QEMU-master with this patchset;
> 5, modprobe kvm (only necessary for KVM mode);
> 6, Use QEMU with TCG:
> qemu-system-mips64el -M loongson3-virt,accel=tcg -cpu Loongson-3A1000
> -kernel <path_to_kernel> -append ...
> Use QEMU with KVM:
> qemu-system-mips64el -M loongson3-virt,accel=kvm -cpu Loongson-3A4000
> -kernel <path_to_kernel> -append ...
>
> The "-cpu" parameter is optional here and QEMU will use the correct type
> for TCG/KVM automatically.
>
> Signed-off-by: Huacai Chen <chenhc@lemote.com>
> Co-developed-by: Jiaxun Yang <jiaxun.yang@flygoat.com>
> Signed-off-by: Jiaxun Yang <jiaxun.yang@flygoat.com>
> ---
> default-configs/devices/mips64el-softmmu.mak | 1 +
> hw/mips/Kconfig | 12 +
> hw/mips/loongson3_virt.c | 620
> +++++++++++++++++++++++++++
> hw/mips/meson.build | 2 +-
> 4 files changed, 634 insertions(+), 1 deletion(-)
> create mode 100644 hw/mips/loongson3_virt.c
...
> +static inline void loongson3_virt_devices_init(MachineState *machine,
> DeviceState *pic)
> +{
> + int i;
> + qemu_irq irq;
> + PCIBus *pci_bus;
> + DeviceState *dev;
> + MemoryRegion *pio_alias;
> + MemoryRegion *mmio_alias, *mmio_reg;
> + MemoryRegion *ecam_alias, *ecam_reg;
> +
> + dev = qdev_new(TYPE_GPEX_HOST);
> + sysbus_realize_and_unref(SYS_BUS_DEVICE(dev), &error_fatal);
> + pci_bus = PCI_HOST_BRIDGE(dev)->bus;
> +
> + ecam_alias = g_new0(MemoryRegion, 1);
> + ecam_reg = sysbus_mmio_get_region(SYS_BUS_DEVICE(dev), 0);
> + memory_region_init_alias(ecam_alias, OBJECT(dev), "pcie-ecam",
> + ecam_reg, 0, virt_memmap[VIRT_PCIE_ECAM].size);
> + memory_region_add_subregion(get_system_memory(),
> + virt_memmap[VIRT_PCIE_ECAM].base,
> ecam_alias);
> +
> + mmio_alias = g_new0(MemoryRegion, 1);
> + mmio_reg = sysbus_mmio_get_region(SYS_BUS_DEVICE(dev), 1);
> + memory_region_init_alias(mmio_alias, OBJECT(dev), "pcie-mmio",
> + mmio_reg, virt_memmap[VIRT_PCIE_MMIO].base,
> + virt_memmap[VIRT_PCIE_MMIO].size);
> + memory_region_add_subregion(get_system_memory(),
> + virt_memmap[VIRT_PCIE_MMIO].base,
> mmio_alias);
> +
> + pio_alias = g_new0(MemoryRegion, 1);
> + memory_region_init_alias(pio_alias, OBJECT(dev), "pcie-pio",
> + get_system_io(), 0,
> virt_memmap[VIRT_PCIE_PIO].size);
> + memory_region_add_subregion(get_system_memory(),
> + virt_memmap[VIRT_PCIE_PIO].base, pio_alias);
> + sysbus_mmio_map(SYS_BUS_DEVICE(dev), 2, virt_memmap[VIRT_PCIE_PIO].base);
> +
> + for (i = 0; i < GPEX_NUM_IRQS; i++) {
> + irq = qdev_get_gpio_in(pic, PCIE_IRQ_BASE + i);
> + sysbus_connect_irq(SYS_BUS_DEVICE(dev), i, irq);
> + gpex_set_irq_num(GPEX_HOST(dev), i, PCIE_IRQ_BASE + i);
> + }
> +
> + pci_vga_init(pci_bus);
> +
> + if (defaults_enabled()) {
> + pci_create_simple(pci_bus, -1, "pci-ohci");
> + usb_create_simple(usb_bus_find(-1), "usb-kbd");
> + usb_create_simple(usb_bus_find(-1), "usb-tablet");
> + }
> +
> + for (i = 0; i < nb_nics; i++) {
> + NICInfo *nd = &nd_table[i];
> +
> + if (!nd->model) {
> + nd->model = g_strdup("virtio");
> + }
> +
> + pci_nic_init_nofail(nd, pci_bus, nd->model, NULL);
> + }
> +}
> +
> +static void mips_loongson3_virt_init(MachineState *machine)
> +{
> + int i;
> + long bios_size;
> + MIPSCPU *cpu;
> + Clock *cpuclk;
> + CPUMIPSState *env;
> + DeviceState *liointc;
> + char *filename;
> + const char *kernel_cmdline = machine->kernel_cmdline;
> + const char *kernel_filename = machine->kernel_filename;
> + const char *initrd_filename = machine->initrd_filename;
> + ram_addr_t ram_size = machine->ram_size;
> + MemoryRegion *address_space_mem = get_system_memory();
> + MemoryRegion *ram = g_new(MemoryRegion, 1);
> + MemoryRegion *bios = g_new(MemoryRegion, 1);
> + MemoryRegion *iomem = g_new(MemoryRegion, 1);
> +
> + /* TODO: TCG will support all CPU types */
> + if (!kvm_enabled()) {
> + if (!machine->cpu_type) {
> + machine->cpu_type = MIPS_CPU_TYPE_NAME("Loongson-3A1000");
> + }
> + if (!strstr(machine->cpu_type, "Loongson-3A1000")) {
> + error_report("Loongson-3/TCG needs cpu type Loongson-3A1000");
> + exit(1);
> + }
> + } else {
> + if (!machine->cpu_type) {
> + machine->cpu_type = MIPS_CPU_TYPE_NAME("Loongson-3A4000");
> + }
> + if (!strstr(machine->cpu_type, "Loongson-3A4000")) {
> + error_report("Loongson-3/KVM needs cpu type Loongson-3A4000");
> + exit(1);
> + }
> + }
> +
> + if (ram_size < 512 * MiB) {
> + error_report("Loongson-3 machine needs at least 512MB memory");
> + exit(1);
> + }
> +
> + /*
> + * The whole MMIO range among configure registers doesn't generate
> + * exception when accessing invalid memory. Create some unimplememted
> + * devices to emulate this feature.
> + */
> + create_unimplemented_device("mmio fallback 0", 0x10000000, 256 * MiB);
> + create_unimplemented_device("mmio fallback 1", 0x30000000, 256 * MiB);
> +
> + liointc = qdev_new("loongson.liointc");
Please use TYPE_name when creating QOM (here TYPE_LOONGSON_LIOINTC).
Similarly loongson3_virt_devices_init(). (no need to respin yet).
> + sysbus_realize_and_unref(SYS_BUS_DEVICE(liointc), &error_fatal);
> +
> + sysbus_mmio_map(SYS_BUS_DEVICE(liointc), 0,
> virt_memmap[VIRT_LIOINTC].base);
> +
> + serial_mm_init(address_space_mem, virt_memmap[VIRT_UART].base, 0,
> + qdev_get_gpio_in(liointc, UART_IRQ), 115200, serial_hd(0),
> + DEVICE_NATIVE_ENDIAN);
> +
> + sysbus_create_simple("goldfish_rtc", virt_memmap[VIRT_RTC].base,
> + qdev_get_gpio_in(liointc, RTC_IRQ));
> +
> + cpuclk = clock_new(OBJECT(machine), "cpu-refclk");
> + clock_set_hz(cpuclk, DEF_LOONGSON3_FREQ);
> +
> + for (i = 0; i < machine->smp.cpus; i++) {
> + int ip;
> +
> + /* init CPUs */
> + cpu = mips_cpu_create_with_clock(machine->cpu_type, cpuclk);
> +
> + /* Init internal devices */
> + cpu_mips_irq_init_cpu(cpu);
> + cpu_mips_clock_init(cpu);
> + qemu_register_reset(main_cpu_reset, cpu);
> +
> + if (i >= 4) {
> + continue; /* Only node-0 can be connected to LIOINTC */
> + }
> +
> + for (ip = 0; ip < 4 ; ip++) {
> + int pin = i * 4 + ip;
> + sysbus_connect_irq(SYS_BUS_DEVICE(liointc),
> + pin, cpu->env.irq[ip + 2]);
> + }
> + }
> + env = &MIPS_CPU(first_cpu)->env;
...
- Re: [PATCH V16 5/6] hw/mips: Add Loongson-3 machine support,
Philippe Mathieu-Daudé <=