From fa96350574af112d7176f6cf5f41508df84b69cc Mon Sep 17 00:00:00 2001 From: wangming9 Date: Fri, 27 Oct 2023 11:22:07 +0800 Subject: [PATCH] arch/arm64: Modify the method for obtaining the CPU frequency MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Summary: 1、cntfrq_el0 is used to store the timer frequency, which may be different from the CPU frequency. 2、Do not use up_perf interface for SMP. Signed-off-by: wangming9 --- arch/arm64/src/common/arm64_boot.c | 1 - arch/arm64/src/common/arm64_cpustart.c | 2 -- arch/arm64/src/common/arm64_perf.c | 17 ++++++++++++----- arch/arm64/src/fvp-v8r/fvp_boot.c | 4 ++++ arch/arm64/src/goldfish/goldfish_boot.c | 4 ++++ arch/arm64/src/imx8/imx8_boot.c | 4 ++++ arch/arm64/src/zynq-mpsoc/zynq_boot.c | 4 ++++ 7 files changed, 28 insertions(+), 8 deletions(-) diff --git a/arch/arm64/src/common/arm64_boot.c b/arch/arm64/src/common/arm64_boot.c index 31230c424f3..bbeda1c0222 100644 --- a/arch/arm64/src/common/arm64_boot.c +++ b/arch/arm64/src/common/arm64_boot.c @@ -202,6 +202,5 @@ void arm64_boot_el1_init(void) void arm64_boot_primary_c_routine(void) { arm64_chip_boot(); - up_perf_init(NULL); nx_start(); } diff --git a/arch/arm64/src/common/arm64_cpustart.c b/arch/arm64/src/common/arm64_cpustart.c index 05fb736143e..46f9b72151c 100644 --- a/arch/arm64/src/common/arm64_cpustart.c +++ b/arch/arm64/src/common/arm64_cpustart.c @@ -232,7 +232,5 @@ void arm64_boot_secondary_c_routine(void) arm64_gic_secondary_init(); - up_perf_init(NULL); - arm64_smp_init_top(); } diff --git a/arch/arm64/src/common/arm64_perf.c b/arch/arm64/src/common/arm64_perf.c index fa19f649055..d2bc84a64d1 100644 --- a/arch/arm64/src/common/arm64_perf.c +++ b/arch/arm64/src/common/arm64_perf.c @@ -28,12 +28,20 @@ #ifdef CONFIG_ARCH_PERF_EVENTS +/**************************************************************************** + * Private Data + ****************************************************************************/ + +static unsigned long g_cpu_freq = ULONG_MAX; + /**************************************************************************** * Public Functions ****************************************************************************/ void up_perf_init(void *arg) { + g_cpu_freq = (unsigned long)(uintptr_t)arg; + pmu_ccntr_ccfiltr_config(PMCCFILTR_EL0_NSH); pmu_cntr_control_config(PMCR_EL0_C | PMCR_EL0_E); pmu_cntr_trap_control(PMUSERENR_EL0_EN); @@ -43,7 +51,7 @@ void up_perf_init(void *arg) unsigned long up_perf_getfreq(void) { - return read_sysreg(cntfrq_el0); + return g_cpu_freq; } unsigned long up_perf_gettime(void) @@ -54,10 +62,9 @@ unsigned long up_perf_gettime(void) void up_perf_convert(unsigned long elapsed, struct timespec *ts) { unsigned long left; - unsigned long cpu_freq = read_sysreg(cntfrq_el0); - ts->tv_sec = elapsed / cpu_freq; - left = elapsed - ts->tv_sec * cpu_freq; - ts->tv_nsec = NSEC_PER_SEC * left / cpu_freq; + ts->tv_sec = elapsed / g_cpu_freq; + left = elapsed - ts->tv_sec * g_cpu_freq; + ts->tv_nsec = NSEC_PER_SEC * left / g_cpu_freq; } #endif diff --git a/arch/arm64/src/fvp-v8r/fvp_boot.c b/arch/arm64/src/fvp-v8r/fvp_boot.c index 3cd7ca0499d..ec76e0ca1fc 100644 --- a/arch/arm64/src/fvp-v8r/fvp_boot.c +++ b/arch/arm64/src/fvp-v8r/fvp_boot.c @@ -182,4 +182,8 @@ void arm64_chip_boot(void) arm64_earlyserialinit(); #endif + +#ifdef CONFIG_ARCH_PERF_EVENTS + up_perf_init((void *)CONFIG_SYS_CLOCK_HW_CYCLES_PER_SEC); +#endif } diff --git a/arch/arm64/src/goldfish/goldfish_boot.c b/arch/arm64/src/goldfish/goldfish_boot.c index f9674b1e697..725d5a0b29e 100644 --- a/arch/arm64/src/goldfish/goldfish_boot.c +++ b/arch/arm64/src/goldfish/goldfish_boot.c @@ -170,6 +170,10 @@ void arm64_chip_boot(void) arm64_earlyserialinit(); #endif + +#ifdef CONFIG_ARCH_PERF_EVENTS + up_perf_init((void *)CONFIG_SYS_CLOCK_HW_CYCLES_PER_SEC); +#endif } #if defined(CONFIG_NET) && !defined(CONFIG_NETDEV_LATEINIT) diff --git a/arch/arm64/src/imx8/imx8_boot.c b/arch/arm64/src/imx8/imx8_boot.c index 62e6b1f0fd7..7272b58f072 100644 --- a/arch/arm64/src/imx8/imx8_boot.c +++ b/arch/arm64/src/imx8/imx8_boot.c @@ -112,4 +112,8 @@ void arm64_chip_boot(void) arm64_earlyserialinit(); #endif + +#ifdef CONFIG_ARCH_PERF_EVENTS + up_perf_init((void *)CONFIG_SYS_CLOCK_HW_CYCLES_PER_SEC); +#endif } diff --git a/arch/arm64/src/zynq-mpsoc/zynq_boot.c b/arch/arm64/src/zynq-mpsoc/zynq_boot.c index 1743908b8be..26a84a6fe97 100644 --- a/arch/arm64/src/zynq-mpsoc/zynq_boot.c +++ b/arch/arm64/src/zynq-mpsoc/zynq_boot.c @@ -195,6 +195,10 @@ void arm64_chip_boot(void) arm64_earlyserialinit(); #endif + +#ifdef CONFIG_ARCH_PERF_EVENTS + up_perf_init((void *)CONFIG_SYS_CLOCK_HW_CYCLES_PER_SEC); +#endif } #if defined(CONFIG_NET) && !defined(CONFIG_NETDEV_LATEINIT)