This will allow sessions with more than CORESIGHT_TRACE_IDS_MAX ETMs
as long as there are fewer than that many ETMs connected to each sink.
Each sink owns its own trace ID map, and any Perf session connecting to
that sink will allocate from it, even if the sink is currently in use by
other users. This is similar to the existing behavior where the dynamic
trace IDs are constant as long as there is any concurrent Perf session
active. It's not completely optimal because slightly more IDs will be
used than necessary, but the optimal solution involves tracking the PIDs
of each session and allocating ID maps based on the session owner. This
is difficult to do with the combination of per-thread and per-cpu modes
and some scheduling issues. The complexity of this isn't likely to worth
it because even with multiple users they'd just see a difference in the
ordering of ID allocations rather than hitting any limits (unless the
hardware does have too many ETMs connected to one sink).
Per-thread mode works but only until there are any overlapping IDs, at
which point Perf will error out. Both per-thread mode and sysfs mode are
left to future changes, but both can be added on top of this initial
implementation and only sysfs mode requires further driver changes.
The HW_ID version field hasn't been bumped in order to not break Perf
which already has an error condition for other values of that field.
Instead a new minor version has been added which signifies that there
are new fields but the old fields are backwards compatible.
James Clark (17):
perf cs-etm: Print error for new PERF_RECORD_AUX_OUTPUT_HW_ID versions
perf auxtrace: Allow number of queues to be specified
perf: cs-etm: Create decoders after both AUX and HW_ID search passes
perf: cs-etm: Allocate queues for all CPUs
perf: cs-etm: Move traceid_list to each queue
perf: cs-etm: Create decoders based on the trace ID mappings
perf: cs-etm: Support version 0.1 of HW_ID packets
coresight: Remove unused stubs
coresight: Clarify comments around the PID of the sink owner
coresight: Move struct coresight_trace_id_map to common header
coresight: Expose map argument in trace ID API
coresight: Make CPU id map a property of a trace ID map
coresight: Pass trace ID map into source enable
coresight: Use per-sink trace ID maps for Perf sessions
coresight: Remove pending trace ID release mechanism
coresight: Re-emit trace IDs when the sink changes in per-thread mode
coresight: Emit HW_IDs for all ETMs that are using the sink
drivers/hwtracing/coresight/coresight-core.c | 10 +
drivers/hwtracing/coresight/coresight-dummy.c | 3 +-
.../hwtracing/coresight/coresight-etm-perf.c | 82 ++-
.../hwtracing/coresight/coresight-etm-perf.h | 20 +-
.../coresight/coresight-etm3x-core.c | 14 +-
.../coresight/coresight-etm4x-core.c | 14 +-
drivers/hwtracing/coresight/coresight-stm.c | 3 +-
drivers/hwtracing/coresight/coresight-sysfs.c | 3 +-
.../hwtracing/coresight/coresight-tmc-etr.c | 5 +-
drivers/hwtracing/coresight/coresight-tmc.h | 5 +-
drivers/hwtracing/coresight/coresight-tpdm.c | 3 +-
.../hwtracing/coresight/coresight-trace-id.c | 107 +--
.../hwtracing/coresight/coresight-trace-id.h | 57 +-
include/linux/coresight-pmu.h | 17 +-
include/linux/coresight.h | 20 +-
tools/include/linux/coresight-pmu.h | 17 +-
tools/perf/util/auxtrace.c | 9 +-
tools/perf/util/auxtrace.h | 1 +
.../perf/util/cs-etm-decoder/cs-etm-decoder.c | 28 +-
tools/perf/util/cs-etm.c | 617 ++++++++++++------
tools/perf/util/cs-etm.h | 2 +-
21 files changed, 633 insertions(+), 404 deletions(-)
--
2.34.1
This detects and enables the scatter gather capability (SG) on ACPI based
Soc-400 TMC ETR devices via a new property called 'arm-armhc97c-sg-enable'.
The updated ACPI spec can be found below, which contains this new property.
https://developer.arm.com/documentation/den0067/latest/
This preserves current handling for the property 'arm,scatter-gather' both
on ACPI and DT based platforms i.e the presence of the property is checked
instead of the value.
Cc: Suzuki K Poulose <suzuki.poulose(a)arm.com>
Cc: Mike Leach <mike.leach(a)linaro.org>
Cc: James Clark <james.clark(a)arm.com>
Cc: Alexander Shishkin <alexander.shishkin(a)linux.intel.com>
Cc: coresight(a)lists.linaro.org
Cc: linux-arm-kernel(a)lists.infradead.org
Cc: linux-kernel(a)vger.kernel.org
Signed-off-by: Anshuman Khandual <anshuman.khandual(a)arm.com>
---
.../hwtracing/coresight/coresight-tmc-core.c | 28 ++++++++++++++++++-
1 file changed, 27 insertions(+), 1 deletion(-)
diff --git a/drivers/hwtracing/coresight/coresight-tmc-core.c b/drivers/hwtracing/coresight/coresight-tmc-core.c
index 72005b0c633e..2b277499b59a 100644
--- a/drivers/hwtracing/coresight/coresight-tmc-core.c
+++ b/drivers/hwtracing/coresight/coresight-tmc-core.c
@@ -4,6 +4,7 @@
* Description: CoreSight Trace Memory Controller driver
*/
+#include <linux/acpi.h>
#include <linux/kernel.h>
#include <linux/init.h>
#include <linux/types.h>
@@ -360,7 +361,32 @@ static const struct attribute_group *coresight_etr_groups[] = {
static inline bool tmc_etr_can_use_sg(struct device *dev)
{
- return fwnode_property_present(dev->fwnode, "arm,scatter-gather");
+ int ret;
+ u8 val_u8;
+
+ /*
+ * Presence of the property 'arm,scatter-gather' is checked
+ * on the platform for the feature support, rather than its
+ * value.
+ */
+ if (is_of_node(dev->fwnode)) {
+ return fwnode_property_present(dev->fwnode, "arm,scatter-gather");
+ } else if (is_acpi_device_node(dev->fwnode)) {
+ /*
+ * TMC_DEVID_NOSCAT test in tmc_etr_setup_caps(), has already ensured
+ * this property is only checked for Coresight SoC 400 TMC configured
+ * as ETR.
+ */
+ ret = fwnode_property_read_u8(dev->fwnode, "arm-armhc97c-sg-enable", &val_u8);
+ if (!ret)
+ return !!val_u8;
+
+ if (fwnode_property_present(dev->fwnode, "arm,scatter-gather")) {
+ pr_warn_once("Deprecated ACPI property - arm,scatter-gather\n");
+ return true;
+ }
+ }
+ return false;
}
static inline bool tmc_etr_has_non_secure_access(struct tmc_drvdata *drvdata)
--
2.25.1
When the config validation functions are warning about ETMv3, they do it
based on "not ETMv4". If the drivers aren't all loaded or the hardware
doesn't support Coresight it will appear as "not ETMv4" and then Perf
will print the error message "... not supported in ETMv3 ..." which is
wrong and confusing.
cs_etm_is_etmv4() is also misnamed because it also returns true for
ETE because ETE has a superset of the ETMv4 metadata files. Although
this was always done in the correct order so it wasn't a bug.
Improve all this by making a single get version function which also
handles not present as a separate case. Change the ETMv3 error message
to only print when ETMv3 is detected, and add a new error message for
the not present case.
Signed-off-by: James Clark <james.clark(a)arm.com>
---
tools/perf/arch/arm/util/cs-etm.c | 64 +++++++++++++++++++++++--------
1 file changed, 48 insertions(+), 16 deletions(-)
diff --git a/tools/perf/arch/arm/util/cs-etm.c b/tools/perf/arch/arm/util/cs-etm.c
index 07be32d99805..2763c6758b91 100644
--- a/tools/perf/arch/arm/util/cs-etm.c
+++ b/tools/perf/arch/arm/util/cs-etm.c
@@ -66,9 +66,25 @@ static const char * const metadata_ete_ro[] = {
[CS_ETE_TS_SOURCE] = "ts_source",
};
-static bool cs_etm_is_etmv4(struct auxtrace_record *itr, int cpu);
+enum cs_etm_version { CS_NOT_PRESENT, CS_ETMV3, CS_ETMV4, CS_ETE };
+
+static bool cs_etm_pmu_file_present(struct auxtrace_record *itr, int cpu,
+ const char *file);
static bool cs_etm_is_ete(struct auxtrace_record *itr, int cpu);
+static enum cs_etm_version cs_etm_get_version(struct auxtrace_record *itr,
+ int cpu)
+{
+ if (cs_etm_is_ete(itr, cpu))
+ return CS_ETE;
+ else if (cs_etm_pmu_file_present(itr, cpu, metadata_etmv4_ro[CS_ETMV4_TRCIDR0]))
+ return CS_ETMV4;
+ else if (cs_etm_pmu_file_present(itr, cpu, metadata_etmv3_ro[CS_ETM_ETMCCER]))
+ return CS_ETMV3;
+
+ return CS_NOT_PRESENT;
+}
+
static int cs_etm_validate_context_id(struct auxtrace_record *itr,
struct evsel *evsel, int cpu)
{
@@ -87,7 +103,7 @@ static int cs_etm_validate_context_id(struct auxtrace_record *itr,
return 0;
/* Not supported in etmv3 */
- if (!cs_etm_is_etmv4(itr, cpu)) {
+ if (cs_etm_get_version(itr, cpu) == CS_ETMV3) {
pr_err("%s: contextid not supported in ETMv3, disable with %s/contextid=0/\n",
CORESIGHT_ETM_PMU_NAME, CORESIGHT_ETM_PMU_NAME);
return -EINVAL;
@@ -154,7 +170,7 @@ static int cs_etm_validate_timestamp(struct auxtrace_record *itr,
perf_pmu__format_bits(cs_etm_pmu, "timestamp")))
return 0;
- if (!cs_etm_is_etmv4(itr, cpu)) {
+ if (cs_etm_get_version(itr, cpu) == CS_ETMV3) {
pr_err("%s: timestamp not supported in ETMv3, disable with %s/timestamp=0/\n",
CORESIGHT_ETM_PMU_NAME, CORESIGHT_ETM_PMU_NAME);
return -EINVAL;
@@ -218,6 +234,11 @@ static int cs_etm_validate_config(struct auxtrace_record *itr,
}
perf_cpu_map__for_each_cpu_skip_any(cpu, idx, intersect_cpus) {
+ if (cs_etm_get_version(itr, cpu.cpu) == CS_NOT_PRESENT) {
+ pr_err("%s: Not found on CPU %d. Check hardware and firmware support and that all Coresight drivers are loaded\n",
+ CORESIGHT_ETM_PMU_NAME, cpu.cpu);
+ return -EINVAL;
+ }
err = cs_etm_validate_context_id(itr, evsel, cpu.cpu);
if (err)
break;
@@ -548,13 +569,13 @@ cs_etm_info_priv_size(struct auxtrace_record *itr __maybe_unused,
/* Event can be "any" CPU so count all online CPUs. */
intersect_cpus = perf_cpu_map__new_online_cpus();
}
+ /* Count number of each type of ETM. Don't count if that CPU has CS_NOT_PRESENT. */
perf_cpu_map__for_each_cpu_skip_any(cpu, idx, intersect_cpus) {
- if (cs_etm_is_ete(itr, cpu.cpu))
- ete++;
- else if (cs_etm_is_etmv4(itr, cpu.cpu))
- etmv4++;
- else
- etmv3++;
+ enum cs_etm_version v = cs_etm_get_version(itr, cpu.cpu);
+
+ ete += v == CS_ETE;
+ etmv4 += v == CS_ETMV4;
+ etmv3 += v == CS_ETMV3;
}
perf_cpu_map__put(intersect_cpus);
@@ -564,7 +585,8 @@ cs_etm_info_priv_size(struct auxtrace_record *itr __maybe_unused,
(etmv3 * CS_ETMV3_PRIV_SIZE));
}
-static bool cs_etm_is_etmv4(struct auxtrace_record *itr, int cpu)
+static bool cs_etm_pmu_file_present(struct auxtrace_record *itr, int cpu,
+ const char *file)
{
bool ret = false;
char path[PATH_MAX];
@@ -574,9 +596,7 @@ static bool cs_etm_is_etmv4(struct auxtrace_record *itr, int cpu)
container_of(itr, struct cs_etm_recording, itr);
struct perf_pmu *cs_etm_pmu = ptr->cs_etm_pmu;
- /* Take any of the RO files for ETMv4 and see if it present */
- snprintf(path, PATH_MAX, "cpu%d/%s",
- cpu, metadata_etmv4_ro[CS_ETMV4_TRCIDR0]);
+ snprintf(path, PATH_MAX, "cpu%d/%s", cpu, file);
scan = perf_pmu__scan_file(cs_etm_pmu, path, "%x", &val);
/* The file was read successfully, we have a winner */
@@ -735,21 +755,26 @@ static void cs_etm_get_metadata(int cpu, u32 *offset,
struct perf_pmu *cs_etm_pmu = ptr->cs_etm_pmu;
/* first see what kind of tracer this cpu is affined to */
- if (cs_etm_is_ete(itr, cpu)) {
+ switch (cs_etm_get_version(itr, cpu)) {
+ case CS_ETE:
magic = __perf_cs_ete_magic;
cs_etm_save_ete_header(&info->priv[*offset], itr, cpu);
/* How much space was used */
increment = CS_ETE_PRIV_MAX;
nr_trc_params = CS_ETE_PRIV_MAX - CS_ETM_COMMON_BLK_MAX_V1;
- } else if (cs_etm_is_etmv4(itr, cpu)) {
+ break;
+
+ case CS_ETMV4:
magic = __perf_cs_etmv4_magic;
cs_etm_save_etmv4_header(&info->priv[*offset], itr, cpu);
/* How much space was used */
increment = CS_ETMV4_PRIV_MAX;
nr_trc_params = CS_ETMV4_PRIV_MAX - CS_ETMV4_TRCCONFIGR;
- } else {
+ break;
+
+ case CS_ETMV3:
magic = __perf_cs_etmv3_magic;
/* Get configuration register */
info->priv[*offset + CS_ETM_ETMCR] = cs_etm_get_config(itr);
@@ -767,6 +792,13 @@ static void cs_etm_get_metadata(int cpu, u32 *offset,
/* How much space was used */
increment = CS_ETM_PRIV_MAX;
nr_trc_params = CS_ETM_PRIV_MAX - CS_ETM_ETMCR;
+ break;
+
+ default:
+ case CS_NOT_PRESENT:
+ /* Unreachable, CPUs already validated in cs_etm_validate_config() */
+ assert(true);
+ return;
}
/* Build generic header portion */
--
2.34.1
This patch series is rebased on v6.8-rc4 from coresisght tree,[1],
since latest changes are dependent on coresight_get/set_mode APIs.
Changelog from v6:
* Added special device files for reading crashdata, so that
read_prevboot mode flag is removed.
* Added new sysfs TMC device attribute, stop_on_flush.
Stop on flush trigger event is disabled by default.
User need to explicitly enable this from sysfs for panic stop
to work.
* Address parameter for panicstop ETM configuration is
chosen as kernel "panic" address by default.
* Added missing tmc_wait_for_tmcready during panic handling
* Few other misc code rearrangements.
Changelog from v5:
* Fixed issues reported by CONFIG_DEBUG_ATOMIC_SLEEP
* Fixed a memory leak while reading data from /dev/tmc_etrx in
READ_PREVBOOT mode
* Tested reading trace data from crashdump kernel
Changelog from v4:
* Device tree binding
- Description is made more explicit on the usage of reserved memory
region
- Mismatch in memory region names in dts binding and driver fixed
- Removed "mem" suffix from the memory region names
* Rename "struct tmc_register_snapshot" -> "struct tmc_crash_metadata",
since it contains more than register snapshot.
Related variables are named accordingly.
* Rename struct tmc_drvdata members
resrv_buf -> crash_tbuf
metadata -> crash_mdata
* Size field in metadata refers to RSZ register and hence indicates the
size in 32 bit words. ETR metadata follows this convention, the same
has been extended to ETF metadata as well.
* Added crc32 for more robust metadata and tracedata validation.
* Added/modified dev_dbg messages during metadata validation
* Fixed a typo in patch 5 commit description
Changelog from v3:
* Converted the Coresight ETM driver change to a named configuration.
RFC tag has been removed with this change.
* Fixed yaml issues reported by "make dt_binding_check"
* Added names for reserved memory regions 0 and 1
* Added prevalidation checks for metadata processing
* Fixed a regression introduced in RFC v3
- TMC Status register was getting saved wrongly
* Reverted memremap attribute changes from _WB to _WC to match
with the dma map attributes
* Introduced reserved buffer mode specific .sync op.
This fixes a possible crash when reserved buffer mode was used in
normal trace capture, due to unwanted dma maintenance operations.
v6 is posted here:
https://www.spinics.net/lists/kernel/msg5055812.html
Using Coresight for Kernel panic and Watchdog reset
===================================================
This patch series is about extending Linux coresight driver support to
address kernel panic and watchdog reset scenarios. This would help
coresight users to debug kernel panic and watchdog reset using
coresight trace data.
Coresight trace capture: Kernel panic
-------------------------------------
From the coresight driver point of view, addressing the kernel panic
situation has four main requirements.
a. Support for allocation of trace buffer pages from reserved memory area.
Platform can advertise this using a new device tree property added to
relevant coresight nodes.
b. Support for stopping coresight blocks at the time of panic
c. Saving required metadata in the specified format
d. Support for reading trace data captured at the time of panic
Allocation of trace buffer pages from reserved RAM
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
A new optional device tree property "memory-region" is added to the
ETR/ETF device nodes, that would give the base address and size of trace
buffer.
Static allocation of trace buffers would ensure that both IOMMU enabled
and disabled cases are handled. Also, platforms that support persistent
RAM will allow users to read trace data in the subsequent boot without
booting the crashdump kernel.
Note:
For ETR sink devices, this reserved region will be used for both trace
capture and trace data retrieval.
For ETF sink devices, internal SRAM would be used for trace capture,
and they would be synced to reserved region for retrieval.
Note: Patches 1 & 2 adds support for this.
Disabling coresight blocks at the time of panic
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
In order to avoid the situation of losing relevant trace data after a
kernel panic, it would be desirable to stop the coresight blocks at the
time of panic.
This can be achieved by configuring the comparator, CTI and sink
devices as below,
Comparator(triggers on kernel panic) --->External out --->CTI --
|
ETR/ETF stop <------External In <--------------
Note:
* Patch 6 provides the necessary ETR configuration.
* Patch 7 provides the necessary ETM configuration.
Saving metadata at the time of kernel panic
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
Coresight metadata involves all additional data that are required for a
successful trace decode in addition to the trace data. This involves
ETR/ETF, ETE register snapshot etc.
A new optional device property "memory-region" is added to
the ETR/ETF/ETE device nodes for this.
Note: Patches 3 & 4 adds support for this.
Reading trace data captured at the time of panic
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
Trace data captured at the time of panic, can be read from rebooted kernel
or from crashdump kernel using the below mentioned interface.
Note: Patch 5 adds support for this.
Steps for reading trace data captured in previous boot
++++++++++++++++++++++++++++++++++++++++++++++++++++++
1. cd /sys/bus/coresight/devices/tmc_etrXX/
2. Dump trace buffer crashdata to a file,
#dd if=/dev/crash_tmc_etrXX of=~/cstrace.bin
General flow of trace capture and decode incase of kernel panic
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
1. Enable source and sink on all the cores using the sysfs interface.
ETR sink will have trace buffers allocated from reserved memory,
by selecting "resrv" buffer mode from sysfs.
2. Run relevant tests.
3. On a kernel panic, all coresight blocks are disabled, necessary
metadata is synced by kernel panic handler.
System would eventually reboot or boot a crashdump kernel.
4. For platforms that supports crashdump kernel, raw trace data can be
dumped using the coresight sysfs interface from the crashdump kernel
itself. Persistent RAM is not a requirement in this case.
5. For platforms that supports persistent RAM, trace data can be dumped
using the coresight sysfs interface in the subsequent Linux boot.
Crashdump kernel is not a requirement in this case. Persistent RAM
ensures that trace data is intact across reboot.
Coresight trace capture: Watchdog reset
---------------------------------------
The main difference between addressing the watchdog reset and kernel panic
case are below,
a. Saving coresight metadata need to be taken care by the
SCP(system control processor) firmware in the specified format,
instead of kernel.
b. Reserved memory region given by firmware for trace buffer and metadata
has to be in persistent RAM.
Note: This is a requirement for watchdog reset case but optional
in kernel panic case.
Watchdog reset can be supported only on platforms that meet the above
two requirements.
Testing Kernel panic on Linux 6.8
---------------------------------
1. Enable the preloaded ETM configuration
#echo 1 > /sys/kernel/config/cs-syscfg/configurations/panicstop/enable
2. Configure CTI using sysfs interface
#./cti_setup.sh
#cat cti_setup.sh
cd /sys/bus/coresight/devices/
ap_cti_config () {
#ETM trig out[0] trigger to Channel 0
echo 0 4 > channels/trigin_attach
}
etf_cti_config () {
#ETF Flush in trigger from Channel 0
echo 0 1 > channels/trigout_attach
echo 1 > channels/trig_filter_enable
}
etr_cti_config () {
#ETR Flush in from Channel 0
echo 0 1 > channels/trigout_attach
echo 1 > channels/trig_filter_enable
}
ctidevs=`find . -name "cti*"`
for i in $ctidevs
do
cd $i
connection=`find . -name "ete*"`
if [ ! -z "$connection" ]
then
echo "AP CTI config for $i"
ap_cti_config
fi
connection=`find . -name "tmc_etf*"`
if [ ! -z "$connection" ]
then
echo "ETF CTI config for $i"
etf_cti_config
fi
connection=`find . -name "tmc_etr*"`
if [ ! -z "$connection" ]
then
echo "ETR CTI config for $i"
etr_cti_config
fi
cd ..
done
Note: CTI connections are SOC specific and hence the above script is
added just for reference.
3. Choose reserved buffer mode for ETR buffer
#echo "resrv" > /sys/bus/coresight/devices/tmc_etr0/buf_mode_preferred
4. Enable stop on flush trigger configuration
#echo 1 > /sys/bus/coresight/devices/tmc_etr0/stop_on_flush
4. Start Coresight tracing on cores 1 and 2 using sysfs interface
5. Run some application on core 1
#taskset -c 1 dd if=/dev/urandom of=/dev/null &
6. Invoke kernel panic on core 2
#echo 1 > /proc/sys/kernel/panic
#taskset -c 2 echo c > /proc/sysrq-trigger
7. From rebooted kernel or crashdump kernel, read crashdata
Note: For crashdump kernel option, please make sure "crash_kexec_post_notifiers" is
added to the kernel bootargs.
#dd if=/dev/crash_tmc_etr0 of=/trace/cstrace.bin
8. Run opencsd decoder tools/scripts to generate the instruction trace.
Sample Core 1 instruction trace dump:
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
A etm4_enable_hw: ffff800008ae1dd4
CONTEXT EL2 etm4_enable_hw: ffff800008ae1dd4
I etm4_enable_hw: ffff800008ae1dd4:
d503201f nop
I etm4_enable_hw: ffff800008ae1dd8:
d503201f nop
I etm4_enable_hw: ffff800008ae1ddc:
d503201f nop
I etm4_enable_hw: ffff800008ae1de0:
d503201f nop
I etm4_enable_hw: ffff800008ae1de4:
d503201f nop
I etm4_enable_hw: ffff800008ae1de8:
d503233f paciasp
I etm4_enable_hw: ffff800008ae1dec:
a9be7bfd stp x29, x30, [sp, #-32]!
I etm4_enable_hw: ffff800008ae1df0:
910003fd mov x29, sp
I etm4_enable_hw: ffff800008ae1df4:
a90153f3 stp x19, x20, [sp, #16]
I etm4_enable_hw: ffff800008ae1df8:
2a0003f4 mov w20, w0
I etm4_enable_hw: ffff800008ae1dfc:
900085b3 adrp x19, ffff800009b95000 <reserved_mem+0xc48>
I etm4_enable_hw: ffff800008ae1e00:
910f4273 add x19, x19, #0x3d0
I etm4_enable_hw: ffff800008ae1e04:
f8747a60 ldr x0, [x19, x20, lsl #3]
E etm4_enable_hw: ffff800008ae1e08:
b4000140 cbz x0, ffff800008ae1e30 <etm4_starting_cpu+0x50>
I 149.039572921 etm4_enable_hw: ffff800008ae1e30:
a94153f3 ldp x19, x20, [sp, #16]
I 149.039572921 etm4_enable_hw: ffff800008ae1e34:
52800000 mov w0, #0x0 // #0
I 149.039572921 etm4_enable_hw: ffff800008ae1e38:
a8c27bfd ldp x29, x30, [sp], #32
..snip
149.052324811 chacha_block_generic: ffff800008642d80:
9100a3e0 add x0,
I 149.052324811 chacha_block_generic: ffff800008642d84:
b86178a2 ldr w2, [x5, x1, lsl #2]
I 149.052324811 chacha_block_generic: ffff800008642d88:
8b010803 add x3, x0, x1, lsl #2
I 149.052324811 chacha_block_generic: ffff800008642d8c:
b85fc063 ldur w3, [x3, #-4]
I 149.052324811 chacha_block_generic: ffff800008642d90:
0b030042 add w2, w2, w3
I 149.052324811 chacha_block_generic: ffff800008642d94:
b8217882 str w2, [x4, x1, lsl #2]
I 149.052324811 chacha_block_generic: ffff800008642d98:
91000421 add x1, x1, #0x1
I 149.052324811 chacha_block_generic: ffff800008642d9c:
f100443f cmp x1, #0x11
Sample Core 2 instruction trace dump(kernel panic triggered core):
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
A etm4_enable_hw: ffff800008ae1dd4
CONTEXT EL2 etm4_enable_hw: ffff800008ae1dd4
I etm4_enable_hw: ffff800008ae1dd4:
d503201f nop
I etm4_enable_hw: ffff800008ae1dd8:
d503201f nop
I etm4_enable_hw: ffff800008ae1ddc:
d503201f nop
I etm4_enable_hw: ffff800008ae1de0:
d503201f nop
I etm4_enable_hw: ffff800008ae1de4:
d503201f nop
I etm4_enable_hw: ffff800008ae1de8:
d503233f paciasp
I etm4_enable_hw: ffff800008ae1dec:
a9be7bfd stp x29, x30, [sp, #-32]!
I etm4_enable_hw: ffff800008ae1df0:
910003fd mov x29, sp
I etm4_enable_hw: ffff800008ae1df4:
a90153f3 stp x19, x20, [sp, #16]
I etm4_enable_hw: ffff800008ae1df8:
2a0003f4 mov w20, w0
I etm4_enable_hw: ffff800008ae1dfc:
900085b3 adrp x19, ffff800009b95000 <reserved_mem+0xc48>
I etm4_enable_hw: ffff800008ae1e00:
910f4273 add x19, x19, #0x3d0
I etm4_enable_hw: ffff800008ae1e04:
f8747a60 ldr x0, [x19, x20, lsl #3]
E etm4_enable_hw: ffff800008ae1e08:
b4000140 cbz x0, ffff800008ae1e30 <etm4_starting_cpu+0x50>
I 149.046243445 etm4_enable_hw: ffff800008ae1e30:
a94153f3 ldp x19, x20, [sp, #16]
I 149.046243445 etm4_enable_hw: ffff800008ae1e34:
52800000 mov w0, #0x0 // #0
I 149.046243445 etm4_enable_hw: ffff800008ae1e38:
a8c27bfd ldp x29, x30, [sp], #32
I 149.046243445 etm4_enable_hw: ffff800008ae1e3c:
d50323bf autiasp
E 149.046243445 etm4_enable_hw: ffff800008ae1e40:
d65f03c0 ret
A ete_sysreg_write: ffff800008adfa18
..snip
I 149.05422547 panic: ffff800008096300:
a90363f7 stp x23, x24, [sp, #48]
I 149.05422547 panic: ffff800008096304:
6b00003f cmp w1, w0
I 149.05422547 panic: ffff800008096308:
3a411804 ccmn w0, #0x1, #0x4, ne // ne = any
N 149.05422547 panic: ffff80000809630c:
540001e0 b.eq ffff800008096348 <panic+0xe0> // b.none
I 149.05422547 panic: ffff800008096310:
f90023f9 str x25, [sp, #64]
E 149.05422547 panic: ffff800008096314:
97fe44ef bl ffff8000080276d0 <panic_smp_self_stop>
A panic: ffff80000809634c
I 149.05422547 panic: ffff80000809634c:
910102d5 add x21, x22, #0x40
I 149.05422547 panic: ffff800008096350:
52800020 mov w0, #0x1 // #1
E 149.05422547 panic: ffff800008096354:
94166b8b bl ffff800008631180 <bust_spinlocks>
N 149.054225518 bust_spinlocks: ffff800008631180:
340000c0 cbz w0, ffff800008631198 <bust_spinlocks+0x18>
I 149.054225518 bust_spinlocks: ffff800008631184:
f000a321 adrp x1, ffff800009a98000 <pbufs.0+0xbb8>
I 149.054225518 bust_spinlocks: ffff800008631188:
b9405c20 ldr w0, [x1, #92]
I 149.054225518 bust_spinlocks: ffff80000863118c:
11000400 add w0, w0, #0x1
I 149.054225518 bust_spinlocks: ffff800008631190:
b9005c20 str w0, [x1, #92]
E 149.054225518 bust_spinlocks: ffff800008631194:
d65f03c0 ret
A panic: ffff800008096358
Future Improvements
-------------------
* Explore changing CTI sysfs script to system configuration manager profile
* Explore Perf based trace capture and decode
Links:
1. https://kernel.googlesource.com/pub/scm/linux/kernel/git/coresight/linux.gi…
Linu Cherian (7):
dt-bindings: arm: coresight-tmc: Add "memory-region" property
coresight: tmc-etr: Add support to use reserved trace memory
coresight: core: Add provision for panic callbacks
coresight: tmc: Enable panic sync handling
coresight: tmc: Add support for reading crash data
coresight: tmc: Stop trace capture on FlIn
coresight: config: Add preloaded configuration
.../bindings/arm/arm,coresight-tmc.yaml | 26 ++
drivers/hwtracing/coresight/Makefile | 2 +-
.../coresight/coresight-cfg-preload.c | 2 +
.../coresight/coresight-cfg-preload.h | 2 +
.../hwtracing/coresight/coresight-cfg-pstop.c | 83 +++++
drivers/hwtracing/coresight/coresight-core.c | 37 ++
.../coresight/coresight-etm4x-core.c | 1 +
.../hwtracing/coresight/coresight-tmc-core.c | 248 +++++++++++++-
.../hwtracing/coresight/coresight-tmc-etf.c | 161 ++++++++-
.../hwtracing/coresight/coresight-tmc-etr.c | 322 +++++++++++++++++-
drivers/hwtracing/coresight/coresight-tmc.h | 83 +++++
include/linux/coresight.h | 25 ++
12 files changed, 972 insertions(+), 20 deletions(-)
create mode 100644 drivers/hwtracing/coresight/coresight-cfg-pstop.c
--
2.34.1
Hi Uwe
On 23/04/2024 09:06, Uwe Kleine-König wrote:
> Hello,
>
> this series converts a few platform drivers below drivers/hwtracing/coresight
> that recently started to implement a .remove() callback to implement
> .remove_new() instead. See commit 5c5a7680e67b ("platform: Provide a remove
> callback that returns no value") for an extended explanation and the eventual
> goal.
>
> All conversations are trivial, because the driver's .remove() callbacks
> returned zero unconditionally already.
>
> There are no interdependencies between the five patches, so they could be picked
> up individually if need be. After the merge window leading to v6.10-rc1
> (assuming Linus has >= 10 fingers this cycle :-) I want to switch the prototype
> of struct platform_driver::remove to return void. So please either merge this
> series together with the commits introducing .remove() that currently sit in
> the next branch of
> git://git.kernel.org/pub/scm/linux/kernel/git/coresight/linux.git, or accept me
> sending them together with the patch changing the function's prototype for
> inclusion to Greg's driver-core tree.
Thanks for catching these. I will apply them to coresight next branch.
>
> Having said that, the patches adding platform driver support for these could be
> improved:
>
> - dev_get_drvdata() never returns NULL in these .remove() functions because
> .probe() called dev_set_drvdata(). For the usage of WARN_ON also see
> https://lwn.net/Articles/969923/. (That link's content is behind a paywall
> until May 2, the TLDR is: Don't use WARN_ON().) So the respective checks
> with the early return could better be dropped IMHO.
>
> - IS_ERR_OR_NULL(drvdata->pclk) is never true in .remove(). Also note that
> IS_ERR_OR_NULL is ugly and gives hardly ever the right condition to check
> for. Note further that clk == NULL isn't usually a problem, NULL is used as
> dummy clk returned by clk_get_optional() and all clock API functions handle
> that just fine. So if at all, better check only for IS_ERR(drvdata->pclk).
Thanks for the suggestions, I will let Anshuman address them.
Kind regards
Suzuki
>
> Best regards
> Uwe
>
> Uwe Kleine-König (5):
> coresight: catu: Convert to platform remove callback returning void
> coresight: debug: Convert to platform remove callback returning void
> coresight: stm: Convert to platform remove callback returning void
> coresight: tmc: Convert to platform remove callback returning void
> coresight: tpiu: Convert to platform remove callback returning void
>
> drivers/hwtracing/coresight/coresight-catu.c | 7 +++----
> drivers/hwtracing/coresight/coresight-cpu-debug.c | 7 +++----
> drivers/hwtracing/coresight/coresight-stm.c | 7 +++----
> drivers/hwtracing/coresight/coresight-tmc-core.c | 7 +++----
> drivers/hwtracing/coresight/coresight-tpiu.c | 7 +++----
> 5 files changed, 15 insertions(+), 20 deletions(-)
>
> base-commit: a59668a9397e7245b26e9be85d23f242ff757ae8