Index: arch/aarch64/aarch64/cpu.c =================================================================== RCS file: /cvsroot/src/sys/arch/aarch64/aarch64/cpu.c,v retrieving revision 1.32 diff -p -u -r1.32 cpu.c --- arch/aarch64/aarch64/cpu.c 9 Jan 2020 16:23:41 -0000 1.32 +++ arch/aarch64/aarch64/cpu.c 10 Jan 2020 23:47:28 -0000 @@ -65,6 +65,7 @@ static void cpu_identify1(device_t self, static void cpu_identify2(device_t self, struct cpu_info *); static void cpu_setup_id(struct cpu_info *); static void cpu_setup_sysctl(device_t, struct cpu_info *); +static void cpu_do_topology(struct cpu_info *); #ifdef MULTIPROCESSOR uint64_t cpu_mpidr[MAXCPUS]; @@ -144,7 +145,7 @@ cpu_attach(device_t dv, cpuid_t id) ci->ci_dev = dv; dv->dv_private = ci; - aarch64_gettopology(ci, ci->ci_id.ac_mpidr); + cpu_do_topology(ci); cpu_identify(ci->ci_dev, ci); #ifdef MULTIPROCESSOR @@ -308,8 +309,8 @@ cpu_identify2(device_t self, struct cpu_ dfr0 = reg_id_aa64dfr0_el1_read(); - aprint_debug_dev(self, "midr=0x%" PRIx32 "\n", - (uint32_t)ci->ci_id.ac_midr); + aprint_normal_dev(self, "midr=0x%" PRIx32 " mpidr=0x%" PRIx32 "\n", + (uint32_t)ci->ci_id.ac_midr, (uint32_t)ci->ci_id.ac_mpidr); aprint_normal_dev(self, "revID=0x%" PRIx64, id->ac_revidr); /* ID_AA64DFR0_EL1 */ @@ -497,6 +498,34 @@ cpu_setup_sysctl(device_t dv, struct cpu CTL_CREATE, CTL_EOL); } +static void +cpu_do_topology(struct cpu_info *newcpu) +{ + struct cpu_info *ci; + CPU_INFO_ITERATOR cii; + prop_dictionary_t dict; + uint64_t capacity_dmips_mhz; + static uint64_t best_cap = 0; + + dict = device_properties(newcpu->ci_dev); + if (prop_dictionary_get_uint64(dict, "capacity_dmips_mhz", + &capacity_dmips_mhz)) { + newcpu->ci_capacity_dmips_mhz = capacity_dmips_mhz; + } else { + newcpu->ci_capacity_dmips_mhz = 0; + } + +printf(": got cap dmips %lu best %lu", newcpu->ci_capacity_dmips_mhz, best_cap); + if (newcpu->ci_capacity_dmips_mhz > best_cap) + best_cap = newcpu->ci_capacity_dmips_mhz; + + /* Using saved largest capacity, re-fresh all the topology info. */ + for (CPU_INFO_FOREACH(cii, ci)) { + aarch64_set_topology(ci, ci->ci_id.ac_mpidr, + ci->ci_capacity_dmips_mhz < best_cap); + } +} + #ifdef MULTIPROCESSOR void cpu_boot_secondary_processors(void) Index: arch/aarch64/aarch64/cpufunc.c =================================================================== RCS file: /cvsroot/src/sys/arch/aarch64/aarch64/cpufunc.c,v retrieving revision 1.13 diff -p -u -r1.13 cpufunc.c --- arch/aarch64/aarch64/cpufunc.c 9 Jan 2020 16:35:03 -0000 1.13 +++ arch/aarch64/aarch64/cpufunc.c 10 Jan 2020 23:47:28 -0000 @@ -89,7 +89,7 @@ extract_cacheunit(int level, bool insn, } void -aarch64_gettopology(struct cpu_info * const ci, uint64_t mpidr) +aarch64_set_topology(struct cpu_info * const ci, uint64_t mpidr, bool slow) { if (mpidr & MPIDR_MT) { @@ -98,14 +98,14 @@ aarch64_gettopology(struct cpu_info * co __SHIFTOUT(mpidr, MPIDR_AFF1), __SHIFTOUT(mpidr, MPIDR_AFF0), 0, - false); + slow); } else { cpu_topology_set(ci, __SHIFTOUT(mpidr, MPIDR_AFF1), __SHIFTOUT(mpidr, MPIDR_AFF0), 0, 0, - false); + slow); } } Index: arch/aarch64/aarch64/locore.S =================================================================== RCS file: /cvsroot/src/sys/arch/aarch64/aarch64/locore.S,v retrieving revision 1.50 diff -p -u -r1.50 locore.S --- arch/aarch64/aarch64/locore.S 8 Jan 2020 05:41:07 -0000 1.50 +++ arch/aarch64/aarch64/locore.S 10 Jan 2020 23:47:28 -0000 @@ -187,7 +187,8 @@ vstart: /* get cache configuration */ mrs x0, tpidr_el1 /* curcpu */ mrs x1, mpidr_el1 - bl aarch64_gettopology + mov x2, #0 + bl aarch64_set_topology mov x0, xzr bl aarch64_getcacheinfo Index: arch/aarch64/include/cpu.h =================================================================== RCS file: /cvsroot/src/sys/arch/aarch64/include/cpu.h,v retrieving revision 1.17 diff -p -u -r1.17 cpu.h --- arch/aarch64/include/cpu.h 5 Jan 2020 20:17:43 -0000 1.17 +++ arch/aarch64/include/cpu.h 10 Jan 2020 23:47:28 -0000 @@ -100,6 +100,9 @@ struct cpu_info { /* ACPI */ uint64_t ci_acpiid; /* ACPI Processor Unique ID */ + /* FDT or similar supplied "cpu capacity" */ + uint64_t ci_capacity_dmips_mhz; + struct aarch64_sysctl_cpu_id ci_id; struct aarch64_cache_info *ci_cacheinfo; Index: arch/aarch64/include/cpufunc.h =================================================================== RCS file: /cvsroot/src/sys/arch/aarch64/include/cpufunc.h,v retrieving revision 1.9 diff -p -u -r1.9 cpufunc.h --- arch/aarch64/include/cpufunc.h 19 Dec 2019 09:47:42 -0000 1.9 +++ arch/aarch64/include/cpufunc.h 10 Jan 2020 23:47:28 -0000 @@ -69,7 +69,7 @@ extern u_int aarch64_cache_prefer_mask; extern u_int cputype; /* compat arm */ int set_cpufuncs(void); -void aarch64_gettopology(struct cpu_info *, uint64_t); +void aarch64_set_topology(struct cpu_info *, uint64_t, bool); void aarch64_getcacheinfo(int); void aarch64_printcacheinfo(device_t); Index: arch/arm/fdt/cpu_fdt.c =================================================================== RCS file: /cvsroot/src/sys/arch/arm/fdt/cpu_fdt.c,v retrieving revision 1.30 diff -p -u -r1.30 cpu_fdt.c --- arch/arm/fdt/cpu_fdt.c 1 Nov 2019 13:22:08 -0000 1.30 +++ arch/arm/fdt/cpu_fdt.c 10 Jan 2020 23:47:28 -0000 @@ -126,10 +126,25 @@ cpu_fdt_attach(device_t parent, device_t enum cpu_fdt_type type; bus_addr_t mpidr; cpuid_t cpuid; + const uint32_t *cap_ptr; + uint64_t capacity_dmips_mhz = 0; + int len = 4; sc->sc_dev = self; sc->sc_phandle = phandle; + cap_ptr = fdtbus_get_prop(phandle, "capacity-dmips-mhz", &len); + if (len == 4) + capacity_dmips_mhz = be32toh(*cap_ptr); + + if (capacity_dmips_mhz) { + prop_dictionary_t dict = device_properties(self); + +printf(" - setting capacity_dmips_mhz prop to %lu - ", capacity_dmips_mhz); + prop_dictionary_set_uint64(dict, "capacity_dmips_mhz", + capacity_dmips_mhz); + } + type = of_search_compatible(phandle, compat_data)->data; switch (type) { Index: kern/subr_cpu.c =================================================================== RCS file: /cvsroot/src/sys/kern/subr_cpu.c,v retrieving revision 1.6 diff -p -u -r1.6 subr_cpu.c --- kern/subr_cpu.c 9 Jan 2020 16:35:03 -0000 1.6 +++ kern/subr_cpu.c 10 Jan 2020 23:47:28 -0000 @@ -152,6 +152,7 @@ cpu_topology_set(struct cpu_info *ci, u_ ci->ci_core_id = core_id; ci->ci_smt_id = smt_id; ci->ci_numa_id = numa_id; + ci->ci_is_slow = slow; for (rel = 0; rel < __arraycount(ci->ci_sibling); rel++) { ci->ci_sibling[rel] = ci; ci->ci_nsibling[rel] = 1; @@ -273,6 +274,9 @@ cpu_topology_init(void) ci2->ci_core_id == ci->ci_core_id && ci2->ci_smt_id == ci->ci_smt_id && ci2 != ci) { +printf("ci %p cpu%d pkg %u core %u smt %u != ci %p cpu%d pkg %u core %u smt %u\n", + ci, cpu_index(ci), ci->ci_package_id, ci->ci_core_id, ci->ci_smt_id, + ci2, cpu_index(ci2), ci2->ci_package_id, ci2->ci_core_id, ci2->ci_smt_id); printf("cpu_topology_init: info bogus, " "faking it\n"); cpu_topology_fake();