* [RFC PATCH 24/25] kvx: Add support for CPU Perf Monitors
2023-01-03 16:43 [RFC PATCH 00/25] Upstream kvx Linux port Yann Sionneau
@ 2023-01-03 16:43 ` Yann Sionneau
2023-01-03 20:52 ` [RFC PATCH 00/25] Upstream kvx Linux port Rob Herring
` (2 subsequent siblings)
3 siblings, 0 replies; 13+ messages in thread
From: Yann Sionneau @ 2023-01-03 16:43 UTC (permalink / raw)
Cc: Yann Sionneau, Will Deacon, Mark Rutland, Rob Herring,
Krzysztof Kozlowski, Peter Zijlstra, Ingo Molnar,
Arnaldo Carvalho de Melo, Alexander Shishkin, Jiri Olsa,
Namhyung Kim, linux-arm-kernel, devicetree, linux-kernel,
linux-perf-users, Clement Leger, Jules Maselbas, Julian Vetter
Each kvx core includes several Perf Monitors.
This commit adds the driver that handles those core PM.
CC: Will Deacon <will@kernel.org>
CC: Mark Rutland <mark.rutland@arm.com>
CC: Rob Herring <robh+dt@kernel.org>
CC: Krzysztof Kozlowski <krzysztof.kozlowski+dt@linaro.org>
CC: Peter Zijlstra <peterz@infradead.org>
CC: Ingo Molnar <mingo@redhat.com>
CC: Arnaldo Carvalho de Melo <acme@kernel.org>
CC: Alexander Shishkin <alexander.shishkin@linux.intel.com>
CC: Jiri Olsa <jolsa@kernel.org>
CC: Namhyung Kim <namhyung@kernel.org>
CC: linux-arm-kernel@lists.infradead.org
CC: devicetree@vger.kernel.org
CC: linux-kernel@vger.kernel.org
CC: linux-perf-users@vger.kernel.org
Co-developed-by: Clement Leger <clement.leger@bootlin.com>
Signed-off-by: Clement Leger <clement.leger@bootlin.com>
Co-developed-by: Jules Maselbas <jmaselbas@kalray.eu>
Signed-off-by: Jules Maselbas <jmaselbas@kalray.eu>
Co-developed-by: Julian Vetter <jvetter@kalray.eu>
Signed-off-by: Julian Vetter <jvetter@kalray.eu>
Co-developed-by: Yann Sionneau <ysionneau@kalray.eu>
Signed-off-by: Yann Sionneau <ysionneau@kalray.eu>
---
.../devicetree/bindings/perf/kalray-pm.txt | 21 +
arch/kvx/include/asm/perf_event.h | 90 +++
arch/kvx/kernel/perf_event.c | 609 ++++++++++++++++++
3 files changed, 720 insertions(+)
create mode 100644 Documentation/devicetree/bindings/perf/kalray-pm.txt
create mode 100644 arch/kvx/include/asm/perf_event.h
create mode 100644 arch/kvx/kernel/perf_event.c
diff --git a/Documentation/devicetree/bindings/perf/kalray-pm.txt b/Documentation/devicetree/bindings/perf/kalray-pm.txt
new file mode 100644
index 000000000000..9ce00d703941
--- /dev/null
+++ b/Documentation/devicetree/bindings/perf/kalray-pm.txt
@@ -0,0 +1,21 @@
+* Kalray kvx Performance Monitors
+
+KVX core has several Performance Monitors for counting cpu and cache events.
+The KVX PM representation in the device tree should be done as under:
+
+Required properties:
+
+- compatible :
+ "kalray,kvx-core-pm"
+
+- interrupts : The interrupt number for kvx PM is 3.
+- interrupt-parent : The kvx core interrupt controller.
+- kalray,pm-num : Number of Performance Monitors the kvx core has.
+
+Example:
+core_pm {
+ compatible = "kalray,kvx-core-pm";
+ interrupts = <3>;
+ interrupt-parent = <&core_intc>;
+ kalray,pm-num = <4>;
+}
diff --git a/arch/kvx/include/asm/perf_event.h b/arch/kvx/include/asm/perf_event.h
new file mode 100644
index 000000000000..bb0147dfdf47
--- /dev/null
+++ b/arch/kvx/include/asm/perf_event.h
@@ -0,0 +1,90 @@
+/* SPDX-License-Identifier: GPL-2.0-only */
+/*
+ * Copyright (C) 2017-2023 Kalray Inc.
+ * Author(s): Yann Sionneau
+ * Clement Leger
+ */
+
+#ifndef _ASM_KVX_PERF_EVENT_H
+#define _ASM_KVX_PERF_EVENT_H
+
+#include <linux/perf_event.h>
+
+/**
+ * struct cpu_hw_events - per-cpu structure to describe PM resource usage
+ * @n_events: number of events currently existing
+ * @events: events[i] is the event using PMi. NULL if PMi is not used.
+ */
+struct cpu_hw_events {
+ unsigned int n_events;
+ struct perf_event **events;
+};
+
+enum kvx_pmc_ie {
+ PMC_IE_DISABLED,
+ PMC_IE_ENABLED
+};
+
+enum kvx_pm_idx {
+ KVX_PM_1,
+ KVX_PM_2,
+ KVX_PM_3
+};
+
+enum kvx_pm_event_code {
+ KVX_PM_PCC,
+ KVX_PM_ICC,
+ KVX_PM_EBE,
+ KVX_PM_ENIE,
+ KVX_PM_ENSE,
+ KVX_PM_ICHE,
+ KVX_PM_ICME,
+ KVX_PM_ICMABE,
+ KVX_PM_MNGIC,
+ KVX_PM_MIMHE,
+ KVX_PM_MIMME,
+ KVX_PM_IATSC,
+ KVX_PM_FE,
+ KVX_PM_PBSC,
+ KVX_PM_PNVC,
+ KVX_PM_PSC,
+ KVX_PM_TADBE,
+ KVX_PM_TABE,
+ KVX_PM_TBE,
+ KVX_PM_MDMHE,
+ KVX_PM_MDMME,
+ KVX_PM_DATSC,
+ KVX_PM_DCLHE,
+ KVX_PM_DCHE,
+ KVX_PM_DCLME,
+ KVX_PM_DCME,
+ KVX_PM_DARSC,
+ KVX_PM_LDSC,
+ KVX_PM_DCNGC,
+ KVX_PM_DMAE,
+ KVX_PM_LCFSC,
+ KVX_PM_MNGDC,
+ KVX_PM_MACC,
+ KVX_PM_TACC,
+ KVX_PM_IWC,
+ KVX_PM_WISC,
+ KVX_PM_SISC,
+ KVX_PM_DDSC,
+ KVX_PM_SC,
+ KVX_PM_ELE,
+ KVX_PM_ELNBE,
+ KVX_PM_ELUE,
+ KVX_PM_ELUNBE,
+ KVX_PM_ESE,
+ KVX_PM_ESNBE,
+ KVX_PM_EAE,
+ KVX_PM_CIRE,
+ KVX_PM_CIE,
+ KVX_PM_SE,
+ KVX_PM_RE,
+ KVX_PM_FSC,
+ KVX_PM_MAX,
+ KVX_PM_UNSUPPORTED = KVX_PM_MAX,
+};
+
+#endif /* _ASM_KVX_PERF_EVENT_H */
diff --git a/arch/kvx/kernel/perf_event.c b/arch/kvx/kernel/perf_event.c
new file mode 100644
index 000000000000..bfc547e78aba
--- /dev/null
+++ b/arch/kvx/kernel/perf_event.c
@@ -0,0 +1,609 @@
+// SPDX-License-Identifier: GPL-2.0-only
+/*
+ * Copyright (C) 2017-2023 Kalray Inc.
+ * Author(s): Yann Sionneau
+ * Clement Leger
+ */
+
+#include <linux/of.h>
+#include <linux/of_irq.h>
+#include <linux/kernel.h>
+#include <linux/perf_event.h>
+#include <linux/errno.h>
+#include <linux/platform_device.h>
+#include <asm/perf_event.h>
+
+static unsigned int pm_num;
+static unsigned int kvx_pm_irq;
+static DEFINE_PER_CPU(struct cpu_hw_events, cpu_hw_events);
+
+static const enum kvx_pm_event_code kvx_hw_event_map[] = {
+ [PERF_COUNT_HW_CPU_CYCLES] = KVX_PM_PCC,
+ [PERF_COUNT_HW_INSTRUCTIONS] = KVX_PM_ENIE,
+ [PERF_COUNT_HW_CACHE_REFERENCES] = KVX_PM_UNSUPPORTED,
+ [PERF_COUNT_HW_CACHE_MISSES] = KVX_PM_UNSUPPORTED,
+ [PERF_COUNT_HW_BRANCH_INSTRUCTIONS] = KVX_PM_TABE,
+ [PERF_COUNT_HW_BRANCH_MISSES] = KVX_PM_UNSUPPORTED,
+ [PERF_COUNT_HW_BUS_CYCLES] = KVX_PM_PCC,
+ [PERF_COUNT_HW_STALLED_CYCLES_FRONTEND] = KVX_PM_PSC,
+ [PERF_COUNT_HW_STALLED_CYCLES_BACKEND] = KVX_PM_UNSUPPORTED,
+ [PERF_COUNT_HW_REF_CPU_CYCLES] = KVX_PM_UNSUPPORTED,
+};
+
+#define C(_x) PERF_COUNT_HW_CACHE_##_x
+
+static const enum kvx_pm_event_code
+ kvx_cache_map[C(MAX)][C(OP_MAX)][C(RESULT_MAX)] = {
+[C(L1D)] = {
+ [C(OP_READ)] = {
+ [C(RESULT_ACCESS)] = KVX_PM_UNSUPPORTED,
+ [C(RESULT_MISS)] = KVX_PM_DCLME,
+ },
+ [C(OP_WRITE)] = {
+ [C(RESULT_ACCESS)] = KVX_PM_UNSUPPORTED,
+ [C(RESULT_MISS)] = KVX_PM_UNSUPPORTED,
+ },
+ [C(OP_PREFETCH)] = {
+ [C(RESULT_ACCESS)] = KVX_PM_UNSUPPORTED,
+ [C(RESULT_MISS)] = KVX_PM_UNSUPPORTED,
+ },
+},
+[C(L1I)] = {
+ [C(OP_READ)] = {
+ [C(RESULT_ACCESS)] = KVX_PM_UNSUPPORTED,
+ [C(RESULT_MISS)] = KVX_PM_ICME,
+ },
+ [C(OP_WRITE)] = {
+ [C(RESULT_ACCESS)] = KVX_PM_UNSUPPORTED,
+ [C(RESULT_MISS)] = KVX_PM_UNSUPPORTED,
+ },
+ [C(OP_PREFETCH)] = {
+ [C(RESULT_ACCESS)] = KVX_PM_UNSUPPORTED,
+ [C(RESULT_MISS)] = KVX_PM_UNSUPPORTED,
+ },
+},
+[C(LL)] = {
+ [C(OP_READ)] = {
+ [C(RESULT_ACCESS)] = KVX_PM_UNSUPPORTED,
+ [C(RESULT_MISS)] = KVX_PM_UNSUPPORTED,
+ },
+ [C(OP_WRITE)] = {
+ [C(RESULT_ACCESS)] = KVX_PM_UNSUPPORTED,
+ [C(RESULT_MISS)] = KVX_PM_UNSUPPORTED,
+ },
+ [C(OP_PREFETCH)] = {
+ [C(RESULT_ACCESS)] = KVX_PM_UNSUPPORTED,
+ [C(RESULT_MISS)] = KVX_PM_UNSUPPORTED,
+ },
+},
+[C(DTLB)] = {
+ [C(OP_READ)] = {
+ [C(RESULT_ACCESS)] = KVX_PM_UNSUPPORTED,
+ [C(RESULT_MISS)] = KVX_PM_UNSUPPORTED,
+ },
+ [C(OP_WRITE)] = {
+ [C(RESULT_ACCESS)] = KVX_PM_UNSUPPORTED,
+ [C(RESULT_MISS)] = KVX_PM_UNSUPPORTED,
+ },
+ [C(OP_PREFETCH)] = {
+ [C(RESULT_ACCESS)] = KVX_PM_UNSUPPORTED,
+ [C(RESULT_MISS)] = KVX_PM_UNSUPPORTED,
+ },
+},
+[C(ITLB)] = {
+ [C(OP_READ)] = {
+ [C(RESULT_ACCESS)] = KVX_PM_UNSUPPORTED,
+ [C(RESULT_MISS)] = KVX_PM_MIMME,
+ },
+ [C(OP_WRITE)] = {
+ [C(RESULT_ACCESS)] = KVX_PM_UNSUPPORTED,
+ [C(RESULT_MISS)] = KVX_PM_UNSUPPORTED,
+ },
+ [C(OP_PREFETCH)] = {
+ [C(RESULT_ACCESS)] = KVX_PM_UNSUPPORTED,
+ [C(RESULT_MISS)] = KVX_PM_UNSUPPORTED,
+ },
+},
+[C(BPU)] = {
+ [C(OP_READ)] = {
+ [C(RESULT_ACCESS)] = KVX_PM_UNSUPPORTED,
+ [C(RESULT_MISS)] = KVX_PM_UNSUPPORTED,
+ },
+ [C(OP_WRITE)] = {
+ [C(RESULT_ACCESS)] = KVX_PM_UNSUPPORTED,
+ [C(RESULT_MISS)] = KVX_PM_UNSUPPORTED,
+ },
+ [C(OP_PREFETCH)] = {
+ [C(RESULT_ACCESS)] = KVX_PM_UNSUPPORTED,
+ [C(RESULT_MISS)] = KVX_PM_UNSUPPORTED,
+ },
+},
+[C(NODE)] = {
+ [C(OP_READ)] = {
+ [C(RESULT_ACCESS)] = KVX_PM_UNSUPPORTED,
+ [C(RESULT_MISS)] = KVX_PM_UNSUPPORTED,
+ },
+ [C(OP_WRITE)] = {
+ [C(RESULT_ACCESS)] = KVX_PM_UNSUPPORTED,
+ [C(RESULT_MISS)] = KVX_PM_UNSUPPORTED,
+ },
+ [C(OP_PREFETCH)] = {
+ [C(RESULT_ACCESS)] = KVX_PM_UNSUPPORTED,
+ [C(RESULT_MISS)] = KVX_PM_UNSUPPORTED,
+ },
+},
+};
+
+static u64 read_counter(struct perf_event *event)
+{
+ struct hw_perf_event *hwc = &event->hw;
+ unsigned int pm = hwc->idx;
+
+ if (pm > pm_num) {
+ WARN_ONCE(1, "This PM (%u) does not exist!\n", pm);
+ return 0;
+ }
+ return kvx_sfr_iget(KVX_SFR_PM1 + pm);
+}
+
+static void kvx_pmu_read(struct perf_event *event)
+{
+ struct hw_perf_event *hwc = &event->hw;
+ u64 delta, prev_raw_count, new_raw_count;
+
+ do {
+ prev_raw_count = local64_read(&hwc->prev_count);
+ new_raw_count = read_counter(event);
+ } while (local64_cmpxchg(&hwc->prev_count, prev_raw_count,
+ new_raw_count) != prev_raw_count);
+ /*
+ * delta is the value to update the counter we maintain in the kernel.
+ */
+ delta = (new_raw_count - prev_raw_count);
+ local64_add(delta, &event->count);
+}
+
+static void kvx_set_pmc_ie(unsigned int pm_num, enum kvx_pmc_ie ievalue)
+{
+ u64 shifted_value = ((u64)ievalue << KVX_SFR_PMC_PM1IE_SHIFT)
+ & KVX_SFR_PMC_PM1IE_MASK;
+ u64 clr_mask = KVX_SFR_PMC_PM1IE_MASK << pm_num;
+ u64 set_mask = shifted_value << pm_num;
+
+ kvx_sfr_set_mask(PMC, clr_mask, set_mask);
+}
+
+static void kvx_set_pmc(unsigned int pm_num, enum kvx_pm_event_code pmc_value)
+{
+ u64 pm_shift = (pm_num + 1) * KVX_SFR_PMC_PM1C_SHIFT;
+ u64 clr_mask = KVX_SFR_PMC_PM0C_MASK << pm_shift;
+ u64 set_mask = pmc_value << pm_shift;
+
+ kvx_sfr_set_mask(PMC, clr_mask, set_mask);
+}
+
+static void give_pm_to_user(unsigned int pm)
+{
+ int pl_value = 1 << (KVX_SFR_MOW_PM0_SHIFT
+ + KVX_SFR_MOW_PM0_WIDTH * (pm + 1));
+ int pl_clr_mask = 3 << (KVX_SFR_MOW_PM0_SHIFT
+ + KVX_SFR_MOW_PM0_WIDTH * (pm + 1));
+ kvx_sfr_set_mask(MOW, pl_clr_mask, pl_value);
+}
+
+static void get_pm_back_to_kernel(unsigned int pm)
+{
+ int pl_value = 0;
+ int pl_clr_mask = 3 << (KVX_SFR_MOW_PM0_SHIFT
+ + KVX_SFR_MOW_PM0_WIDTH * (pm + 1));
+ kvx_sfr_set_mask(MOW, pl_clr_mask, pl_value);
+}
+
+static void kvx_set_pm(enum kvx_pm_idx pm, u64 value)
+{
+ switch (pm) {
+ case KVX_PM_1:
+ kvx_sfr_set(PM1, value);
+ break;
+ case KVX_PM_2:
+ kvx_sfr_set(PM2, value);
+ break;
+ case KVX_PM_3:
+ kvx_sfr_set(PM3, value);
+ break;
+ default:
+ WARN_ONCE(1, "This PM (%u) does not exist!\n", pm);
+ }
+}
+
+static void kvx_stop_sampling_event(unsigned int pm)
+{
+ kvx_set_pmc_ie(pm, PMC_IE_DISABLED);
+}
+
+static u64 kvx_start_sampling_event(struct perf_event *event, unsigned int pm)
+{
+ u64 start_value;
+
+ if (event->attr.freq) {
+ pr_err_once("kvx_pm: Frequency sampling is not supported\n");
+ return 0;
+ }
+
+ /* PM counter will overflow after "sample_period" ticks */
+ start_value = (u64)(-event->attr.sample_period);
+
+ kvx_set_pmc(pm, KVX_PM_SE);
+ kvx_set_pm(pm, start_value);
+ kvx_set_pmc_ie(pm, PMC_IE_ENABLED);
+ return start_value;
+}
+
+static void kvx_pmu_start(struct perf_event *event, int flags)
+{
+ struct hw_perf_event *hwc = &event->hw;
+ struct perf_event_attr *attr = &event->attr;
+ u64 pm_config = hwc->config;
+ unsigned int pm = hwc->idx;
+ u64 start_value = 0;
+
+ if (WARN_ON_ONCE(!(event->hw.state & PERF_HES_STOPPED)))
+ return;
+
+ if (flags & PERF_EF_RELOAD)
+ WARN_ON_ONCE(!(event->hw.state & PERF_HES_UPTODATE));
+
+ hwc->state = 0;
+ perf_event_update_userpage(event);
+
+ if (is_sampling_event(event))
+ start_value = kvx_start_sampling_event(event, pm);
+
+ local64_set(&hwc->prev_count, start_value);
+ if (attr->exclude_kernel)
+ give_pm_to_user(pm);
+ if (!is_sampling_event(event))
+ kvx_set_pmc(pm, KVX_PM_RE);
+ kvx_set_pmc(pm, pm_config);
+}
+
+static void kvx_pmu_stop(struct perf_event *event, int flags)
+{
+ struct hw_perf_event *hwc = &event->hw;
+ struct perf_event_attr *attr = &event->attr;
+ unsigned int pm = hwc->idx;
+
+ if (is_sampling_event(event))
+ kvx_stop_sampling_event(pm);
+
+ kvx_set_pmc(pm, KVX_PM_SE);
+ if (attr->exclude_kernel)
+ get_pm_back_to_kernel(pm);
+
+ WARN_ON_ONCE(hwc->state & PERF_HES_STOPPED);
+ hwc->state |= PERF_HES_STOPPED;
+
+ if ((flags & PERF_EF_UPDATE) && !(hwc->state & PERF_HES_UPTODATE)) {
+ kvx_pmu_read(event);
+ hwc->state |= PERF_HES_UPTODATE;
+ }
+}
+
+static void kvx_pmu_del(struct perf_event *event, int flags)
+{
+ struct hw_perf_event *hwc = &event->hw;
+ struct cpu_hw_events *cpuc = &get_cpu_var(cpu_hw_events);
+
+ cpuc->events[hwc->idx] = NULL;
+ cpuc->n_events--;
+ put_cpu_var(cpu_hw_events);
+ kvx_pmu_stop(event, PERF_EF_UPDATE);
+ perf_event_update_userpage(event);
+}
+
+static int kvx_pmu_add(struct perf_event *event, int flags)
+{
+ struct hw_perf_event *hwc = &event->hw;
+ struct cpu_hw_events *cpuc = &get_cpu_var(cpu_hw_events);
+ unsigned int i, idx = -1;
+
+ if (cpuc->n_events >= pm_num) {
+ put_cpu_var(cpu_hw_events);
+ return -ENOSPC;
+ }
+
+ for (i = 0; i < pm_num; i++)
+ if (cpuc->events[i] == NULL)
+ idx = i;
+
+ BUG_ON(idx == -1);
+
+ hwc->idx = idx;
+ cpuc->events[idx] = event;
+ cpuc->n_events++;
+ put_cpu_var(cpu_hw_events);
+ hwc->state = PERF_HES_UPTODATE | PERF_HES_STOPPED;
+
+ if (flags & PERF_EF_START)
+ kvx_pmu_start(event, PERF_EF_RELOAD);
+
+ return 0;
+}
+
+static enum kvx_pm_event_code kvx_pmu_cache_event(u64 config)
+{
+ unsigned int type, op, result;
+ enum kvx_pm_event_code code;
+
+ type = (config >> 0) & 0xff;
+ op = (config >> 8) & 0xff;
+ result = (config >> 16) & 0xff;
+ if (type >= PERF_COUNT_HW_CACHE_MAX ||
+ op >= PERF_COUNT_HW_CACHE_OP_MAX ||
+ result >= PERF_COUNT_HW_CACHE_RESULT_MAX)
+ return KVX_PM_UNSUPPORTED;
+
+ code = kvx_cache_map[type][op][result];
+
+ return code;
+}
+
+static int kvx_pm_starting_cpu(unsigned int cpu)
+{
+ struct cpu_hw_events *cpuc = &per_cpu(cpu_hw_events, cpu);
+
+ cpuc->events = kmalloc_array(pm_num, sizeof(struct perf_event *),
+ GFP_ATOMIC);
+ if (!cpuc->events)
+ return -ENOMEM;
+
+ memset(cpuc->events, 0, pm_num * sizeof(struct perf_event *));
+
+ enable_percpu_irq(kvx_pm_irq, IRQ_TYPE_NONE);
+ return 0;
+}
+
+static int kvx_pm_dying_cpu(unsigned int cpu)
+{
+ struct cpu_hw_events *cpuc = &get_cpu_var(cpu_hw_events);
+
+ disable_percpu_irq(kvx_pm_irq);
+ kfree(cpuc->events);
+ put_cpu_var(cpu_hw_events);
+ return 0;
+}
+
+static enum kvx_pm_event_code kvx_pmu_raw_events(u64 config)
+{
+ if (config >= KVX_PM_MAX)
+ return KVX_PM_UNSUPPORTED;
+
+ if (config == KVX_PM_SE || config == KVX_PM_RE)
+ return KVX_PM_UNSUPPORTED;
+
+ return config;
+}
+
+static int kvx_pmu_event_init(struct perf_event *event)
+{
+ struct perf_event_attr *attr = &event->attr;
+ struct hw_perf_event *hwc = &event->hw;
+ enum kvx_pm_event_code code;
+
+ if (attr->exclude_user && !attr->exclude_kernel) {
+ attr->exclude_user = 0;
+ pr_err_once("kvx_pm: Cannot exclude userspace from perf events and not kernelspace\n");
+ }
+
+ switch (attr->type) {
+ case PERF_TYPE_HARDWARE:
+ code = kvx_hw_event_map[attr->config];
+ break;
+ case PERF_TYPE_HW_CACHE:
+ code = kvx_pmu_cache_event(attr->config);
+ break;
+ case PERF_TYPE_RAW:
+ code = kvx_pmu_raw_events(attr->config);
+ break;
+ default:
+ return -ENOENT;
+ }
+
+ if (code == KVX_PM_UNSUPPORTED)
+ return -EOPNOTSUPP;
+
+ hwc->config = code;
+ hwc->idx = -1;
+
+ if (event->cpu >= 0 && !cpu_online(event->cpu))
+ return -ENODEV;
+
+ return 0;
+}
+
+static struct pmu pmu = {
+ .event_init = kvx_pmu_event_init,
+ .add = kvx_pmu_add,
+ .del = kvx_pmu_del,
+ .start = kvx_pmu_start,
+ .stop = kvx_pmu_stop,
+ .read = kvx_pmu_read,
+};
+
+static void kvx_pm_clear_sav(void)
+{
+ u64 clr_mask = KVX_SFR_PMC_SAV_MASK;
+ u64 set_mask = 0;
+
+ kvx_sfr_set_mask(PMC, clr_mask, set_mask);
+}
+
+static void kvx_pm_reload(struct perf_event *event)
+{
+ struct hw_perf_event *hwc = &event->hw;
+ u64 pm = hwc->idx;
+ u64 start_value = (u64)(-event->attr.sample_period);
+
+ kvx_set_pmc(pm, KVX_PM_SE);
+ kvx_set_pm(pm, start_value);
+}
+
+static bool kvx_pm_is_sav_set(void)
+{
+ return kvx_sfr_get(PMC) & KVX_SFR_PMC_SAV_MASK;
+}
+
+static int handle_pm_overflow(u8 pm_id, struct perf_event *event, u64 pmc,
+ struct pt_regs *regs)
+{
+ u64 pm_ie_mask = KVX_SFR_PMC_PM0IE_MASK << (pm_id + 1);
+ u64 pmc_event_code_mask = KVX_SFR_PMC_PM0C_MASK <<
+ ((pm_id + 1)
+ * KVX_SFR_PMC_PM1C_SHIFT);
+ struct hw_perf_event *hwc = &event->hw;
+ struct perf_sample_data data;
+ u64 sample_period;
+ u64 pm;
+
+ sample_period = event->attr.sample_period;
+ pm = kvx_sfr_iget(pm_id + KVX_SFR_PM1);
+
+ /*
+ * check if this pm has just overflowed
+ * ie: pm value is 0, pm interrupt is enabled
+ * and pm is not stopped.
+ */
+ if ((pm < local64_read(&hwc->prev_count)) && (pmc & pm_ie_mask)
+ && ((pmc & pmc_event_code_mask) != KVX_PM_SE)) {
+ perf_sample_data_init(&data, 0, sample_period);
+ if (perf_event_overflow(event, &data, regs))
+ pmu.stop(event, 0);
+ else {
+ kvx_pmu_read(event);
+ if (is_sampling_event(event))
+ kvx_pm_reload(event);
+ }
+ return 1;
+ }
+
+ return 0;
+}
+
+irqreturn_t pm_irq_handler(int irq, void *dev_id)
+{
+ struct cpu_hw_events *cpuc = &get_cpu_var(cpu_hw_events);
+ struct pt_regs *regs;
+ enum kvx_pm_idx pm_id;
+ u64 pmc;
+ bool a_pm_overflowed = false;
+ irqreturn_t ret = IRQ_NONE;
+
+ regs = get_irq_regs();
+ pmc = kvx_sfr_get(PMC);
+
+ for (pm_id = KVX_PM_1; pm_id <= KVX_PM_3; pm_id++) {
+ struct perf_event *event = cpuc->events[pm_id];
+
+ if (!event)
+ continue;
+
+ if (handle_pm_overflow(pm_id, event, pmc, regs)) {
+ ret = IRQ_HANDLED;
+ a_pm_overflowed = true;
+ }
+ }
+
+ put_cpu_var(cpu_hw_events);
+
+ if (likely(kvx_pm_is_sav_set()))
+ kvx_pm_clear_sav();
+ else
+ pr_err_once("kvx_pm: PM triggered an IRQ but did not set pmc.sav\n");
+
+ if (unlikely(!a_pm_overflowed))
+ pr_err_once("kvx_pm: PM triggered an IRQ but no PM seemed to have overflowed\n");
+
+ if (ret == IRQ_HANDLED)
+ irq_work_run();
+ return ret;
+}
+
+static int kvx_pmu_device_probe(struct platform_device *pdev)
+{
+ int ret;
+ int statenum;
+ struct device *dev = &pdev->dev;
+
+ ret = of_property_read_u32(dev->of_node, "kalray,pm-num", &pm_num);
+ if (ret < 0) {
+ dev_err(dev, "Cannot read kalray,pm-num from device tree\n");
+ return -ENODEV;
+ }
+
+ /*
+ * PM0 is reserved for cycle counting, that's why pm_num is
+ * decremented.
+ */
+ if (pm_num-- < 2) {
+ dev_err(dev, "Not enough PM to handle perf events, at least 2 are needed\n");
+ return -ENODEV;
+ }
+
+ kvx_pm_irq = platform_get_irq(pdev, 0);
+ if (!kvx_pm_irq) {
+ dev_err(dev, "Failed to parse pm irq\n");
+ return -ENODEV;
+ }
+
+ ret = request_percpu_irq(kvx_pm_irq, pm_irq_handler, "pm",
+ this_cpu_ptr(&cpu_hw_events));
+ if (ret) {
+ dev_err(dev, "Failed to request pm irq\n");
+ return -ENODEV;
+ }
+
+ ret = cpuhp_setup_state(CPUHP_AP_ONLINE_DYN,
+ "kvx/pm_handler:online",
+ kvx_pm_starting_cpu,
+ kvx_pm_dying_cpu);
+
+ if (ret <= 0) {
+ dev_err(dev, "Failed to setup cpuhp\n");
+ goto free_irq;
+ }
+ statenum = ret;
+
+ ret = perf_pmu_register(&pmu, "cpu", PERF_TYPE_RAW);
+ if (ret) {
+ dev_err(dev, "Failed to register CPU PM as PMU\n");
+ goto free_cpuhp_state;
+ }
+
+ return ret;
+
+free_cpuhp_state:
+ cpuhp_remove_state(statenum);
+free_irq:
+ free_percpu_irq(kvx_pm_irq, this_cpu_ptr(&cpu_hw_events));
+ return ret;
+}
+
+static const struct of_device_id kvx_pmu_of_device_ids[] = {
+ {.compatible = "kalray,kvx-core-pm"},
+ {},
+};
+
+static struct platform_driver kvx_pmu_driver = {
+ .driver = {
+ .name = "pmu",
+ .of_match_table = kvx_pmu_of_device_ids,
+ },
+ .probe = kvx_pmu_device_probe,
+};
+
+static int __init kvx_pmu_driver_init(void)
+{
+ return platform_driver_register(&kvx_pmu_driver);
+}
+
+device_initcall(kvx_pmu_driver_init);
--
2.37.2
^ permalink raw reply related [flat|nested] 13+ messages in thread
* Re: [RFC PATCH 00/25] Upstream kvx Linux port
2023-01-03 16:43 [RFC PATCH 00/25] Upstream kvx Linux port Yann Sionneau
2023-01-03 16:43 ` [RFC PATCH 24/25] kvx: Add support for CPU Perf Monitors Yann Sionneau
@ 2023-01-03 20:52 ` Rob Herring
2023-01-04 15:58 ` Arnd Bergmann
2023-01-07 6:25 ` Jeff Xie
3 siblings, 0 replies; 13+ messages in thread
From: Rob Herring @ 2023-01-03 20:52 UTC (permalink / raw)
To: Yann Sionneau
Cc: Arnd Bergmann, Albert Ou, Alexander Shishkin, Andrew Morton,
Aneesh Kumar K.V, Ard Biesheuvel, Arnaldo Carvalho de Melo,
Boqun Feng, bpf, Christian Brauner, devicetree, Eric Biederman,
Eric Paris, Ingo Molnar, Jan Kiszka, Jason Baron, Jiri Olsa,
Jonathan Corbet, Josh Poimboeuf, Kees Cook, Kieran Bingham,
Krzysztof Kozlowski, linux-arch, linux-arm-kernel, linux-audit,
linux-doc, linux-kernel, linux-mm, linux-perf-users, linux-pm,
linux-riscv, Marc Zyngier, Mark Rutland, Masami Hiramatsu,
Namhyung Kim, Nick Piggin, Oleg Nesterov, Palmer Dabbelt,
Paul Moore, Paul Walmsley, Peter Zijlstra, Sebastian Reichel,
Steven Rostedt, Thomas Gleixner, Waiman Long, Will Deacon,
Alex Michon, Ashley Lesdalons, Benjamin Mugnier, Clement Leger,
Guillaume Missonnier, Guillaume Thouvenin, Jean-Christophe Pince,
Jonathan Borne, Jules Maselbas, Julian Vetter, Julien Hascoet,
Julien Villette, Louis Morhet, Luc Michel, Marc Poulhiès,
Marius Gligor, Samuel Jones, Thomas Costis, Vincent Chardon
On Tue, Jan 03, 2023 at 05:43:34PM +0100, Yann Sionneau wrote:
> This patch series adds support for the kv3-1 CPU architecture of the kvx family
> found in the Coolidge (aka MPPA3-80) SoC of Kalray.
>
> This is an RFC, since kvx support is not yet upstreamed into gcc/binutils,
> therefore this patch series cannot be merged into Linux for now.
>
> The goal is to have preliminary reviews and to fix problems early.
>
> The Kalray VLIW processor family (kvx) has the following features:
> * 32/64 bits execution mode
> * 6-issue VLIW architecture
> * 64 x 64bits general purpose registers
> * SIMD instructions
> * little-endian
> * deep learning co-processor
>
> Kalray kv3-1 core which is the third of the kvx family is embedded in Kalray
> Coolidge SoC currently used on K200 and K200-LP boards.
>
> The Coolidge SoC contains 5 clusters each of which is made of:
> * 4MiB of on-chip memory (SMEM)
> * 1 dedicated safety/security core (kv3-1 core).
> * 16 PEs (Processing Elements) (kv3-1 cores).
> * 16 Co-processors (one per PE)
> * 2 Crypto accelerators
>
> The Coolidge SoC contains the following features:
> * 5 Clusters
> * 2 100G Ethernet controllers
> * 8 PCIe GEN4 controllers (Root Complex and Endpoint capable)
> * 2 USB 2.0 controllers
> * 1 Octal SPI-NOR flash controller
> * 1 eMMC controller
> * 3 Quad SPI controllers
> * 6 UART
> * 5 I2C controllers (3 of which are SMBus capable)
> * 4 CAN controllers
> * 1 OTP memory
>
> A kvx toolchain can be built using:
> # install dependencies: texinfo bison flex libgmp-dev libmpc-dev libmpfr-dev
> $ git clone https://github.com/kalray/build-scripts
> $ cd build-scripts
> $ source last.refs
> $ ./build-kvx-xgcc.sh output
>
> The kvx toolchain will be installed in the "output" directory.
>
> A buildroot image (kernel+rootfs) and toolchain can be built using:
> $ git clone -b coolidge-for-upstream https://github.com/kalray/buildroot
> $ cd buildroot
> $ make O=build_kvx kvx_defconfig
> $ make O=build_kvx
>
> The vmlinux image can be found in buildroot/build_kvx/images/vmlinux.
>
> If you are just interested in building the Linux kernel with no rootfs you can
> just do this with the kvx-elf- toolchain:
> $ make ARCH=kvx O=build_kvx CROSS_COMPILE=kvx-elf- default_defconfig
> $ make ARCH=kvx O=build_kvx CROSS_COMPILE=kvx-elf- -j$(($(nproc) + 1))
>
> The vmlinux ELF can be run with qemu by doing:
> # install dependencies: ninja pkg-config libglib-2.0-dev cmake libfdt-dev libpixman-1-dev zlib1g-dev
> $ git clone https://github.com/kalray/qemu-builder
> $ cd qemu-builder
> $ git submodule update --init
> $ make -j$(($(nproc) + 1))
> $ ./qemu-system-kvx -m 1024 -nographic -kernel <path/to/vmlinux>
>
> Yann Sionneau (25):
> Documentation: kvx: Add basic documentation
> kvx: Add ELF-related definitions
> kvx: Add build infrastructure
> kvx: Add CPU definition headers
> kvx: Add atomic/locking headers
> kvx: Add other common headers
> kvx: Add boot and setup routines
> kvx: Add exception/interrupt handling
> kvx: irqchip: Add support for irq controllers
> kvx: Add process management
> kvx: Add memory management
> kvx: Add system call support
> kvx: Add signal handling support
> kvx: Add ELF relocations and module support
> kvx: Add misc common routines
> kvx: Add some library functions
> kvx: Add multi-processor (SMP) support
> kvx: Add kvx default config file
> kvx: power: scall poweroff driver
> kvx: gdb: add kvx related gdb helpers
> kvx: Add support for ftrace
> kvx: Add support for jump labels
> kvx: Add debugging related support
> kvx: Add support for CPU Perf Monitors
> kvx: Add support for cpuinfo
You should strip this series down to just what's needed to boot. You
don't need the last 7 patches at least.
Rob
^ permalink raw reply [flat|nested] 13+ messages in thread
* Re: [RFC PATCH 00/25] Upstream kvx Linux port
2023-01-03 16:43 [RFC PATCH 00/25] Upstream kvx Linux port Yann Sionneau
2023-01-03 16:43 ` [RFC PATCH 24/25] kvx: Add support for CPU Perf Monitors Yann Sionneau
2023-01-03 20:52 ` [RFC PATCH 00/25] Upstream kvx Linux port Rob Herring
@ 2023-01-04 15:58 ` Arnd Bergmann
2023-01-05 10:40 ` Jules Maselbas
2023-01-07 6:25 ` Jeff Xie
3 siblings, 1 reply; 13+ messages in thread
From: Arnd Bergmann @ 2023-01-04 15:58 UTC (permalink / raw)
To: Yann Sionneau
Cc: Albert Ou, Alexander Shishkin, Andrew Morton, Aneesh Kumar,
Ard Biesheuvel, Arnaldo Carvalho de Melo, Boqun Feng, bpf,
Christian Brauner, devicetree, Eric W. Biederman, Eric Paris,
Ingo Molnar, Jan Kiszka, Jason Baron, Jiri Olsa, Jonathan Corbet,
Josh Poimboeuf, Kees Cook, Kieran Bingham, Krzysztof Kozlowski,
Linux-Arch, linux-arm-kernel, linux-audit, linux-doc,
linux-kernel, linux-mm, linux-perf-users, linux-pm, linux-riscv,
Marc Zyngier, Mark Rutland, Masami Hiramatsu, Namhyung Kim,
Nicholas Piggin, Oleg Nesterov, Palmer Dabbelt, Paul Moore,
Paul Walmsley, Peter Zijlstra, Rob Herring, Sebastian Reichel,
Steven Rostedt, Thomas Gleixner, Waiman Long, Will Deacon,
Alex Michon, Ashley Lesdalons, Benjamin Mugnier, Clement Leger,
Guillaume Missonnier, Guillaume Thouvenin, Jean-Christophe Pince,
Jonathan Borne, Jules Maselbas, Julian Vetter, Julien Hascoet,
Julien Villette, Louis Morhet, Luc Michel, Marc Poulhiès,
Marius Gligor, Samuel Jones, Thomas Costis, Vincent Chardon
On Tue, Jan 3, 2023, at 17:43, Yann Sionneau wrote:
> This patch series adds support for the kv3-1 CPU architecture of the kvx family
> found in the Coolidge (aka MPPA3-80) SoC of Kalray.
>
> This is an RFC, since kvx support is not yet upstreamed into gcc/binutils,
> therefore this patch series cannot be merged into Linux for now.
>
> The goal is to have preliminary reviews and to fix problems early.
>
> The Kalray VLIW processor family (kvx) has the following features:
> * 32/64 bits execution mode
> * 6-issue VLIW architecture
> * 64 x 64bits general purpose registers
> * SIMD instructions
> * little-endian
> * deep learning co-processor
Thanks for posting these, I had been wondering about the
state of the port. Overall this looks really nice, I can
see that you and the team have looked at other ports
and generally made the right decisions.
I commented on the syscall patch directly, I think it's
important to stop using the deprecated syscalls as soon
as possible to avoid having dependencies in too many
libc binaries. Almost everything else can be changed
easily as you get closer to upstream inclusion.
I did not receive most of the other patches as I'm
not subscribed to all the mainline lists. For future
submissions, can you add the linux-arch list to Cc for
all patches?
Reading the rest of the series through lore.kernel.org,
most of the comments I have are for improvements that
you may find valuable rather than serious mistakes:
- the {copy_to,copy_from,clear}_user functions are
well worth optimizing better than the byte-at-a-time
version you have, even just a C version built around
your __get_user/__put_user inline asm should help, and
could be added to lib/usercopy.c.
- The __raw_{read,write}{b,w,l,q} helpers should
normally be defined as inline asm instead of
volatile pointer dereferences, I've seen cases where
the compiler ends up splitting the access or does
other things you may not want on MMIO areas.
- I would recomment implementing HAVE_ARCH_VMAP_STACK
as well as IRQ stacks, both of these help to
avoid data corruption from stack overflow that you
will eventually run into.
- You use qspinlock as the only available spinlock
implementation, but only support running on a
single cluster of 16 cores. It may help to use
the generic ticket spinlock instead, or leave it
as a Kconfig option, in particular since you only
have the emulated xchg16() atomic for qspinlock.
- Your defconfig file enables CONFIG_EMBEDDED, which
in turn enables CONFIG_EXPERT. This is probably
not what you want, so better turn off both of these.
- The GENERIC_CALIBRATE_DELAY should not be necessary
since you have a get_cycles() based delay loop.
Just set loops_per_jiffy to the correct value based
on the frequency of the cycle counter, to save
a little time during boot and get a more accurate
delay loop.
Arnd
^ permalink raw reply [flat|nested] 13+ messages in thread
* Re: [RFC PATCH 00/25] Upstream kvx Linux port
2023-01-03 16:43 [RFC PATCH 00/25] Upstream kvx Linux port Yann Sionneau
` (2 preceding siblings ...)
2023-01-04 15:58 ` Arnd Bergmann
@ 2023-01-07 6:25 ` Jeff Xie
2023-01-09 13:21 ` Yann Sionneau
3 siblings, 1 reply; 13+ messages in thread
From: Jeff Xie @ 2023-01-07 6:25 UTC (permalink / raw)
To: Yann Sionneau
Cc: Arnd Bergmann, Albert Ou, Alexander Shishkin, Andrew Morton,
Aneesh Kumar K.V, Ard Biesheuvel, Arnaldo Carvalho de Melo,
Boqun Feng, bpf, Christian Brauner, devicetree, Eric Biederman,
Eric Paris, Ingo Molnar, Jan Kiszka, Jason Baron, Jiri Olsa,
Jonathan Corbet, Josh Poimboeuf, Kees Cook, Kieran Bingham,
Krzysztof Kozlowski, linux-arch, linux-arm-kernel, linux-audit,
linux-doc, linux-kernel, linux-mm, linux-perf-users, linux-pm,
linux-riscv, Marc Zyngier, Mark Rutland, Masami Hiramatsu,
Namhyung Kim, Nick Piggin, Oleg Nesterov, Palmer Dabbelt,
Paul Moore, Paul Walmsley, Peter Zijlstra, Rob Herring,
Sebastian Reichel, Steven Rostedt, Thomas Gleixner, Waiman Long,
Will Deacon, Alex Michon, Ashley Lesdalons, Benjamin Mugnier,
Clement Leger, Guillaume Missonnier, Guillaume Thouvenin,
Jean-Christophe Pince, Jonathan Borne, Jules Maselbas,
Julian Vetter, Julien Hascoet, Julien Villette, Louis Morhet,
Luc Michel, Marc Poulhiès, Marius Gligor, Samuel Jones,
Thomas Costis, Vincent Chardon
Hi,
On Wed, Jan 4, 2023 at 1:01 AM Yann Sionneau <ysionneau@kalray.eu> wrote:
>
> This patch series adds support for the kv3-1 CPU architecture of the kvx family
> found in the Coolidge (aka MPPA3-80) SoC of Kalray.
>
> This is an RFC, since kvx support is not yet upstreamed into gcc/binutils,
> therefore this patch series cannot be merged into Linux for now.
>
> The goal is to have preliminary reviews and to fix problems early.
>
> The Kalray VLIW processor family (kvx) has the following features:
> * 32/64 bits execution mode
> * 6-issue VLIW architecture
> * 64 x 64bits general purpose registers
> * SIMD instructions
> * little-endian
> * deep learning co-processor
>
> Kalray kv3-1 core which is the third of the kvx family is embedded in Kalray
> Coolidge SoC currently used on K200 and K200-LP boards.
>
> The Coolidge SoC contains 5 clusters each of which is made of:
> * 4MiB of on-chip memory (SMEM)
> * 1 dedicated safety/security core (kv3-1 core).
> * 16 PEs (Processing Elements) (kv3-1 cores).
> * 16 Co-processors (one per PE)
> * 2 Crypto accelerators
>
> The Coolidge SoC contains the following features:
> * 5 Clusters
> * 2 100G Ethernet controllers
> * 8 PCIe GEN4 controllers (Root Complex and Endpoint capable)
> * 2 USB 2.0 controllers
> * 1 Octal SPI-NOR flash controller
> * 1 eMMC controller
> * 3 Quad SPI controllers
> * 6 UART
> * 5 I2C controllers (3 of which are SMBus capable)
> * 4 CAN controllers
> * 1 OTP memory
>
> A kvx toolchain can be built using:
> # install dependencies: texinfo bison flex libgmp-dev libmpc-dev libmpfr-dev
> $ git clone https://github.com/kalray/build-scripts
> $ cd build-scripts
> $ source last.refs
> $ ./build-kvx-xgcc.sh output
I would like to build the kvx-xgcc to compile and test the linux
kernel, but it reported a compile error.
I wonder what version of gcc you are using.
My build environment:
VERSION="20.04.2 LTS (Focal Fossa)"
gcc version 9.3.0 (Ubuntu 9.3.0-17ubuntu1~20.04)
Compile error:
$ ./build-kvx-xgcc.sh output
../../binutils/libiberty/fibheap.c: In function ‘fibheap_replace_key_data’:
../../binutils/libiberty/fibheap.c:38:24: error: ‘LONG_MIN’ undeclared
(first use in this function)
38 | #define FIBHEAPKEY_MIN LONG_MIN
| ^~~~~~~~
../../binutils/libiberty/fibheap.c:220:30: note: in expansion of macro
‘FIBHEAPKEY_MIN’
220 | if (okey == key && okey != FIBHEAPKEY_MIN)
| ^~~~~~~~~~~~~~
../../binutils/libiberty/fibheap.c:36:1: note: ‘LONG_MIN’ is defined
in header ‘<limits.h>’; did you forget to ‘#include <limits.h>’?
35 | #include "fibheap.h"
+++ |+#include <limits.h>
36 |
../../binutils/libiberty/fibheap.c:38:24: note: each undeclared
identifier is reported only once for each function it appears in
38 | #define FIBHEAPKEY_MIN LONG_MIN
| ^~~~~~~~
../../binutils/libiberty/fibheap.c:220:30: note: in expansion of macro
‘FIBHEAPKEY_MIN’
220 | if (okey == key && okey != FIBHEAPKEY_MIN)
| ^~~~~~~~~~~~~~
../../binutils/libiberty/fibheap.c: In function ‘fibheap_delete_node’:
../../binutils/libiberty/fibheap.c:38:24: error: ‘LONG_MIN’ undeclared
(first use in this function)
38 | #define FIBHEAPKEY_MIN LONG_MIN
| ^~~~~~~~
../../binutils/libiberty/fibheap.c:261:36: note: in expansion of macro
‘FIBHEAPKEY_MIN’
261 | fibheap_replace_key (heap, node, FIBHEAPKEY_MIN);
| ^~~~~~~~~~~~~~
../../binutils/libiberty/fibheap.c:38:24: note: ‘LONG_MIN’ is defined
in header ‘<limits.h>’; did you forget to ‘#include <limits.h>’?
38 | #define FIBHEAPKEY_MIN LONG_MIN
| ^~~~~~~~
../../binutils/libiberty/fibheap.c:261:36: note: in expansion of macro
‘FIBHEAPKEY_MIN’
261 | fibheap_replace_key (heap, node, FIBHEAPKEY_MIN);
| ^~~~~~~~~~~~~~
> The kvx toolchain will be installed in the "output" directory.
>
> A buildroot image (kernel+rootfs) and toolchain can be built using:
> $ git clone -b coolidge-for-upstream https://github.com/kalray/buildroot
> $ cd buildroot
> $ make O=build_kvx kvx_defconfig
> $ make O=build_kvx
>
> The vmlinux image can be found in buildroot/build_kvx/images/vmlinux.
>
> If you are just interested in building the Linux kernel with no rootfs you can
> just do this with the kvx-elf- toolchain:
> $ make ARCH=kvx O=build_kvx CROSS_COMPILE=kvx-elf- default_defconfig
> $ make ARCH=kvx O=build_kvx CROSS_COMPILE=kvx-elf- -j$(($(nproc) + 1))
>
> The vmlinux ELF can be run with qemu by doing:
> # install dependencies: ninja pkg-config libglib-2.0-dev cmake libfdt-dev libpixman-1-dev zlib1g-dev
> $ git clone https://github.com/kalray/qemu-builder
> $ cd qemu-builder
> $ git submodule update --init
> $ make -j$(($(nproc) + 1))
> $ ./qemu-system-kvx -m 1024 -nographic -kernel <path/to/vmlinux>
>
> Yann Sionneau (25):
> Documentation: kvx: Add basic documentation
> kvx: Add ELF-related definitions
> kvx: Add build infrastructure
> kvx: Add CPU definition headers
> kvx: Add atomic/locking headers
> kvx: Add other common headers
> kvx: Add boot and setup routines
> kvx: Add exception/interrupt handling
> kvx: irqchip: Add support for irq controllers
> kvx: Add process management
> kvx: Add memory management
> kvx: Add system call support
> kvx: Add signal handling support
> kvx: Add ELF relocations and module support
> kvx: Add misc common routines
> kvx: Add some library functions
> kvx: Add multi-processor (SMP) support
> kvx: Add kvx default config file
> kvx: power: scall poweroff driver
> kvx: gdb: add kvx related gdb helpers
> kvx: Add support for ftrace
> kvx: Add support for jump labels
> kvx: Add debugging related support
> kvx: Add support for CPU Perf Monitors
> kvx: Add support for cpuinfo
>
> .../kalray,kvx-core-intc.txt | 22 +
> .../devicetree/bindings/perf/kalray-pm.txt | 21 +
> Documentation/kvx/kvx-exceptions.txt | 246 +
> Documentation/kvx/kvx-iommu.txt | 183 +
> Documentation/kvx/kvx-mmu.txt | 272 +
> Documentation/kvx/kvx-smp.txt | 36 +
> Documentation/kvx/kvx.txt | 268 +
> arch/kvx/Kconfig | 249 +
> arch/kvx/Kconfig.debug | 70 +
> arch/kvx/Makefile | 52 +
> arch/kvx/configs/default_defconfig | 130 +
> arch/kvx/include/asm/Kbuild | 20 +
> arch/kvx/include/asm/asm-prototypes.h | 14 +
> arch/kvx/include/asm/atomic.h | 104 +
> arch/kvx/include/asm/barrier.h | 15 +
> arch/kvx/include/asm/bitops.h | 207 +
> arch/kvx/include/asm/bitrev.h | 32 +
> arch/kvx/include/asm/break_hook.h | 69 +
> arch/kvx/include/asm/bug.h | 67 +
> arch/kvx/include/asm/cache.h | 46 +
> arch/kvx/include/asm/cacheflush.h | 181 +
> arch/kvx/include/asm/clocksource.h | 17 +
> arch/kvx/include/asm/cmpxchg.h | 185 +
> arch/kvx/include/asm/current.h | 22 +
> arch/kvx/include/asm/dame.h | 31 +
> arch/kvx/include/asm/debug.h | 35 +
> arch/kvx/include/asm/elf.h | 155 +
> arch/kvx/include/asm/fixmap.h | 47 +
> arch/kvx/include/asm/ftrace.h | 41 +
> arch/kvx/include/asm/futex.h | 141 +
> arch/kvx/include/asm/hardirq.h | 14 +
> arch/kvx/include/asm/hugetlb.h | 36 +
> arch/kvx/include/asm/hw_breakpoint.h | 72 +
> arch/kvx/include/asm/hw_irq.h | 14 +
> arch/kvx/include/asm/insns.h | 16 +
> arch/kvx/include/asm/insns_defs.h | 197 +
> arch/kvx/include/asm/io.h | 34 +
> arch/kvx/include/asm/ipi.h | 16 +
> arch/kvx/include/asm/irqflags.h | 58 +
> arch/kvx/include/asm/jump_label.h | 59 +
> arch/kvx/include/asm/l2_cache.h | 75 +
> arch/kvx/include/asm/l2_cache_defs.h | 64 +
> arch/kvx/include/asm/linkage.h | 13 +
> arch/kvx/include/asm/mem_map.h | 44 +
> arch/kvx/include/asm/mmu.h | 296 +
> arch/kvx/include/asm/mmu_context.h | 156 +
> arch/kvx/include/asm/mmu_stats.h | 38 +
> arch/kvx/include/asm/page.h | 187 +
> arch/kvx/include/asm/page_size.h | 29 +
> arch/kvx/include/asm/pci.h | 36 +
> arch/kvx/include/asm/perf_event.h | 90 +
> arch/kvx/include/asm/pgalloc.h | 101 +
> arch/kvx/include/asm/pgtable-bits.h | 102 +
> arch/kvx/include/asm/pgtable.h | 451 ++
> arch/kvx/include/asm/privilege.h | 211 +
> arch/kvx/include/asm/processor.h | 176 +
> arch/kvx/include/asm/ptrace.h | 217 +
> arch/kvx/include/asm/pwr_ctrl.h | 45 +
> arch/kvx/include/asm/rm_fw.h | 16 +
> arch/kvx/include/asm/sections.h | 18 +
> arch/kvx/include/asm/setup.h | 29 +
> arch/kvx/include/asm/sfr.h | 107 +
> arch/kvx/include/asm/sfr_defs.h | 5028 +++++++++++++++++
> arch/kvx/include/asm/smp.h | 42 +
> arch/kvx/include/asm/sparsemem.h | 15 +
> arch/kvx/include/asm/spinlock.h | 16 +
> arch/kvx/include/asm/spinlock_types.h | 17 +
> arch/kvx/include/asm/stackprotector.h | 47 +
> arch/kvx/include/asm/stacktrace.h | 44 +
> arch/kvx/include/asm/string.h | 20 +
> arch/kvx/include/asm/swab.h | 48 +
> arch/kvx/include/asm/switch_to.h | 21 +
> arch/kvx/include/asm/symbols.h | 16 +
> arch/kvx/include/asm/sys_arch.h | 51 +
> arch/kvx/include/asm/syscall.h | 73 +
> arch/kvx/include/asm/syscalls.h | 21 +
> arch/kvx/include/asm/thread_info.h | 78 +
> arch/kvx/include/asm/timex.h | 20 +
> arch/kvx/include/asm/tlb.h | 24 +
> arch/kvx/include/asm/tlb_defs.h | 131 +
> arch/kvx/include/asm/tlbflush.h | 58 +
> arch/kvx/include/asm/traps.h | 76 +
> arch/kvx/include/asm/types.h | 12 +
> arch/kvx/include/asm/uaccess.h | 324 ++
> arch/kvx/include/asm/unistd.h | 11 +
> arch/kvx/include/asm/vermagic.h | 12 +
> arch/kvx/include/asm/vmalloc.h | 10 +
> arch/kvx/include/uapi/asm/Kbuild | 1 +
> arch/kvx/include/uapi/asm/bitsperlong.h | 14 +
> arch/kvx/include/uapi/asm/byteorder.h | 12 +
> arch/kvx/include/uapi/asm/cachectl.h | 25 +
> arch/kvx/include/uapi/asm/ptrace.h | 114 +
> arch/kvx/include/uapi/asm/sigcontext.h | 16 +
> arch/kvx/include/uapi/asm/unistd.h | 16 +
> arch/kvx/kernel/Makefile | 27 +
> arch/kvx/kernel/asm-offsets.c | 157 +
> arch/kvx/kernel/break_hook.c | 77 +
> arch/kvx/kernel/common.c | 11 +
> arch/kvx/kernel/cpuinfo.c | 96 +
> arch/kvx/kernel/dame_handler.c | 113 +
> arch/kvx/kernel/debug.c | 64 +
> arch/kvx/kernel/entry.S | 1759 ++++++
> arch/kvx/kernel/ftrace.c | 339 ++
> arch/kvx/kernel/head.S | 612 ++
> arch/kvx/kernel/hw_breakpoint.c | 556 ++
> arch/kvx/kernel/insns.c | 146 +
> arch/kvx/kernel/io.c | 96 +
> arch/kvx/kernel/irq.c | 78 +
> arch/kvx/kernel/jump_label.c | 34 +
> arch/kvx/kernel/kvx_ksyms.c | 29 +
> arch/kvx/kernel/l2_cache.c | 448 ++
> arch/kvx/kernel/mcount.S | 340 ++
> arch/kvx/kernel/module.c | 148 +
> arch/kvx/kernel/perf_event.c | 609 ++
> arch/kvx/kernel/process.c | 212 +
> arch/kvx/kernel/prom.c | 24 +
> arch/kvx/kernel/ptrace.c | 461 ++
> arch/kvx/kernel/reset.c | 37 +
> arch/kvx/kernel/return_address.c | 55 +
> arch/kvx/kernel/setup.c | 178 +
> arch/kvx/kernel/signal.c | 266 +
> arch/kvx/kernel/smp.c | 110 +
> arch/kvx/kernel/smpboot.c | 127 +
> arch/kvx/kernel/stacktrace.c | 173 +
> arch/kvx/kernel/sys_kvx.c | 58 +
> arch/kvx/kernel/syscall_table.c | 19 +
> arch/kvx/kernel/time.c | 242 +
> arch/kvx/kernel/traps.c | 243 +
> arch/kvx/kernel/vdso.c | 87 +
> arch/kvx/kernel/vmlinux.lds.S | 173 +
> arch/kvx/lib/Makefile | 6 +
> arch/kvx/lib/clear_page.S | 40 +
> arch/kvx/lib/copy_page.S | 90 +
> arch/kvx/lib/delay.c | 39 +
> arch/kvx/lib/memcpy.c | 70 +
> arch/kvx/lib/memset.S | 351 ++
> arch/kvx/lib/strlen.S | 122 +
> arch/kvx/lib/usercopy.S | 90 +
> arch/kvx/mm/Makefile | 10 +
> arch/kvx/mm/cacheflush.c | 154 +
> arch/kvx/mm/dma-mapping.c | 95 +
> arch/kvx/mm/extable.c | 24 +
> arch/kvx/mm/fault.c | 264 +
> arch/kvx/mm/hugetlbpage.c | 317 ++
> arch/kvx/mm/init.c | 527 ++
> arch/kvx/mm/kernel_rwx.c | 228 +
> arch/kvx/mm/mmap.c | 31 +
> arch/kvx/mm/mmu.c | 204 +
> arch/kvx/mm/mmu_stats.c | 94 +
> arch/kvx/mm/tlb.c | 433 ++
> arch/kvx/platform/Makefile | 7 +
> arch/kvx/platform/ipi.c | 110 +
> arch/kvx/platform/pwr_ctrl.c | 93 +
> drivers/irqchip/Kconfig | 27 +
> drivers/irqchip/Makefile | 4 +
> drivers/irqchip/irq-kvx-apic-gic.c | 349 ++
> drivers/irqchip/irq-kvx-apic-mailbox.c | 465 ++
> drivers/irqchip/irq-kvx-core-intc.c | 82 +
> drivers/irqchip/irq-kvx-itgen.c | 224 +
> drivers/power/reset/kvx-scall-poweroff.c | 53 +
> include/linux/cpuhotplug.h | 2 +
> include/linux/irqchip/irq-kvx-apic-gic.h | 21 +
> include/linux/irqchip/irq-kvx-apic-mailbox.h | 29 +
> include/linux/irqchip/irq-kvx-itgen.h | 24 +
> include/uapi/linux/audit.h | 1 +
> include/uapi/linux/elf-em.h | 1 +
> include/uapi/linux/elf.h | 1 +
> scripts/gdb/arch/Makefile | 11 +
> scripts/gdb/arch/__init__.py | 1 +
> scripts/gdb/arch/kvx/Makefile | 25 +
> scripts/gdb/arch/kvx/__init__.py | 1 +
> scripts/gdb/arch/kvx/constants.py.in | 74 +
> scripts/gdb/arch/kvx/mmu.py | 199 +
> scripts/gdb/arch/kvx/page_table_walk.py | 207 +
> tools/include/uapi/asm/bitsperlong.h | 2 +
> 175 files changed, 25814 insertions(+)
> create mode 100644 Documentation/devicetree/bindings/interrupt-controller/kalray,kvx-core-intc.txt
> create mode 100644 Documentation/devicetree/bindings/perf/kalray-pm.txt
> create mode 100644 Documentation/kvx/kvx-exceptions.txt
> create mode 100644 Documentation/kvx/kvx-iommu.txt
> create mode 100644 Documentation/kvx/kvx-mmu.txt
> create mode 100644 Documentation/kvx/kvx-smp.txt
> create mode 100644 Documentation/kvx/kvx.txt
> create mode 100644 arch/kvx/Kconfig
> create mode 100644 arch/kvx/Kconfig.debug
> create mode 100644 arch/kvx/Makefile
> create mode 100644 arch/kvx/configs/default_defconfig
> create mode 100644 arch/kvx/include/asm/Kbuild
> create mode 100644 arch/kvx/include/asm/asm-prototypes.h
> create mode 100644 arch/kvx/include/asm/atomic.h
> create mode 100644 arch/kvx/include/asm/barrier.h
> create mode 100644 arch/kvx/include/asm/bitops.h
> create mode 100644 arch/kvx/include/asm/bitrev.h
> create mode 100644 arch/kvx/include/asm/break_hook.h
> create mode 100644 arch/kvx/include/asm/bug.h
> create mode 100644 arch/kvx/include/asm/cache.h
> create mode 100644 arch/kvx/include/asm/cacheflush.h
> create mode 100644 arch/kvx/include/asm/clocksource.h
> create mode 100644 arch/kvx/include/asm/cmpxchg.h
> create mode 100644 arch/kvx/include/asm/current.h
> create mode 100644 arch/kvx/include/asm/dame.h
> create mode 100644 arch/kvx/include/asm/debug.h
> create mode 100644 arch/kvx/include/asm/elf.h
> create mode 100644 arch/kvx/include/asm/fixmap.h
> create mode 100644 arch/kvx/include/asm/ftrace.h
> create mode 100644 arch/kvx/include/asm/futex.h
> create mode 100644 arch/kvx/include/asm/hardirq.h
> create mode 100644 arch/kvx/include/asm/hugetlb.h
> create mode 100644 arch/kvx/include/asm/hw_breakpoint.h
> create mode 100644 arch/kvx/include/asm/hw_irq.h
> create mode 100644 arch/kvx/include/asm/insns.h
> create mode 100644 arch/kvx/include/asm/insns_defs.h
> create mode 100644 arch/kvx/include/asm/io.h
> create mode 100644 arch/kvx/include/asm/ipi.h
> create mode 100644 arch/kvx/include/asm/irqflags.h
> create mode 100644 arch/kvx/include/asm/jump_label.h
> create mode 100644 arch/kvx/include/asm/l2_cache.h
> create mode 100644 arch/kvx/include/asm/l2_cache_defs.h
> create mode 100644 arch/kvx/include/asm/linkage.h
> create mode 100644 arch/kvx/include/asm/mem_map.h
> create mode 100644 arch/kvx/include/asm/mmu.h
> create mode 100644 arch/kvx/include/asm/mmu_context.h
> create mode 100644 arch/kvx/include/asm/mmu_stats.h
> create mode 100644 arch/kvx/include/asm/page.h
> create mode 100644 arch/kvx/include/asm/page_size.h
> create mode 100644 arch/kvx/include/asm/pci.h
> create mode 100644 arch/kvx/include/asm/perf_event.h
> create mode 100644 arch/kvx/include/asm/pgalloc.h
> create mode 100644 arch/kvx/include/asm/pgtable-bits.h
> create mode 100644 arch/kvx/include/asm/pgtable.h
> create mode 100644 arch/kvx/include/asm/privilege.h
> create mode 100644 arch/kvx/include/asm/processor.h
> create mode 100644 arch/kvx/include/asm/ptrace.h
> create mode 100644 arch/kvx/include/asm/pwr_ctrl.h
> create mode 100644 arch/kvx/include/asm/rm_fw.h
> create mode 100644 arch/kvx/include/asm/sections.h
> create mode 100644 arch/kvx/include/asm/setup.h
> create mode 100644 arch/kvx/include/asm/sfr.h
> create mode 100644 arch/kvx/include/asm/sfr_defs.h
> create mode 100644 arch/kvx/include/asm/smp.h
> create mode 100644 arch/kvx/include/asm/sparsemem.h
> create mode 100644 arch/kvx/include/asm/spinlock.h
> create mode 100644 arch/kvx/include/asm/spinlock_types.h
> create mode 100644 arch/kvx/include/asm/stackprotector.h
> create mode 100644 arch/kvx/include/asm/stacktrace.h
> create mode 100644 arch/kvx/include/asm/string.h
> create mode 100644 arch/kvx/include/asm/swab.h
> create mode 100644 arch/kvx/include/asm/switch_to.h
> create mode 100644 arch/kvx/include/asm/symbols.h
> create mode 100644 arch/kvx/include/asm/sys_arch.h
> create mode 100644 arch/kvx/include/asm/syscall.h
> create mode 100644 arch/kvx/include/asm/syscalls.h
> create mode 100644 arch/kvx/include/asm/thread_info.h
> create mode 100644 arch/kvx/include/asm/timex.h
> create mode 100644 arch/kvx/include/asm/tlb.h
> create mode 100644 arch/kvx/include/asm/tlb_defs.h
> create mode 100644 arch/kvx/include/asm/tlbflush.h
> create mode 100644 arch/kvx/include/asm/traps.h
> create mode 100644 arch/kvx/include/asm/types.h
> create mode 100644 arch/kvx/include/asm/uaccess.h
> create mode 100644 arch/kvx/include/asm/unistd.h
> create mode 100644 arch/kvx/include/asm/vermagic.h
> create mode 100644 arch/kvx/include/asm/vmalloc.h
> create mode 100644 arch/kvx/include/uapi/asm/Kbuild
> create mode 100644 arch/kvx/include/uapi/asm/bitsperlong.h
> create mode 100644 arch/kvx/include/uapi/asm/byteorder.h
> create mode 100644 arch/kvx/include/uapi/asm/cachectl.h
> create mode 100644 arch/kvx/include/uapi/asm/ptrace.h
> create mode 100644 arch/kvx/include/uapi/asm/sigcontext.h
> create mode 100644 arch/kvx/include/uapi/asm/unistd.h
> create mode 100644 arch/kvx/kernel/Makefile
> create mode 100644 arch/kvx/kernel/asm-offsets.c
> create mode 100644 arch/kvx/kernel/break_hook.c
> create mode 100644 arch/kvx/kernel/common.c
> create mode 100644 arch/kvx/kernel/cpuinfo.c
> create mode 100644 arch/kvx/kernel/dame_handler.c
> create mode 100644 arch/kvx/kernel/debug.c
> create mode 100644 arch/kvx/kernel/entry.S
> create mode 100644 arch/kvx/kernel/ftrace.c
> create mode 100644 arch/kvx/kernel/head.S
> create mode 100644 arch/kvx/kernel/hw_breakpoint.c
> create mode 100644 arch/kvx/kernel/insns.c
> create mode 100644 arch/kvx/kernel/io.c
> create mode 100644 arch/kvx/kernel/irq.c
> create mode 100644 arch/kvx/kernel/jump_label.c
> create mode 100644 arch/kvx/kernel/kvx_ksyms.c
> create mode 100644 arch/kvx/kernel/l2_cache.c
> create mode 100644 arch/kvx/kernel/mcount.S
> create mode 100644 arch/kvx/kernel/module.c
> create mode 100644 arch/kvx/kernel/perf_event.c
> create mode 100644 arch/kvx/kernel/process.c
> create mode 100644 arch/kvx/kernel/prom.c
> create mode 100644 arch/kvx/kernel/ptrace.c
> create mode 100644 arch/kvx/kernel/reset.c
> create mode 100644 arch/kvx/kernel/return_address.c
> create mode 100644 arch/kvx/kernel/setup.c
> create mode 100644 arch/kvx/kernel/signal.c
> create mode 100644 arch/kvx/kernel/smp.c
> create mode 100644 arch/kvx/kernel/smpboot.c
> create mode 100644 arch/kvx/kernel/stacktrace.c
> create mode 100644 arch/kvx/kernel/sys_kvx.c
> create mode 100644 arch/kvx/kernel/syscall_table.c
> create mode 100644 arch/kvx/kernel/time.c
> create mode 100644 arch/kvx/kernel/traps.c
> create mode 100644 arch/kvx/kernel/vdso.c
> create mode 100644 arch/kvx/kernel/vmlinux.lds.S
> create mode 100644 arch/kvx/lib/Makefile
> create mode 100644 arch/kvx/lib/clear_page.S
> create mode 100644 arch/kvx/lib/copy_page.S
> create mode 100644 arch/kvx/lib/delay.c
> create mode 100644 arch/kvx/lib/memcpy.c
> create mode 100644 arch/kvx/lib/memset.S
> create mode 100644 arch/kvx/lib/strlen.S
> create mode 100644 arch/kvx/lib/usercopy.S
> create mode 100644 arch/kvx/mm/Makefile
> create mode 100644 arch/kvx/mm/cacheflush.c
> create mode 100644 arch/kvx/mm/dma-mapping.c
> create mode 100644 arch/kvx/mm/extable.c
> create mode 100644 arch/kvx/mm/fault.c
> create mode 100644 arch/kvx/mm/hugetlbpage.c
> create mode 100644 arch/kvx/mm/init.c
> create mode 100644 arch/kvx/mm/kernel_rwx.c
> create mode 100644 arch/kvx/mm/mmap.c
> create mode 100644 arch/kvx/mm/mmu.c
> create mode 100644 arch/kvx/mm/mmu_stats.c
> create mode 100644 arch/kvx/mm/tlb.c
> create mode 100644 arch/kvx/platform/Makefile
> create mode 100644 arch/kvx/platform/ipi.c
> create mode 100644 arch/kvx/platform/pwr_ctrl.c
> create mode 100644 drivers/irqchip/irq-kvx-apic-gic.c
> create mode 100644 drivers/irqchip/irq-kvx-apic-mailbox.c
> create mode 100644 drivers/irqchip/irq-kvx-core-intc.c
> create mode 100644 drivers/irqchip/irq-kvx-itgen.c
> create mode 100644 drivers/power/reset/kvx-scall-poweroff.c
> create mode 100644 include/linux/irqchip/irq-kvx-apic-gic.h
> create mode 100644 include/linux/irqchip/irq-kvx-apic-mailbox.h
> create mode 100644 include/linux/irqchip/irq-kvx-itgen.h
> create mode 100644 scripts/gdb/arch/Makefile
> create mode 100644 scripts/gdb/arch/__init__.py
> create mode 100644 scripts/gdb/arch/kvx/Makefile
> create mode 100644 scripts/gdb/arch/kvx/__init__.py
> create mode 100644 scripts/gdb/arch/kvx/constants.py.in
> create mode 100644 scripts/gdb/arch/kvx/mmu.py
> create mode 100644 scripts/gdb/arch/kvx/page_table_walk.py
>
> --
> 2.37.2
>
>
>
>
>
--
Thanks,
JeffXie
^ permalink raw reply [flat|nested] 13+ messages in thread