Index: lib/libvmmapi/riscv/vmmapi_machdep.c =================================================================== --- lib/libvmmapi/riscv/vmmapi_machdep.c +++ lib/libvmmapi/riscv/vmmapi_machdep.c @@ -40,6 +40,7 @@ #include "internal.h" const char *vm_capstrmap[] = { + [VM_CAP_SSTC] = "sstc", [VM_CAP_MAX] = NULL, }; Index: sys/riscv/include/vmm.h =================================================================== --- sys/riscv/include/vmm.h +++ sys/riscv/include/vmm.h @@ -275,6 +275,7 @@ */ enum vm_cap_type { VM_CAP_UNRESTRICTED_GUEST, + VM_CAP_SSTC, VM_CAP_MAX }; Index: sys/riscv/vmm/vmm_riscv.c =================================================================== --- sys/riscv/vmm/vmm_riscv.c +++ sys/riscv/vmm/vmm_riscv.c @@ -903,6 +903,10 @@ ret = ENOENT; switch (num) { + case VM_CAP_SSTC: + *retval = has_sstc; + ret = 0; + break; case VM_CAP_UNRESTRICTED_GUEST: *retval = 1; ret = 0; Index: usr.sbin/bhyve/riscv/bhyverun_machdep.c =================================================================== --- usr.sbin/bhyve/riscv/bhyverun_machdep.c +++ usr.sbin/bhyve/riscv/bhyverun_machdep.c @@ -308,6 +308,8 @@ int error; int pcie_intrs[4] = {PCIE_INTA, PCIE_INTB, PCIE_INTC, PCIE_INTD}; vm_paddr_t fdt_gpa; + bool has_sstc; + int retval; bootrom = get_config_value("bootrom"); if (bootrom == NULL) { @@ -321,8 +323,14 @@ return (error); } + error = vm_get_capability(bsp, VM_CAP_SSTC, &retval); + if (error == 0 && retval == 1) + has_sstc = true; + else + has_sstc = false; + fdt_gpa = vm_get_highmem_base(ctx) + roundup2(len, FDT_DTB_ALIGN); - error = fdt_init(ctx, guest_ncpus, fdt_gpa, FDT_SIZE); + error = fdt_init(ctx, guest_ncpus, fdt_gpa, FDT_SIZE, has_sstc); if (error != 0) return (error); Index: usr.sbin/bhyve/riscv/fdt.h =================================================================== --- usr.sbin/bhyve/riscv/fdt.h +++ usr.sbin/bhyve/riscv/fdt.h @@ -36,7 +36,7 @@ struct vmctx; int fdt_init(struct vmctx *ctx, int ncpu, vm_paddr_t addrp, - vm_size_t size); + vm_size_t size, bool has_sstc); void fdt_add_aplic(uint64_t dist_base, uint64_t dist_size); void fdt_add_pcie(int intrs[static 4]); void fdt_add_uart(uint64_t uart_base, uint64_t uart_size, int intr); Index: usr.sbin/bhyve/riscv/fdt.c =================================================================== --- usr.sbin/bhyve/riscv/fdt.c +++ usr.sbin/bhyve/riscv/fdt.c @@ -84,9 +84,14 @@ } static void -add_cpu(void *fdt, int cpuid) +add_cpu(void *fdt, int cpuid, bool has_sstc) { char node_name[16]; + char isa[32]; + + sprintf(isa, "rv64imafdc"); + if (has_sstc) + sprintf(isa + strlen(isa), "_sstc"); snprintf(node_name, sizeof(node_name), "cpu@%d", cpuid); @@ -94,7 +99,7 @@ fdt_property_string(fdt, "device_type", "cpu"); fdt_property_string(fdt, "compatible", "riscv"); fdt_property_u32(fdt, "reg", cpuid); - fdt_property_string(fdt, "riscv,isa", "rv64imafdc_sstc"); + fdt_property_string(fdt, "riscv,isa", isa); fdt_property_string(fdt, "mmu-type", "riscv,sv39"); fdt_property_string(fdt, "clock-frequency", "1000000000"); @@ -110,7 +115,7 @@ } static void -add_cpus(void *fdt, int ncpu) +add_cpus(void *fdt, int ncpu, bool has_sstc) { int cpuid; @@ -120,14 +125,15 @@ fdt_property_u32(fdt, "#size-cells", 0); fdt_property_u32(fdt, "timebase-frequency", 10000000); - for (cpuid = 0; cpuid < ncpu; cpuid++) { - add_cpu(fdt, cpuid); - } + for (cpuid = 0; cpuid < ncpu; cpuid++) + add_cpu(fdt, cpuid, has_sstc); + fdt_end_node(fdt); } int -fdt_init(struct vmctx *ctx, int ncpu, vm_paddr_t fdtaddr, vm_size_t fdtsize) +fdt_init(struct vmctx *ctx, int ncpu, vm_paddr_t fdtaddr, vm_size_t fdtsize, + bool has_sstc) { void *fdt; const char *bootargs; @@ -162,7 +168,7 @@ set_single_reg(fdt, vm_get_highmem_base(ctx), vm_get_highmem_size(ctx)); fdt_end_node(fdt); - add_cpus(fdt, ncpu); + add_cpus(fdt, ncpu, has_sstc); /* Finalized by fdt_finalized(). */ fdtroot = fdt;