Commit 585e351f authored by Atish Patra's avatar Atish Patra Committed by Anup Patel

perf: RISC-V: Define helper functions expose hpm counter width and count

KVM module needs to know how many hardware counters and the counter
width that the platform supports. Otherwise, it will not be able to show
optimal value of virtual counters to the guest. The virtual hardware
counters also need to have the same width as the logical hardware
counters for simplicity. However, there shouldn't be mapping between
virtual hardware counters and logical hardware counters. As we don't
support hetergeneous harts or counters with different width as of now,
the implementation relies on the counter width of the first available
programmable counter.
Reviewed-by: default avatarAnup Patel <anup@brainfault.org>
Reviewed-by: default avatarAndrew Jones <ajones@ventanamicro.com>
Signed-off-by: default avatarAtish Patra <atishp@rivosinc.com>
Signed-off-by: default avatarAnup Patel <anup@brainfault.org>
parent cdeb59bb
...@@ -44,7 +44,7 @@ static const struct attribute_group *riscv_pmu_attr_groups[] = { ...@@ -44,7 +44,7 @@ static const struct attribute_group *riscv_pmu_attr_groups[] = {
}; };
/* /*
* RISC-V doesn't have hetergenous harts yet. This need to be part of * RISC-V doesn't have heterogeneous harts yet. This need to be part of
* per_cpu in case of harts with different pmu counters * per_cpu in case of harts with different pmu counters
*/ */
static union sbi_pmu_ctr_info *pmu_ctr_list; static union sbi_pmu_ctr_info *pmu_ctr_list;
...@@ -52,6 +52,9 @@ static bool riscv_pmu_use_irq; ...@@ -52,6 +52,9 @@ static bool riscv_pmu_use_irq;
static unsigned int riscv_pmu_irq_num; static unsigned int riscv_pmu_irq_num;
static unsigned int riscv_pmu_irq; static unsigned int riscv_pmu_irq;
/* Cache the available counters in a bitmask */
static unsigned long cmask;
struct sbi_pmu_event_data { struct sbi_pmu_event_data {
union { union {
union { union {
...@@ -267,6 +270,37 @@ static bool pmu_sbi_ctr_is_fw(int cidx) ...@@ -267,6 +270,37 @@ static bool pmu_sbi_ctr_is_fw(int cidx)
return (info->type == SBI_PMU_CTR_TYPE_FW) ? true : false; return (info->type == SBI_PMU_CTR_TYPE_FW) ? true : false;
} }
/*
* Returns the counter width of a programmable counter and number of hardware
* counters. As we don't support heterogeneous CPUs yet, it is okay to just
* return the counter width of the first programmable counter.
*/
int riscv_pmu_get_hpm_info(u32 *hw_ctr_width, u32 *num_hw_ctr)
{
int i;
union sbi_pmu_ctr_info *info;
u32 hpm_width = 0, hpm_count = 0;
if (!cmask)
return -EINVAL;
for_each_set_bit(i, &cmask, RISCV_MAX_COUNTERS) {
info = &pmu_ctr_list[i];
if (!info)
continue;
if (!hpm_width && info->csr != CSR_CYCLE && info->csr != CSR_INSTRET)
hpm_width = info->width;
if (info->type == SBI_PMU_CTR_TYPE_HW)
hpm_count++;
}
*hw_ctr_width = hpm_width;
*num_hw_ctr = hpm_count;
return 0;
}
EXPORT_SYMBOL_GPL(riscv_pmu_get_hpm_info);
static int pmu_sbi_ctr_get_idx(struct perf_event *event) static int pmu_sbi_ctr_get_idx(struct perf_event *event)
{ {
struct hw_perf_event *hwc = &event->hw; struct hw_perf_event *hwc = &event->hw;
...@@ -812,7 +846,6 @@ static void riscv_pmu_destroy(struct riscv_pmu *pmu) ...@@ -812,7 +846,6 @@ static void riscv_pmu_destroy(struct riscv_pmu *pmu)
static int pmu_sbi_device_probe(struct platform_device *pdev) static int pmu_sbi_device_probe(struct platform_device *pdev)
{ {
struct riscv_pmu *pmu = NULL; struct riscv_pmu *pmu = NULL;
unsigned long cmask = 0;
int ret = -ENODEV; int ret = -ENODEV;
int num_counters; int num_counters;
......
...@@ -73,6 +73,9 @@ void riscv_pmu_legacy_skip_init(void); ...@@ -73,6 +73,9 @@ void riscv_pmu_legacy_skip_init(void);
static inline void riscv_pmu_legacy_skip_init(void) {}; static inline void riscv_pmu_legacy_skip_init(void) {};
#endif #endif
struct riscv_pmu *riscv_pmu_alloc(void); struct riscv_pmu *riscv_pmu_alloc(void);
#ifdef CONFIG_RISCV_PMU_SBI
int riscv_pmu_get_hpm_info(u32 *hw_ctr_width, u32 *num_hw_ctr);
#endif
#endif /* CONFIG_RISCV_PMU */ #endif /* CONFIG_RISCV_PMU */
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment