CoreSight ETMv4.4 introduced system instructions for accessing
the ETM. This also implies that they may not be on the amba bus.
Right now all the CoreSight components are accessed via memory
map. Also, we have some common routines in coresight generic
code driver (e.g, CS_LOCK, claim/disclaim), which assume the
mmio. In order to preserve the generic algorithms at a single
place and to allow dynamic switch for ETMs, this series introduces
an abstraction layer for accessing a coresight device. It is
designed such that the mmio access are fast tracked (i.e, without
an indirect function call).
This will also help us to get rid of the driver+attribute specific
sysfs show/store routines and replace them with a single routine
to access a given register offset (which can be embedded in the
dev_ext_attribute). This is not currently implemented in the series,
but can be achieved.
Further we switch the generic routines to work with the abstraction.
With this in place, we refactor the etm4x code a bit to allow for
supporting the system instructions with very little new code. The
changes also switch to using the system instructions by default
even when we may have an MMIO.
The series has been mildly tested on a model. I would really
appreciate any testing on real hardware.
Applies on coresight/next tree. The tree is also available here :
git://linux-arm.org/linux-skp.git etm-4.4/rfc
Suzuki K Poulose (14):
coresight: etm4x: Skip save/restore before device registration
coresight: Introduce device access abstraction
coresight: tpiu: Use coresight device access abstraction
coresight: etm4x: Free up argument of etm4_init_arch_data
coresight: Convert coresight_timeout to use access abstraction
coresight: Convert claim and lock operations to use access wrappers
coresight: etm4x: Always read the registers on the host CPU
coresight: etm4x: Convert all register accesses
coresight: etm4x: Add sysreg access helpers
coresight: etm4x: Define DEVARCH register fields
coresight: etm4x: Detect system register access support
coresight: etm4x: Refactor probing routine
coresight: etm4x: Add support for sysreg only devices
dts: bindings: coresight: ETMv4.4 system register access only units
.../devicetree/bindings/arm/coresight.txt | 6 +-
drivers/hwtracing/coresight/coresight-catu.c | 17 +-
.../hwtracing/coresight/coresight-cpu-debug.c | 26 +-
.../hwtracing/coresight/coresight-cti-sysfs.c | 4 +-
drivers/hwtracing/coresight/coresight-cti.c | 31 +-
drivers/hwtracing/coresight/coresight-etb10.c | 26 +-
.../coresight/coresight-etm3x-sysfs.c | 8 +-
drivers/hwtracing/coresight/coresight-etm3x.c | 45 +-
.../coresight/coresight-etm4x-sysfs.c | 32 +-
drivers/hwtracing/coresight/coresight-etm4x.c | 580 +++++++++++-------
drivers/hwtracing/coresight/coresight-etm4x.h | 403 +++++++++++-
.../hwtracing/coresight/coresight-funnel.c | 19 +-
drivers/hwtracing/coresight/coresight-priv.h | 9 +-
.../coresight/coresight-replicator.c | 28 +-
drivers/hwtracing/coresight/coresight-stm.c | 49 +-
.../hwtracing/coresight/coresight-tmc-etf.c | 36 +-
.../hwtracing/coresight/coresight-tmc-etr.c | 19 +-
drivers/hwtracing/coresight/coresight-tmc.c | 10 +-
drivers/hwtracing/coresight/coresight-tpiu.c | 32 +-
drivers/hwtracing/coresight/coresight.c | 130 +++-
include/linux/coresight.h | 189 +++++-
21 files changed, 1273 insertions(+), 426 deletions(-)
--
2.24.1
CoreSight ETM with system register access may not have a
memory mapped i/o access. Refactor the ETM specific probing
into a common routine to allow reusing the code for such ETMs.
Cc: Mathieu Poirier <[email protected]>
Cc: Mike Leach <[email protected]>
Signed-off-by: Suzuki K Poulose <[email protected]>
---
drivers/hwtracing/coresight/coresight-etm4x.c | 64 ++++++++++++-------
1 file changed, 41 insertions(+), 23 deletions(-)
diff --git a/drivers/hwtracing/coresight/coresight-etm4x.c b/drivers/hwtracing/coresight/coresight-etm4x.c
index 831206f7f306..e91af23ac419 100644
--- a/drivers/hwtracing/coresight/coresight-etm4x.c
+++ b/drivers/hwtracing/coresight/coresight-etm4x.c
@@ -1541,27 +1541,43 @@ static bool etm4_cpu_supports_sysreg(int cpu)
return sys_reg_support;
}
-static int etm4_probe(struct amba_device *adev, const struct amba_id *id)
+static int etm4_probe_common(struct device *dev, void __iomem *base)
{
int ret, cpu;
bool sys_reg = false;
- void __iomem *base;
- struct device *dev = &adev->dev;
struct coresight_platform_data *pdata = NULL;
struct etmv4_drvdata *drvdata;
- struct resource *res = &adev->res;
struct coresight_desc desc = { 0 };
+ cpu = coresight_get_cpu(dev);
+ if (cpu < 0)
+ return cpu;
+
cpu = coresight_get_cpu(dev);
if (cpu < 0 || !cpu_online(cpu))
return -EPROBE_DEFER;
sys_reg = etm4_cpu_supports_sysreg(cpu);
+ if (sys_reg) {
+ desc.access = (struct csdev_access){
+ .no_iomem = true,
+ .read = etm4x_sysreg_read,
+ .write = etm4x_sysreg_write,
+ };
+ } else if (base) {
+ desc.access.base = base;
+ } else {
+ dev_crit(dev, "etm4x: Unable to detect access\n");
+ return -ENODEV;
+ }
+
+
drvdata = devm_kzalloc(dev, sizeof(*drvdata), GFP_KERNEL);
if (!drvdata)
return -ENOMEM;
+ drvdata->base = base;
drvdata->cpu = cpu;
dev_set_drvdata(dev, drvdata);
@@ -1579,22 +1595,6 @@ static int etm4_probe(struct amba_device *adev, const struct amba_id *id)
if (fwnode_property_present(dev_fwnode(dev), "qcom,skip-power-up"))
drvdata->skip_power_up = true;
- if (sys_reg) {
- desc.access = (struct csdev_access){
- .no_iomem = true,
- .read = etm4x_sysreg_read,
- .write = etm4x_sysreg_write,
- };
- } else {
- /* Validity for the resource is already checked by the AMBA core */
- base = devm_ioremap_resource(dev, res);
- if (IS_ERR(base))
- return PTR_ERR(base);
-
- drvdata->base = base;
- desc.access.base = base;
- }
-
spin_lock_init(&drvdata->spinlock);
desc.name = devm_kasprintf(dev, GFP_KERNEL, "etm%d", drvdata->cpu);
@@ -1630,7 +1630,7 @@ static int etm4_probe(struct amba_device *adev, const struct amba_id *id)
ret = PTR_ERR(pdata);
goto err_arch_supported;
}
- adev->dev.platform_data = pdata;
+ dev->platform_data = pdata;
desc.type = CORESIGHT_DEV_TYPE_SOURCE;
desc.subtype.source_subtype = CORESIGHT_DEV_SUBTYPE_SOURCE_PROC;
@@ -1650,7 +1650,6 @@ static int etm4_probe(struct amba_device *adev, const struct amba_id *id)
goto err_arch_supported;
}
- pm_runtime_put(&adev->dev);
dev_info(&drvdata->csdev->dev, "CPU%d: ETM v%d.%d initialized\n",
drvdata->cpu, drvdata->arch >> 4, drvdata->arch & 0xf);
if (sys_reg)
@@ -1669,6 +1668,25 @@ static int etm4_probe(struct amba_device *adev, const struct amba_id *id)
return ret;
}
+static int etm4_probe_amba(struct amba_device *adev, const struct amba_id *id)
+{
+ void __iomem *base;
+ struct device *dev = &adev->dev;
+ struct resource *res = &adev->res;
+ int ret;
+
+ /* Validity for the resource is already checked by the AMBA core */
+ base = devm_ioremap_resource(dev, res);
+ if (IS_ERR(base))
+ return PTR_ERR(base);
+
+ ret = etm4_probe_common(dev, base);
+ if (!ret)
+ pm_runtime_put(&adev->dev);
+
+ return ret;
+}
+
static struct amba_cs_uci_id uci_id_etm4[] = {
{
/* ETMv4 UCI data */
@@ -1700,7 +1718,7 @@ static struct amba_driver etm4x_driver = {
.name = "coresight-etm4x",
.suppress_bind_attrs = true,
},
- .probe = etm4_probe,
+ .probe = etm4_probe_amba,
.id_table = etm4_ids,
};
builtin_amba_driver(etm4x_driver);
--
2.24.1
Check if the etm4x supports system register access and use
it instead of the memory mapped IO.
We need to detect that :
a) The CPU implements system register access to the Trace unit
AND
b) The trace unit is an ETMv4.x component.
Cc: Mathieu Poirier <[email protected]>
Cc: Mike Leach <[email protected]>
Signed-off-by: Suzuki K Poulose <[email protected]>
---
drivers/hwtracing/coresight/coresight-etm4x.c | 76 +++++++++++++++----
drivers/hwtracing/coresight/coresight-etm4x.h | 16 ++++
2 files changed, 78 insertions(+), 14 deletions(-)
diff --git a/drivers/hwtracing/coresight/coresight-etm4x.c b/drivers/hwtracing/coresight/coresight-etm4x.c
index 776a59f62710..831206f7f306 100644
--- a/drivers/hwtracing/coresight/coresight-etm4x.c
+++ b/drivers/hwtracing/coresight/coresight-etm4x.c
@@ -19,6 +19,7 @@
#include <linux/clk.h>
#include <linux/cpu.h>
#include <linux/cpu_pm.h>
+#include <linux/cpumask.h>
#include <linux/coresight.h>
#include <linux/coresight-pmu.h>
#include <linux/pm_wakeup.h>
@@ -1507,9 +1508,43 @@ static void etm4_pm_clear(void)
}
}
+static inline bool trace_unit_is_etmv4(u32 devarch)
+{
+ return (devarch & ETM_DEVARCH_ID_MASK) == ETM_DEVARCH_ETMv4x_ARCH;
+}
+
+static void etm4_check_sysreg_access(void *arg)
+{
+ bool *status = arg;
+ u32 devarch;
+
+ if (!arch_cpu_supports_sysreg_trace()) {
+ *status = false;
+ return;
+ }
+
+ devarch = read_etm4x_sysreg_const_offset(TRCDEVARCH);
+ if (!trace_unit_is_etmv4(devarch)) {
+ *status = false;
+ return;
+ }
+
+ *status = true;
+}
+
+static bool etm4_cpu_supports_sysreg(int cpu)
+{
+ bool sys_reg_support = false;
+
+ smp_call_function_single(cpu, etm4_check_sysreg_access, &sys_reg_support, 1);
+
+ return sys_reg_support;
+}
+
static int etm4_probe(struct amba_device *adev, const struct amba_id *id)
{
- int ret;
+ int ret, cpu;
+ bool sys_reg = false;
void __iomem *base;
struct device *dev = &adev->dev;
struct coresight_platform_data *pdata = NULL;
@@ -1517,10 +1552,17 @@ static int etm4_probe(struct amba_device *adev, const struct amba_id *id)
struct resource *res = &adev->res;
struct coresight_desc desc = { 0 };
+ cpu = coresight_get_cpu(dev);
+ if (cpu < 0 || !cpu_online(cpu))
+ return -EPROBE_DEFER;
+
+ sys_reg = etm4_cpu_supports_sysreg(cpu);
+
drvdata = devm_kzalloc(dev, sizeof(*drvdata), GFP_KERNEL);
if (!drvdata)
return -ENOMEM;
+ drvdata->cpu = cpu;
dev_set_drvdata(dev, drvdata);
if (pm_save_enable == PARAM_PM_SAVE_FIRMWARE)
@@ -1537,26 +1579,30 @@ static int etm4_probe(struct amba_device *adev, const struct amba_id *id)
if (fwnode_property_present(dev_fwnode(dev), "qcom,skip-power-up"))
drvdata->skip_power_up = true;
- /* Validity for the resource is already checked by the AMBA core */
- base = devm_ioremap_resource(dev, res);
- if (IS_ERR(base))
- return PTR_ERR(base);
-
- drvdata->base = base;
- desc.access.base = base;
+ if (sys_reg) {
+ desc.access = (struct csdev_access){
+ .no_iomem = true,
+ .read = etm4x_sysreg_read,
+ .write = etm4x_sysreg_write,
+ };
+ } else {
+ /* Validity for the resource is already checked by the AMBA core */
+ base = devm_ioremap_resource(dev, res);
+ if (IS_ERR(base))
+ return PTR_ERR(base);
+
+ drvdata->base = base;
+ desc.access.base = base;
+ }
spin_lock_init(&drvdata->spinlock);
- drvdata->cpu = coresight_get_cpu(dev);
- if (drvdata->cpu < 0)
- return drvdata->cpu;
-
desc.name = devm_kasprintf(dev, GFP_KERNEL, "etm%d", drvdata->cpu);
if (!desc.name)
return -ENOMEM;
cpus_read_lock();
- etmdrvdata[drvdata->cpu] = drvdata;
+ etmdrvdata[cpu] = drvdata;
if (smp_call_function_single(drvdata->cpu,
etm4_init_arch_data, &desc.access, 1))
@@ -1607,6 +1653,8 @@ static int etm4_probe(struct amba_device *adev, const struct amba_id *id)
pm_runtime_put(&adev->dev);
dev_info(&drvdata->csdev->dev, "CPU%d: ETM v%d.%d initialized\n",
drvdata->cpu, drvdata->arch >> 4, drvdata->arch & 0xf);
+ if (sys_reg)
+ dev_info(&drvdata->csdev->dev, "Using system register accesses\n");
if (boot_enable) {
coresight_enable(drvdata->csdev);
@@ -1616,7 +1664,7 @@ static int etm4_probe(struct amba_device *adev, const struct amba_id *id)
return 0;
err_arch_supported:
- etmdrvdata[drvdata->cpu] = NULL;
+ etmdrvdata[cpu] = NULL;
etm4_pm_clear();
return ret;
}
diff --git a/drivers/hwtracing/coresight/coresight-etm4x.h b/drivers/hwtracing/coresight/coresight-etm4x.h
index ab3d1c195387..86fdcbafc895 100644
--- a/drivers/hwtracing/coresight/coresight-etm4x.h
+++ b/drivers/hwtracing/coresight/coresight-etm4x.h
@@ -152,6 +152,13 @@
#define write_etm4x_sysreg_const_offset(val, offset) \
WRITE_ETM4x_REG(val, ETM4x_OFFSET_TO_REG(offset))
+static inline bool arch_cpu_supports_sysreg_trace(void)
+{
+ u64 dfr0 = read_sysreg_s(SYS_ID_AA64DFR0_EL1);
+
+ return ((dfr0 >> ID_AA64DFR0_TRACEVER_SHIFT) & 0xfUL) > 0;
+}
+
#elif defined(CONFIG_ARM)
#include <asm/hardware/cp14.h>
@@ -172,6 +179,15 @@
#define write_etm4x_sysreg_const_offset(val, offset) \
WRITE_ETM4x_REG(val, ETM4x_OFFSET_TO_REG(offset))
+#define ID_DFR0_CopTrc_SHIFT 12
+static inline bool arch_cpu_supports_sysreg_trace(void)
+{
+ u32 dfr0;
+
+ asm volatile("mrc p15, 0, %0, c0, c1, 2" : "=r" (dfr0));
+
+ return ((dfr0 >> ID_DFR0_CopTrc_SHIFT) & 0xfUL) > 0;
+}
#endif
#define CASE_READ(res, x) \
--
2.24.1
Convert all register accesses from etm4x driver to use a wrapper
to allow switching the access at runtime with little overhead.
co-developed by sed tool ;-), mostly equivalent to :
s/readl\(_relaxed\)\?(drvdata->base + \(.*\))/etm4x_\1_read32(csdev, \2)
s/writel\(_relaxed\)\?(\(.*\), drvdata->base + \(.*\))/etm4x_\1_write32(csdev, \2, \3)
We don't want to replace them with the csdev_access_* to
avoid a function call for every register access for system
register access.
Cc: Mathieu Poirier <[email protected]>
Cc: Mike Leach <[email protected]>
Signed-off-by: Suzuki K Poulose <[email protected]>
---
.../coresight/coresight-etm4x-sysfs.c | 9 +-
drivers/hwtracing/coresight/coresight-etm4x.c | 334 +++++++++---------
drivers/hwtracing/coresight/coresight-etm4x.h | 24 ++
3 files changed, 189 insertions(+), 178 deletions(-)
diff --git a/drivers/hwtracing/coresight/coresight-etm4x-sysfs.c b/drivers/hwtracing/coresight/coresight-etm4x-sysfs.c
index 90c75ba31a0c..fe40355f6a2c 100644
--- a/drivers/hwtracing/coresight/coresight-etm4x-sysfs.c
+++ b/drivers/hwtracing/coresight/coresight-etm4x-sysfs.c
@@ -2316,7 +2316,8 @@ static struct attribute *coresight_etmv4_attrs[] = {
};
struct etmv4_reg {
- void __iomem *addr;
+ struct coresight_device *csdev;
+ u32 offset;
u32 data;
};
@@ -2324,7 +2325,7 @@ static void do_smp_cross_read(void *data)
{
struct etmv4_reg *reg = data;
- reg->data = readl_relaxed(reg->addr);
+ reg->data = etm4x_relaxed_read32(®->csdev->access, reg->offset);
}
static u32 etmv4_cross_read(const struct device *dev, u32 offset)
@@ -2332,7 +2333,9 @@ static u32 etmv4_cross_read(const struct device *dev, u32 offset)
struct etmv4_drvdata *drvdata = dev_get_drvdata(dev);
struct etmv4_reg reg;
- reg.addr = drvdata->base + offset;
+ reg.offset = offset;
+ reg.csdev = drvdata->csdev;
+
/*
* smp cross call ensures the CPU will be powered up before
* accessing the ETMv4 trace core registers
diff --git a/drivers/hwtracing/coresight/coresight-etm4x.c b/drivers/hwtracing/coresight/coresight-etm4x.c
index ce32d4ebc8b9..b901c91d3ee4 100644
--- a/drivers/hwtracing/coresight/coresight-etm4x.c
+++ b/drivers/hwtracing/coresight/coresight-etm4x.c
@@ -57,18 +57,28 @@ static int etm4_set_event_filters(struct etmv4_drvdata *drvdata,
static enum cpuhp_state hp_online;
-static void etm4_os_unlock(struct etmv4_drvdata *drvdata)
+static void etm4_os_unlock_csa(struct etmv4_drvdata *drvdata, struct csdev_access *csa)
{
/* Writing 0 to TRCOSLAR unlocks the trace registers */
- writel_relaxed(0x0, drvdata->base + TRCOSLAR);
+ etm4x_relaxed_write32(csa, 0x0, TRCOSLAR);
drvdata->os_unlock = true;
isb();
}
+static void etm4_os_unlock(struct etmv4_drvdata *drvdata)
+{
+ if (!WARN_ON(!drvdata->csdev))
+ etm4_os_unlock_csa(drvdata, &drvdata->csdev->access);
+
+}
+
static void etm4_os_lock(struct etmv4_drvdata *drvdata)
{
+ if (WARN_ON(!drvdata->csdev))
+ return;
+
/* Writing 0x1 to TRCOSLAR locks the trace registers */
- writel_relaxed(0x1, drvdata->base + TRCOSLAR);
+ etm4x_relaxed_write32(&drvdata->csdev->access, 0x1, TRCOSLAR);
drvdata->os_unlock = false;
isb();
}
@@ -121,44 +131,38 @@ static int etm4_enable_hw(struct etmv4_drvdata *drvdata)
goto done;
/* Disable the trace unit before programming trace registers */
- writel_relaxed(0, drvdata->base + TRCPRGCTLR);
+ etm4x_relaxed_write32(csa, 0, TRCPRGCTLR);
/* wait for TRCSTATR.IDLE to go up */
if (coresight_timeout(&csdev->access, TRCSTATR, TRCSTATR_IDLE_BIT, 1))
dev_err(etm_dev,
"timeout while waiting for Idle Trace Status\n");
- writel_relaxed(config->pe_sel, drvdata->base + TRCPROCSELR);
- writel_relaxed(config->cfg, drvdata->base + TRCCONFIGR);
+ etm4x_relaxed_write32(csa, config->pe_sel, TRCPROCSELR);
+ etm4x_relaxed_write32(csa, config->cfg, TRCCONFIGR);
/* nothing specific implemented */
- writel_relaxed(0x0, drvdata->base + TRCAUXCTLR);
- writel_relaxed(config->eventctrl0, drvdata->base + TRCEVENTCTL0R);
- writel_relaxed(config->eventctrl1, drvdata->base + TRCEVENTCTL1R);
- writel_relaxed(config->stall_ctrl, drvdata->base + TRCSTALLCTLR);
- writel_relaxed(config->ts_ctrl, drvdata->base + TRCTSCTLR);
- writel_relaxed(config->syncfreq, drvdata->base + TRCSYNCPR);
- writel_relaxed(config->ccctlr, drvdata->base + TRCCCCTLR);
- writel_relaxed(config->bb_ctrl, drvdata->base + TRCBBCTLR);
- writel_relaxed(drvdata->trcid, drvdata->base + TRCTRACEIDR);
- writel_relaxed(config->vinst_ctrl, drvdata->base + TRCVICTLR);
- writel_relaxed(config->viiectlr, drvdata->base + TRCVIIECTLR);
- writel_relaxed(config->vissctlr,
- drvdata->base + TRCVISSCTLR);
- writel_relaxed(config->vipcssctlr,
- drvdata->base + TRCVIPCSSCTLR);
+ etm4x_relaxed_write32(csa, 0x0, TRCAUXCTLR);
+ etm4x_relaxed_write32(csa, config->eventctrl0, TRCEVENTCTL0R);
+ etm4x_relaxed_write32(csa, config->eventctrl1, TRCEVENTCTL1R);
+ etm4x_relaxed_write32(csa, config->stall_ctrl, TRCSTALLCTLR);
+ etm4x_relaxed_write32(csa, config->ts_ctrl, TRCTSCTLR);
+ etm4x_relaxed_write32(csa, config->syncfreq, TRCSYNCPR);
+ etm4x_relaxed_write32(csa, config->ccctlr, TRCCCCTLR);
+ etm4x_relaxed_write32(csa, config->bb_ctrl, TRCBBCTLR);
+ etm4x_relaxed_write32(csa, drvdata->trcid, TRCTRACEIDR);
+ etm4x_relaxed_write32(csa, config->vinst_ctrl, TRCVICTLR);
+ etm4x_relaxed_write32(csa, config->viiectlr, TRCVIIECTLR);
+ etm4x_relaxed_write32(csa, config->vissctlr, TRCVISSCTLR);
+ etm4x_relaxed_write32(csa, config->vipcssctlr, TRCVIPCSSCTLR);
for (i = 0; i < drvdata->nrseqstate - 1; i++)
- writel_relaxed(config->seq_ctrl[i],
- drvdata->base + TRCSEQEVRn(i));
- writel_relaxed(config->seq_rst, drvdata->base + TRCSEQRSTEVR);
- writel_relaxed(config->seq_state, drvdata->base + TRCSEQSTR);
- writel_relaxed(config->ext_inp, drvdata->base + TRCEXTINSELR);
+ etm4x_relaxed_write32(csa, config->seq_ctrl[i], TRCSEQEVRn(i));
+ etm4x_relaxed_write32(csa, config->seq_rst, TRCSEQRSTEVR);
+ etm4x_relaxed_write32(csa, config->seq_state, TRCSEQSTR);
+ etm4x_relaxed_write32(csa, config->ext_inp, TRCEXTINSELR);
for (i = 0; i < drvdata->nr_cntr; i++) {
- writel_relaxed(config->cntrldvr[i],
- drvdata->base + TRCCNTRLDVRn(i));
- writel_relaxed(config->cntr_ctrl[i],
- drvdata->base + TRCCNTCTLRn(i));
- writel_relaxed(config->cntr_val[i],
- drvdata->base + TRCCNTVRn(i));
+ etm4x_relaxed_write32(csa, config->cntrldvr[i], TRCCNTRLDVRn(i));
+ etm4x_relaxed_write32(csa, config->cntr_ctrl[i], TRCCNTCTLRn(i));
+ etm4x_relaxed_write32(csa, config->cntr_val[i], TRCCNTVRn(i));
}
/*
@@ -166,52 +170,45 @@ static int etm4_enable_hw(struct etmv4_drvdata *drvdata)
* such start at 2.
*/
for (i = 2; i < drvdata->nr_resource * 2; i++)
- writel_relaxed(config->res_ctrl[i],
- drvdata->base + TRCRSCTLRn(i));
+ etm4x_relaxed_write32(csa, config->res_ctrl[i], TRCRSCTLRn(i));
for (i = 0; i < drvdata->nr_ss_cmp; i++) {
/* always clear status bit on restart if using single-shot */
if (config->ss_ctrl[i] || config->ss_pe_cmp[i])
config->ss_status[i] &= ~BIT(31);
- writel_relaxed(config->ss_ctrl[i],
- drvdata->base + TRCSSCCRn(i));
- writel_relaxed(config->ss_status[i],
- drvdata->base + TRCSSCSRn(i));
- writel_relaxed(config->ss_pe_cmp[i],
- drvdata->base + TRCSSPCICRn(i));
+ etm4x_relaxed_write32(csa, config->ss_ctrl[i], TRCSSCCRn(i));
+ etm4x_relaxed_write32(csa, config->ss_status[i], TRCSSCSRn(i));
+ etm4x_relaxed_write32(csa, config->ss_pe_cmp[i], TRCSSPCICRn(i));
}
for (i = 0; i < drvdata->nr_addr_cmp; i++) {
- writeq_relaxed(config->addr_val[i],
- drvdata->base + TRCACVRn(i));
- writeq_relaxed(config->addr_acc[i],
- drvdata->base + TRCACATRn(i));
+ etm4x_relaxed_write64(csa, config->addr_val[i], TRCACVRn(i));
+ etm4x_relaxed_write64(csa, config->addr_acc[i], TRCACATRn(i));
}
for (i = 0; i < drvdata->numcidc; i++)
- writeq_relaxed(config->ctxid_pid[i],
- drvdata->base + TRCCIDCVRn(i));
- writel_relaxed(config->ctxid_mask0, drvdata->base + TRCCIDCCTLR0);
- writel_relaxed(config->ctxid_mask1, drvdata->base + TRCCIDCCTLR1);
+ etm4x_relaxed_write64(csa, config->ctxid_pid[i], TRCCIDCVRn(i));
+ etm4x_relaxed_write32(csa, config->ctxid_mask0, TRCCIDCCTLR0);
+ etm4x_relaxed_write32(csa, config->ctxid_mask1, TRCCIDCCTLR1);
for (i = 0; i < drvdata->numvmidc; i++)
- writeq_relaxed(config->vmid_val[i],
- drvdata->base + TRCVMIDCVRn(i));
- writel_relaxed(config->vmid_mask0, drvdata->base + TRCVMIDCCTLR0);
- writel_relaxed(config->vmid_mask1, drvdata->base + TRCVMIDCCTLR1);
+ etm4x_relaxed_write64(csa, config->vmid_val[i], TRCVMIDCVRn(i));
+ etm4x_relaxed_write32(csa, config->vmid_mask0, TRCVMIDCCTLR0);
+ etm4x_relaxed_write32(csa, config->vmid_mask1, TRCVMIDCCTLR1);
if (!drvdata->skip_power_up) {
+ u32 trcpdcr = etm4x_relaxed_read32(csa, TRCPDCR);
+
/*
* Request to keep the trace unit powered and also
* emulation of powerdown
*/
- writel_relaxed(readl_relaxed(drvdata->base + TRCPDCR) |
- TRCPDCR_PU, drvdata->base + TRCPDCR);
+ etm4x_relaxed_write32(csa, trcpdcr | TRCPDCR_PU, TRCPDCR);
}
/* Enable the trace unit */
- writel_relaxed(1, drvdata->base + TRCPRGCTLR);
+ etm4x_relaxed_write32(csa, 1, TRCPRGCTLR);
/* wait for TRCSTATR.IDLE to go back down to '0' */
- if (coresight_timeout(&csdev->access, TRCSTATR, TRCSTATR_IDLE_BIT, 0))
+ if (coresight_timeout(csa, TRCSTATR, TRCSTATR_IDLE_BIT, 0))
dev_err(etm_dev,
"timeout while waiting for Idle Trace Status\n");
@@ -477,18 +474,19 @@ static void etm4_disable_hw(void *info)
struct etmv4_config *config = &drvdata->config;
struct device *etm_dev = &drvdata->csdev->dev;
struct coresight_device *csdev = drvdata->csdev;
+ struct csdev_access *csa = &csdev->access;
int i;
- CS_UNLOCK(&csdev->access);
+ CS_UNLOCK(csa);
if (!drvdata->skip_power_up) {
/* power can be removed from the trace unit now */
- control = readl_relaxed(drvdata->base + TRCPDCR);
+ control = etm4x_relaxed_read32(csa, TRCPDCR);
control &= ~TRCPDCR_PU;
- writel_relaxed(control, drvdata->base + TRCPDCR);
+ etm4x_relaxed_write32(csa, control, TRCPDCR);
}
- control = readl_relaxed(drvdata->base + TRCPRGCTLR);
+ control = etm4x_relaxed_read32(csa, TRCPRGCTLR);
/* EN, bit[0] Trace unit enable bit */
control &= ~0x1;
@@ -500,7 +498,7 @@ static void etm4_disable_hw(void *info)
*/
dsb(sy);
isb();
- writel_relaxed(control, drvdata->base + TRCPRGCTLR);
+ etm4x_relaxed_write32(csa, control, TRCPRGCTLR);
/* wait for TRCSTATR.PMSTABLE to go to '1' */
if (coresight_timeout(&csdev->access, TRCSTATR,
@@ -511,13 +509,13 @@ static void etm4_disable_hw(void *info)
/* read the status of the single shot comparators */
for (i = 0; i < drvdata->nr_ss_cmp; i++) {
config->ss_status[i] =
- readl_relaxed(drvdata->base + TRCSSCSRn(i));
+ etm4x_relaxed_read32(csa, TRCSSCSRn(i));
}
/* read back the current counter values */
for (i = 0; i < drvdata->nr_cntr; i++) {
config->cntr_val[i] =
- readl_relaxed(drvdata->base + TRCCNTVRn(i));
+ etm4x_relaxed_read32(csa, TRCCNTVRn(i));
}
coresight_disclaim_device_unlocked(csdev);
@@ -546,7 +544,7 @@ static int etm4_disable_perf(struct coresight_device *csdev,
* scheduled again. Configuration of the start/stop logic happens in
* function etm4_set_event_filters().
*/
- control = readl_relaxed(drvdata->base + TRCVICTLR);
+ control = etm4x_relaxed_read32(&csdev->access, TRCVICTLR);
/* TRCVICTLR::SSSTATUS, bit[9] */
filters->ssstatus = (control & BIT(9));
@@ -641,12 +639,12 @@ static void etm4_init_arch_data(void *info)
return;
/* Make sure all registers are accessible */
- etm4_os_unlock(drvdata);
+ etm4_os_unlock_csa(drvdata, csa);
CS_UNLOCK(csa);
/* find all capabilities of the tracing unit */
- etmidr0 = readl_relaxed(drvdata->base + TRCIDR0);
+ etmidr0 = etm4x_relaxed_read32(csa, TRCIDR0);
/* INSTP0, bits[2:1] P0 tracing support field */
if (BMVAL(etmidr0, 1, 1) && BMVAL(etmidr0, 2, 2))
@@ -686,7 +684,7 @@ static void etm4_init_arch_data(void *info)
drvdata->ts_size = BMVAL(etmidr0, 24, 28);
/* base architecture of trace unit */
- etmidr1 = readl_relaxed(drvdata->base + TRCIDR1);
+ etmidr1 = etm4x_relaxed_read32(csa, TRCIDR1);
/*
* TRCARCHMIN, bits[7:4] architecture the minor version number
* TRCARCHMAJ, bits[11:8] architecture major versin number
@@ -695,7 +693,7 @@ static void etm4_init_arch_data(void *info)
drvdata->config.arch = drvdata->arch;
/* maximum size of resources */
- etmidr2 = readl_relaxed(drvdata->base + TRCIDR2);
+ etmidr2 = etm4x_relaxed_read32(csa, TRCIDR2);
/* CIDSIZE, bits[9:5] Indicates the Context ID size */
drvdata->ctxid_size = BMVAL(etmidr2, 5, 9);
/* VMIDSIZE, bits[14:10] Indicates the VMID size */
@@ -703,7 +701,7 @@ static void etm4_init_arch_data(void *info)
/* CCSIZE, bits[28:25] size of the cycle counter in bits minus 12 */
drvdata->ccsize = BMVAL(etmidr2, 25, 28);
- etmidr3 = readl_relaxed(drvdata->base + TRCIDR3);
+ etmidr3 = etm4x_relaxed_read32(csa, TRCIDR3);
/* CCITMIN, bits[11:0] minimum threshold value that can be programmed */
drvdata->ccitmin = BMVAL(etmidr3, 0, 11);
/* EXLEVEL_S, bits[19:16] Secure state instruction tracing */
@@ -748,7 +746,7 @@ static void etm4_init_arch_data(void *info)
drvdata->nooverflow = false;
/* number of resources trace unit supports */
- etmidr4 = readl_relaxed(drvdata->base + TRCIDR4);
+ etmidr4 = etm4x_relaxed_read32(csa, TRCIDR4);
/* NUMACPAIRS, bits[0:3] number of addr comparator pairs for tracing */
drvdata->nr_addr_cmp = BMVAL(etmidr4, 0, 3);
/* NUMPC, bits[15:12] number of PE comparator inputs for tracing */
@@ -768,14 +766,14 @@ static void etm4_init_arch_data(void *info)
drvdata->nr_ss_cmp = BMVAL(etmidr4, 20, 23);
for (i = 0; i < drvdata->nr_ss_cmp; i++) {
drvdata->config.ss_status[i] =
- readl_relaxed(drvdata->base + TRCSSCSRn(i));
+ etm4x_relaxed_read32(csa, TRCSSCSRn(i));
}
/* NUMCIDC, bits[27:24] number of Context ID comparators for tracing */
drvdata->numcidc = BMVAL(etmidr4, 24, 27);
/* NUMVMIDC, bits[31:28] number of VMID comparators for tracing */
drvdata->numvmidc = BMVAL(etmidr4, 28, 31);
- etmidr5 = readl_relaxed(drvdata->base + TRCIDR5);
+ etmidr5 = etm4x_relaxed_read32(csa, TRCIDR5);
/* NUMEXTIN, bits[8:0] number of external inputs implemented */
drvdata->nr_ext_inp = BMVAL(etmidr5, 0, 8);
/* TRACEIDSIZE, bits[21:16] indicates the trace ID width */
@@ -1173,8 +1171,7 @@ static int etm4_cpu_save(struct etmv4_drvdata *drvdata)
etm4_os_lock(drvdata);
/* wait for TRCSTATR.PMSTABLE to go up */
- if (coresight_timeout(&csdev->access, TRCSTATR,
- TRCSTATR_PMSTABLE_BIT, 1)) {
+ if (coresight_timeout(csa, TRCSTATR, TRCSTATR_PMSTABLE_BIT, 1)) {
dev_err(etm_dev,
"timeout while waiting for PM Stable Status\n");
etm4_os_unlock(drvdata);
@@ -1184,53 +1181,53 @@ static int etm4_cpu_save(struct etmv4_drvdata *drvdata)
state = drvdata->save_state;
- state->trcprgctlr = readl(drvdata->base + TRCPRGCTLR);
- state->trcprocselr = readl(drvdata->base + TRCPROCSELR);
- state->trcconfigr = readl(drvdata->base + TRCCONFIGR);
- state->trcauxctlr = readl(drvdata->base + TRCAUXCTLR);
- state->trceventctl0r = readl(drvdata->base + TRCEVENTCTL0R);
- state->trceventctl1r = readl(drvdata->base + TRCEVENTCTL1R);
- state->trcstallctlr = readl(drvdata->base + TRCSTALLCTLR);
- state->trctsctlr = readl(drvdata->base + TRCTSCTLR);
- state->trcsyncpr = readl(drvdata->base + TRCSYNCPR);
- state->trcccctlr = readl(drvdata->base + TRCCCCTLR);
- state->trcbbctlr = readl(drvdata->base + TRCBBCTLR);
- state->trctraceidr = readl(drvdata->base + TRCTRACEIDR);
- state->trcqctlr = readl(drvdata->base + TRCQCTLR);
-
- state->trcvictlr = readl(drvdata->base + TRCVICTLR);
- state->trcviiectlr = readl(drvdata->base + TRCVIIECTLR);
- state->trcvissctlr = readl(drvdata->base + TRCVISSCTLR);
- state->trcvipcssctlr = readl(drvdata->base + TRCVIPCSSCTLR);
- state->trcvdctlr = readl(drvdata->base + TRCVDCTLR);
- state->trcvdsacctlr = readl(drvdata->base + TRCVDSACCTLR);
- state->trcvdarcctlr = readl(drvdata->base + TRCVDARCCTLR);
+ state->trcprgctlr = etm4x_read32(csa, TRCPRGCTLR);
+ state->trcprocselr = etm4x_read32(csa, TRCPROCSELR);
+ state->trcconfigr = etm4x_read32(csa, TRCCONFIGR);
+ state->trcauxctlr = etm4x_read32(csa, TRCAUXCTLR);
+ state->trceventctl0r = etm4x_read32(csa, TRCEVENTCTL0R);
+ state->trceventctl1r = etm4x_read32(csa, TRCEVENTCTL1R);
+ state->trcstallctlr = etm4x_read32(csa, TRCSTALLCTLR);
+ state->trctsctlr = etm4x_read32(csa, TRCTSCTLR);
+ state->trcsyncpr = etm4x_read32(csa, TRCSYNCPR);
+ state->trcccctlr = etm4x_read32(csa, TRCCCCTLR);
+ state->trcbbctlr = etm4x_read32(csa, TRCBBCTLR);
+ state->trctraceidr = etm4x_read32(csa, TRCTRACEIDR);
+ state->trcqctlr = etm4x_read32(csa, TRCQCTLR);
+
+ state->trcvictlr = etm4x_read32(csa, TRCVICTLR);
+ state->trcviiectlr = etm4x_read32(csa, TRCVIIECTLR);
+ state->trcvissctlr = etm4x_read32(csa, TRCVISSCTLR);
+ state->trcvipcssctlr = etm4x_read32(csa, TRCVIPCSSCTLR);
+ state->trcvdctlr = etm4x_read32(csa, TRCVDCTLR);
+ state->trcvdsacctlr = etm4x_read32(csa, TRCVDSACCTLR);
+ state->trcvdarcctlr = etm4x_read32(csa, TRCVDARCCTLR);
for (i = 0; i < drvdata->nrseqstate; i++)
- state->trcseqevr[i] = readl(drvdata->base + TRCSEQEVRn(i));
+ state->trcseqevr[i] = etm4x_read32(csa, TRCSEQEVRn(i));
- state->trcseqrstevr = readl(drvdata->base + TRCSEQRSTEVR);
- state->trcseqstr = readl(drvdata->base + TRCSEQSTR);
- state->trcextinselr = readl(drvdata->base + TRCEXTINSELR);
+ state->trcseqrstevr = etm4x_read32(csa, TRCSEQRSTEVR);
+ state->trcseqstr = etm4x_read32(csa, TRCSEQSTR);
+ state->trcextinselr = etm4x_read32(csa, TRCEXTINSELR);
for (i = 0; i < drvdata->nr_cntr; i++) {
- state->trccntrldvr[i] = readl(drvdata->base + TRCCNTRLDVRn(i));
- state->trccntctlr[i] = readl(drvdata->base + TRCCNTCTLRn(i));
- state->trccntvr[i] = readl(drvdata->base + TRCCNTVRn(i));
+ state->trccntrldvr[i] = etm4x_read32(csa, TRCCNTRLDVRn(i));
+ state->trccntctlr[i] = etm4x_read32(csa, TRCCNTCTLRn(i));
+ state->trccntvr[i] = etm4x_read32(csa, TRCCNTVRn(i));
}
for (i = 0; i < drvdata->nr_resource * 2; i++)
- state->trcrsctlr[i] = readl(drvdata->base + TRCRSCTLRn(i));
+ state->trcrsctlr[i] = etm4x_read32(csa, TRCRSCTLRn(i));
for (i = 0; i < drvdata->nr_ss_cmp; i++) {
- state->trcssccr[i] = readl(drvdata->base + TRCSSCCRn(i));
- state->trcsscsr[i] = readl(drvdata->base + TRCSSCSRn(i));
- state->trcsspcicr[i] = readl(drvdata->base + TRCSSPCICRn(i));
+ state->trcssccr[i] = etm4x_read32(csa, TRCSSCCRn(i));
+ state->trcsscsr[i] = etm4x_read32(csa, TRCSSCSRn(i));
+ state->trcsspcicr[i] = etm4x_read32(csa, TRCSSPCICRn(i));
}
for (i = 0; i < drvdata->nr_addr_cmp * 2; i++) {
- state->trcacvr[i] = readq(drvdata->base + TRCACVRn(i));
- state->trcacatr[i] = readq(drvdata->base + TRCACATRn(i));
+ state->trcacvr[i] = etm4x_read64(csa, TRCACVRn(i));
+ state->trcacatr[i] = etm4x_read64(csa, TRCACATRn(i));
}
/*
@@ -1241,23 +1238,23 @@ static int etm4_cpu_save(struct etmv4_drvdata *drvdata)
*/
for (i = 0; i < drvdata->numcidc; i++)
- state->trccidcvr[i] = readq(drvdata->base + TRCCIDCVRn(i));
+ state->trccidcvr[i] = etm4x_read64(csa, TRCCIDCVRn(i));
for (i = 0; i < drvdata->numvmidc; i++)
- state->trcvmidcvr[i] = readq(drvdata->base + TRCVMIDCVRn(i));
+ state->trcvmidcvr[i] = etm4x_read64(csa, TRCVMIDCVRn(i));
- state->trccidcctlr0 = readl(drvdata->base + TRCCIDCCTLR0);
- state->trccidcctlr1 = readl(drvdata->base + TRCCIDCCTLR1);
+ state->trccidcctlr0 = etm4x_read32(csa, TRCCIDCCTLR0);
+ state->trccidcctlr1 = etm4x_read32(csa, TRCCIDCCTLR1);
- state->trcvmidcctlr0 = readl(drvdata->base + TRCVMIDCCTLR0);
- state->trcvmidcctlr0 = readl(drvdata->base + TRCVMIDCCTLR1);
+ state->trcvmidcctlr0 = etm4x_read32(csa, TRCVMIDCCTLR0);
+ state->trcvmidcctlr0 = etm4x_read32(csa, TRCVMIDCCTLR1);
- state->trcclaimset = readl(drvdata->base + TRCCLAIMCLR);
+ state->trcclaimset = etm4x_read32(csa, TRCCLAIMCLR);
- state->trcpdcr = readl(drvdata->base + TRCPDCR);
+ state->trcpdcr = etm4x_read32(csa, TRCPDCR);
/* wait for TRCSTATR.IDLE to go up */
- if (coresight_timeout(&csdev->access, TRCSTATR, TRCSTATR_IDLE_BIT, 1)) {
+ if (coresight_timeout(csa, TRCSTATR, TRCSTATR_IDLE_BIT, 1)) {
dev_err(etm_dev,
"timeout while waiting for Idle Trace Status\n");
etm4_os_unlock(drvdata);
@@ -1272,8 +1269,7 @@ static int etm4_cpu_save(struct etmv4_drvdata *drvdata)
* potentially save power on systems that respect the TRCPDCR_PU
* despite requesting software to save/restore state.
*/
- writel_relaxed((state->trcpdcr & ~TRCPDCR_PU),
- drvdata->base + TRCPDCR);
+ etm4x_relaxed_write32(csa, (state->trcpdcr & ~TRCPDCR_PU), TRCPDCR);
out:
CS_LOCK(csa);
@@ -1293,84 +1289,72 @@ static void etm4_cpu_restore(struct etmv4_drvdata *drvdata)
csa = &csdev->access;
CS_UNLOCK(csa);
- writel_relaxed(state->trcclaimset, drvdata->base + TRCCLAIMSET);
-
- writel_relaxed(state->trcprgctlr, drvdata->base + TRCPRGCTLR);
- writel_relaxed(state->trcprocselr, drvdata->base + TRCPROCSELR);
- writel_relaxed(state->trcconfigr, drvdata->base + TRCCONFIGR);
- writel_relaxed(state->trcauxctlr, drvdata->base + TRCAUXCTLR);
- writel_relaxed(state->trceventctl0r, drvdata->base + TRCEVENTCTL0R);
- writel_relaxed(state->trceventctl1r, drvdata->base + TRCEVENTCTL1R);
- writel_relaxed(state->trcstallctlr, drvdata->base + TRCSTALLCTLR);
- writel_relaxed(state->trctsctlr, drvdata->base + TRCTSCTLR);
- writel_relaxed(state->trcsyncpr, drvdata->base + TRCSYNCPR);
- writel_relaxed(state->trcccctlr, drvdata->base + TRCCCCTLR);
- writel_relaxed(state->trcbbctlr, drvdata->base + TRCBBCTLR);
- writel_relaxed(state->trctraceidr, drvdata->base + TRCTRACEIDR);
- writel_relaxed(state->trcqctlr, drvdata->base + TRCQCTLR);
-
- writel_relaxed(state->trcvictlr, drvdata->base + TRCVICTLR);
- writel_relaxed(state->trcviiectlr, drvdata->base + TRCVIIECTLR);
- writel_relaxed(state->trcvissctlr, drvdata->base + TRCVISSCTLR);
- writel_relaxed(state->trcvipcssctlr, drvdata->base + TRCVIPCSSCTLR);
- writel_relaxed(state->trcvdctlr, drvdata->base + TRCVDCTLR);
- writel_relaxed(state->trcvdsacctlr, drvdata->base + TRCVDSACCTLR);
- writel_relaxed(state->trcvdarcctlr, drvdata->base + TRCVDARCCTLR);
+ etm4x_relaxed_write32(csa, state->trcclaimset, TRCCLAIMSET);
+
+ etm4x_relaxed_write32(csa, state->trcprgctlr, TRCPRGCTLR);
+ etm4x_relaxed_write32(csa, state->trcprocselr, TRCPROCSELR);
+ etm4x_relaxed_write32(csa, state->trcconfigr, TRCCONFIGR);
+ etm4x_relaxed_write32(csa, state->trcauxctlr, TRCAUXCTLR);
+ etm4x_relaxed_write32(csa, state->trceventctl0r, TRCEVENTCTL0R);
+ etm4x_relaxed_write32(csa, state->trceventctl1r, TRCEVENTCTL1R);
+ etm4x_relaxed_write32(csa, state->trcstallctlr, TRCSTALLCTLR);
+ etm4x_relaxed_write32(csa, state->trctsctlr, TRCTSCTLR);
+ etm4x_relaxed_write32(csa, state->trcsyncpr, TRCSYNCPR);
+ etm4x_relaxed_write32(csa, state->trcccctlr, TRCCCCTLR);
+ etm4x_relaxed_write32(csa, state->trcbbctlr, TRCBBCTLR);
+ etm4x_relaxed_write32(csa, state->trctraceidr, TRCTRACEIDR);
+ etm4x_relaxed_write32(csa, state->trcqctlr, TRCQCTLR);
+
+ etm4x_relaxed_write32(csa, state->trcvictlr, TRCVICTLR);
+ etm4x_relaxed_write32(csa, state->trcviiectlr, TRCVIIECTLR);
+ etm4x_relaxed_write32(csa, state->trcvissctlr, TRCVISSCTLR);
+ etm4x_relaxed_write32(csa, state->trcvipcssctlr, TRCVIPCSSCTLR);
+ etm4x_relaxed_write32(csa, state->trcvdctlr, TRCVDCTLR);
+ etm4x_relaxed_write32(csa, state->trcvdsacctlr, TRCVDSACCTLR);
+ etm4x_relaxed_write32(csa, state->trcvdarcctlr, TRCVDARCCTLR);
for (i = 0; i < drvdata->nrseqstate; i++)
- writel_relaxed(state->trcseqevr[i],
- drvdata->base + TRCSEQEVRn(i));
+ etm4x_relaxed_write32(csa, state->trcseqevr[i], TRCSEQEVRn(i));
- writel_relaxed(state->trcseqrstevr, drvdata->base + TRCSEQRSTEVR);
- writel_relaxed(state->trcseqstr, drvdata->base + TRCSEQSTR);
- writel_relaxed(state->trcextinselr, drvdata->base + TRCEXTINSELR);
+ etm4x_relaxed_write32(csa, state->trcseqrstevr, TRCSEQRSTEVR);
+ etm4x_relaxed_write32(csa, state->trcseqstr, TRCSEQSTR);
+ etm4x_relaxed_write32(csa, state->trcextinselr, TRCEXTINSELR);
for (i = 0; i < drvdata->nr_cntr; i++) {
- writel_relaxed(state->trccntrldvr[i],
- drvdata->base + TRCCNTRLDVRn(i));
- writel_relaxed(state->trccntctlr[i],
- drvdata->base + TRCCNTCTLRn(i));
- writel_relaxed(state->trccntvr[i],
- drvdata->base + TRCCNTVRn(i));
+ etm4x_relaxed_write32(csa, state->trccntrldvr[i], TRCCNTRLDVRn(i));
+ etm4x_relaxed_write32(csa, state->trccntctlr[i], TRCCNTCTLRn(i));
+ etm4x_relaxed_write32(csa, state->trccntvr[i], TRCCNTVRn(i));
}
for (i = 0; i < drvdata->nr_resource * 2; i++)
- writel_relaxed(state->trcrsctlr[i],
- drvdata->base + TRCRSCTLRn(i));
+ etm4x_relaxed_write32(csa, state->trcrsctlr[i], TRCRSCTLRn(i));
for (i = 0; i < drvdata->nr_ss_cmp; i++) {
- writel_relaxed(state->trcssccr[i],
- drvdata->base + TRCSSCCRn(i));
- writel_relaxed(state->trcsscsr[i],
- drvdata->base + TRCSSCSRn(i));
- writel_relaxed(state->trcsspcicr[i],
- drvdata->base + TRCSSPCICRn(i));
+ etm4x_relaxed_write32(csa, state->trcssccr[i], TRCSSCCRn(i));
+ etm4x_relaxed_write32(csa, state->trcsscsr[i], TRCSSCSRn(i));
+ etm4x_relaxed_write32(csa, state->trcsspcicr[i], TRCSSPCICRn(i));
}
for (i = 0; i < drvdata->nr_addr_cmp * 2; i++) {
- writeq_relaxed(state->trcacvr[i],
- drvdata->base + TRCACVRn(i));
- writeq_relaxed(state->trcacatr[i],
- drvdata->base + TRCACATRn(i));
+ etm4x_relaxed_write64(csa, state->trcacvr[i], TRCACVRn(i));
+ etm4x_relaxed_write64(csa, state->trcacatr[i], TRCACATRn(i));
}
for (i = 0; i < drvdata->numcidc; i++)
- writeq_relaxed(state->trccidcvr[i],
- drvdata->base + TRCCIDCVRn(i));
+ etm4x_relaxed_write64(csa, state->trccidcvr[i], TRCCIDCVRn(i));
for (i = 0; i < drvdata->numvmidc; i++)
- writeq_relaxed(state->trcvmidcvr[i],
- drvdata->base + TRCVMIDCVRn(i));
+ etm4x_relaxed_write64(csa, state->trcvmidcvr[i], TRCVMIDCVRn(i));
- writel_relaxed(state->trccidcctlr0, drvdata->base + TRCCIDCCTLR0);
- writel_relaxed(state->trccidcctlr1, drvdata->base + TRCCIDCCTLR1);
+ etm4x_relaxed_write32(csa, state->trccidcctlr0, TRCCIDCCTLR0);
+ etm4x_relaxed_write32(csa, state->trccidcctlr1, TRCCIDCCTLR1);
- writel_relaxed(state->trcvmidcctlr0, drvdata->base + TRCVMIDCCTLR0);
- writel_relaxed(state->trcvmidcctlr0, drvdata->base + TRCVMIDCCTLR1);
+ etm4x_relaxed_write32(csa, state->trcvmidcctlr0, TRCVMIDCCTLR0);
+ etm4x_relaxed_write32(csa, state->trcvmidcctlr0, TRCVMIDCCTLR1);
- writel_relaxed(state->trcclaimset, drvdata->base + TRCCLAIMSET);
+ etm4x_relaxed_write32(csa, state->trcclaimset, TRCCLAIMSET);
- writel_relaxed(state->trcpdcr, drvdata->base + TRCPDCR);
+ etm4x_relaxed_write32(csa, state->trcpdcr, TRCPDCR);
drvdata->state_needs_restore = false;
diff --git a/drivers/hwtracing/coresight/coresight-etm4x.h b/drivers/hwtracing/coresight/coresight-etm4x.h
index b8283e1d6d88..2b51d03ab6d7 100644
--- a/drivers/hwtracing/coresight/coresight-etm4x.h
+++ b/drivers/hwtracing/coresight/coresight-etm4x.h
@@ -120,6 +120,30 @@
#define TRCCIDR2 0xFF8
#define TRCCIDR3 0xFFC
+#define etm4x_relaxed_read32(csa, offset) \
+ readl_relaxed((csa)->base + (offset))
+
+#define etm4x_read32(csa, offset) \
+ readl((csa)->base + (offset))
+
+#define etm4x_relaxed_write32(csa, val, offset) \
+ writel_relaxed((val), (csa)->base + (offset))
+
+#define etm4x_write32(csa, val, offset) \
+ writel((val), (csa)->base + (offset))
+
+#define etm4x_relaxed_read64(csa, offset) \
+ readq_relaxed((csa)->base + (offset))
+
+#define etm4x_read64(csa, offset) \
+ readq((csa)->base + (offset))
+
+#define etm4x_relaxed_write64(csa, val, offset) \
+ writeq_relaxed((val), (csa)->base + (offset))
+
+#define etm4x_write64(csa, val, offset) \
+ writeq((val), (csa)->base + (offset))
+
/* ETMv4 resources */
#define ETM_MAX_NR_PE 8
#define ETMv4_MAX_CNTR 4
--
2.24.1
etm4_init_arch_data is called early during the device probe,
even before the coresight_device is registered. Since we are
about to replace the direct access via abstraction layer, we
need a way to pass in the csdev_access for the given device.
Towards this free up the argument, which is already available
via etmdrvdata[smp_processor_id()].
Cc: Mathieu Poirier <[email protected]>
Cc: Mike Leach <[email protected]>
Signed-off-by: Suzuki K Poulose <[email protected]>
---
drivers/hwtracing/coresight/coresight-etm4x.c | 15 +++++++++++----
1 file changed, 11 insertions(+), 4 deletions(-)
diff --git a/drivers/hwtracing/coresight/coresight-etm4x.c b/drivers/hwtracing/coresight/coresight-etm4x.c
index 7bb74c659c4f..67deb4a4e618 100644
--- a/drivers/hwtracing/coresight/coresight-etm4x.c
+++ b/drivers/hwtracing/coresight/coresight-etm4x.c
@@ -614,7 +614,8 @@ static const struct coresight_ops etm4_cs_ops = {
.source_ops = &etm4_source_ops,
};
-static void etm4_init_arch_data(void *info)
+
+static void etm4_init_arch_data(void *__unused)
{
u32 etmidr0;
u32 etmidr1;
@@ -622,8 +623,14 @@ static void etm4_init_arch_data(void *info)
u32 etmidr3;
u32 etmidr4;
u32 etmidr5;
- struct etmv4_drvdata *drvdata = info;
- int i;
+ struct etmv4_drvdata *drvdata;
+ int i, cpu;
+
+ cpu = raw_smp_processor_id();
+ drvdata = etmdrvdata[cpu];
+
+ if (WARN_ON(!etmdrvdata[cpu]))
+ return;
/* Make sure all registers are accessible */
etm4_os_unlock(drvdata);
@@ -1517,7 +1524,7 @@ static int etm4_probe(struct amba_device *adev, const struct amba_id *id)
etmdrvdata[drvdata->cpu] = drvdata;
if (smp_call_function_single(drvdata->cpu,
- etm4_init_arch_data, drvdata, 1))
+ etm4_init_arch_data, NULL, 1))
dev_err(dev, "ETM arch init failed\n");
ret = etm4_pm_setup_cpuslocked();
--
2.24.1
On Wed, Jul 22, 2020 at 06:20:30PM +0100, Suzuki K Poulose wrote:
> etm4_init_arch_data is called early during the device probe,
> even before the coresight_device is registered. Since we are
> about to replace the direct access via abstraction layer, we
> need a way to pass in the csdev_access for the given device.
> Towards this free up the argument, which is already available
> via etmdrvdata[smp_processor_id()].
>
> Cc: Mathieu Poirier <[email protected]>
> Cc: Mike Leach <[email protected]>
> Signed-off-by: Suzuki K Poulose <[email protected]>
> ---
> drivers/hwtracing/coresight/coresight-etm4x.c | 15 +++++++++++----
> 1 file changed, 11 insertions(+), 4 deletions(-)
>
> diff --git a/drivers/hwtracing/coresight/coresight-etm4x.c b/drivers/hwtracing/coresight/coresight-etm4x.c
> index 7bb74c659c4f..67deb4a4e618 100644
> --- a/drivers/hwtracing/coresight/coresight-etm4x.c
> +++ b/drivers/hwtracing/coresight/coresight-etm4x.c
> @@ -614,7 +614,8 @@ static const struct coresight_ops etm4_cs_ops = {
> .source_ops = &etm4_source_ops,
> };
>
> -static void etm4_init_arch_data(void *info)
> +
> +static void etm4_init_arch_data(void *__unused)
> {
> u32 etmidr0;
> u32 etmidr1;
> @@ -622,8 +623,14 @@ static void etm4_init_arch_data(void *info)
> u32 etmidr3;
> u32 etmidr4;
> u32 etmidr5;
> - struct etmv4_drvdata *drvdata = info;
> - int i;
> + struct etmv4_drvdata *drvdata;
> + int i, cpu;
> +
> + cpu = raw_smp_processor_id();
Can you provide details on the motivation to use the raw_ version over the regular
one? As far as I can see in linux/smp.h there is no difference between them
unless DEBUB_PREEMPT is enabled. Even then the debug version won't complain
since the task is CPU affined.
> + drvdata = etmdrvdata[cpu];
> +
> + if (WARN_ON(!etmdrvdata[cpu]))
> + return;
>
> /* Make sure all registers are accessible */
> etm4_os_unlock(drvdata);
> @@ -1517,7 +1524,7 @@ static int etm4_probe(struct amba_device *adev, const struct amba_id *id)
> etmdrvdata[drvdata->cpu] = drvdata;
>
> if (smp_call_function_single(drvdata->cpu,
> - etm4_init_arch_data, drvdata, 1))
> + etm4_init_arch_data, NULL, 1))
> dev_err(dev, "ETM arch init failed\n");
>
> ret = etm4_pm_setup_cpuslocked();
> --
> 2.24.1
>
On Wed, Jul 22, 2020 at 06:20:34PM +0100, Suzuki K Poulose wrote:
> Convert all register accesses from etm4x driver to use a wrapper
> to allow switching the access at runtime with little overhead.
>
> co-developed by sed tool ;-), mostly equivalent to :
>
> s/readl\(_relaxed\)\?(drvdata->base + \(.*\))/etm4x_\1_read32(csdev, \2)
> s/writel\(_relaxed\)\?(\(.*\), drvdata->base + \(.*\))/etm4x_\1_write32(csdev, \2, \3)
>
> We don't want to replace them with the csdev_access_* to
> avoid a function call for every register access for system
> register access.
>
> Cc: Mathieu Poirier <[email protected]>
> Cc: Mike Leach <[email protected]>
> Signed-off-by: Suzuki K Poulose <[email protected]>
> ---
> .../coresight/coresight-etm4x-sysfs.c | 9 +-
> drivers/hwtracing/coresight/coresight-etm4x.c | 334 +++++++++---------
> drivers/hwtracing/coresight/coresight-etm4x.h | 24 ++
> 3 files changed, 189 insertions(+), 178 deletions(-)
>
> diff --git a/drivers/hwtracing/coresight/coresight-etm4x-sysfs.c b/drivers/hwtracing/coresight/coresight-etm4x-sysfs.c
> index 90c75ba31a0c..fe40355f6a2c 100644
> --- a/drivers/hwtracing/coresight/coresight-etm4x-sysfs.c
> +++ b/drivers/hwtracing/coresight/coresight-etm4x-sysfs.c
> @@ -2316,7 +2316,8 @@ static struct attribute *coresight_etmv4_attrs[] = {
> };
>
> struct etmv4_reg {
> - void __iomem *addr;
> + struct coresight_device *csdev;
> + u32 offset;
> u32 data;
> };
>
> @@ -2324,7 +2325,7 @@ static void do_smp_cross_read(void *data)
> {
> struct etmv4_reg *reg = data;
>
> - reg->data = readl_relaxed(reg->addr);
> + reg->data = etm4x_relaxed_read32(®->csdev->access, reg->offset);
> }
>
> static u32 etmv4_cross_read(const struct device *dev, u32 offset)
> @@ -2332,7 +2333,9 @@ static u32 etmv4_cross_read(const struct device *dev, u32 offset)
> struct etmv4_drvdata *drvdata = dev_get_drvdata(dev);
> struct etmv4_reg reg;
>
> - reg.addr = drvdata->base + offset;
> + reg.offset = offset;
> + reg.csdev = drvdata->csdev;
> +
> /*
> * smp cross call ensures the CPU will be powered up before
> * accessing the ETMv4 trace core registers
> diff --git a/drivers/hwtracing/coresight/coresight-etm4x.c b/drivers/hwtracing/coresight/coresight-etm4x.c
> index ce32d4ebc8b9..b901c91d3ee4 100644
> --- a/drivers/hwtracing/coresight/coresight-etm4x.c
> +++ b/drivers/hwtracing/coresight/coresight-etm4x.c
> @@ -57,18 +57,28 @@ static int etm4_set_event_filters(struct etmv4_drvdata *drvdata,
>
> static enum cpuhp_state hp_online;
>
> -static void etm4_os_unlock(struct etmv4_drvdata *drvdata)
> +static void etm4_os_unlock_csa(struct etmv4_drvdata *drvdata, struct csdev_access *csa)
> {
> /* Writing 0 to TRCOSLAR unlocks the trace registers */
> - writel_relaxed(0x0, drvdata->base + TRCOSLAR);
> + etm4x_relaxed_write32(csa, 0x0, TRCOSLAR);
> drvdata->os_unlock = true;
> isb();
> }
>
> +static void etm4_os_unlock(struct etmv4_drvdata *drvdata)
> +{
> + if (!WARN_ON(!drvdata->csdev))
> + etm4_os_unlock_csa(drvdata, &drvdata->csdev->access);
> +
> +}
> +
> static void etm4_os_lock(struct etmv4_drvdata *drvdata)
> {
> + if (WARN_ON(!drvdata->csdev))
> + return;
> +
> /* Writing 0x1 to TRCOSLAR locks the trace registers */
> - writel_relaxed(0x1, drvdata->base + TRCOSLAR);
> + etm4x_relaxed_write32(&drvdata->csdev->access, 0x1, TRCOSLAR);
> drvdata->os_unlock = false;
> isb();
> }
> @@ -121,44 +131,38 @@ static int etm4_enable_hw(struct etmv4_drvdata *drvdata)
> goto done;
>
> /* Disable the trace unit before programming trace registers */
> - writel_relaxed(0, drvdata->base + TRCPRGCTLR);
> + etm4x_relaxed_write32(csa, 0, TRCPRGCTLR);
>
> /* wait for TRCSTATR.IDLE to go up */
> if (coresight_timeout(&csdev->access, TRCSTATR, TRCSTATR_IDLE_BIT, 1))
> dev_err(etm_dev,
> "timeout while waiting for Idle Trace Status\n");
>
> - writel_relaxed(config->pe_sel, drvdata->base + TRCPROCSELR);
> - writel_relaxed(config->cfg, drvdata->base + TRCCONFIGR);
> + etm4x_relaxed_write32(csa, config->pe_sel, TRCPROCSELR);
> + etm4x_relaxed_write32(csa, config->cfg, TRCCONFIGR);
> /* nothing specific implemented */
> - writel_relaxed(0x0, drvdata->base + TRCAUXCTLR);
> - writel_relaxed(config->eventctrl0, drvdata->base + TRCEVENTCTL0R);
> - writel_relaxed(config->eventctrl1, drvdata->base + TRCEVENTCTL1R);
> - writel_relaxed(config->stall_ctrl, drvdata->base + TRCSTALLCTLR);
> - writel_relaxed(config->ts_ctrl, drvdata->base + TRCTSCTLR);
> - writel_relaxed(config->syncfreq, drvdata->base + TRCSYNCPR);
> - writel_relaxed(config->ccctlr, drvdata->base + TRCCCCTLR);
> - writel_relaxed(config->bb_ctrl, drvdata->base + TRCBBCTLR);
> - writel_relaxed(drvdata->trcid, drvdata->base + TRCTRACEIDR);
> - writel_relaxed(config->vinst_ctrl, drvdata->base + TRCVICTLR);
> - writel_relaxed(config->viiectlr, drvdata->base + TRCVIIECTLR);
> - writel_relaxed(config->vissctlr,
> - drvdata->base + TRCVISSCTLR);
> - writel_relaxed(config->vipcssctlr,
> - drvdata->base + TRCVIPCSSCTLR);
> + etm4x_relaxed_write32(csa, 0x0, TRCAUXCTLR);
> + etm4x_relaxed_write32(csa, config->eventctrl0, TRCEVENTCTL0R);
> + etm4x_relaxed_write32(csa, config->eventctrl1, TRCEVENTCTL1R);
> + etm4x_relaxed_write32(csa, config->stall_ctrl, TRCSTALLCTLR);
> + etm4x_relaxed_write32(csa, config->ts_ctrl, TRCTSCTLR);
> + etm4x_relaxed_write32(csa, config->syncfreq, TRCSYNCPR);
> + etm4x_relaxed_write32(csa, config->ccctlr, TRCCCCTLR);
> + etm4x_relaxed_write32(csa, config->bb_ctrl, TRCBBCTLR);
> + etm4x_relaxed_write32(csa, drvdata->trcid, TRCTRACEIDR);
> + etm4x_relaxed_write32(csa, config->vinst_ctrl, TRCVICTLR);
> + etm4x_relaxed_write32(csa, config->viiectlr, TRCVIIECTLR);
> + etm4x_relaxed_write32(csa, config->vissctlr, TRCVISSCTLR);
> + etm4x_relaxed_write32(csa, config->vipcssctlr, TRCVIPCSSCTLR);
> for (i = 0; i < drvdata->nrseqstate - 1; i++)
> - writel_relaxed(config->seq_ctrl[i],
> - drvdata->base + TRCSEQEVRn(i));
> - writel_relaxed(config->seq_rst, drvdata->base + TRCSEQRSTEVR);
> - writel_relaxed(config->seq_state, drvdata->base + TRCSEQSTR);
> - writel_relaxed(config->ext_inp, drvdata->base + TRCEXTINSELR);
> + etm4x_relaxed_write32(csa, config->seq_ctrl[i], TRCSEQEVRn(i));
> + etm4x_relaxed_write32(csa, config->seq_rst, TRCSEQRSTEVR);
> + etm4x_relaxed_write32(csa, config->seq_state, TRCSEQSTR);
> + etm4x_relaxed_write32(csa, config->ext_inp, TRCEXTINSELR);
> for (i = 0; i < drvdata->nr_cntr; i++) {
> - writel_relaxed(config->cntrldvr[i],
> - drvdata->base + TRCCNTRLDVRn(i));
> - writel_relaxed(config->cntr_ctrl[i],
> - drvdata->base + TRCCNTCTLRn(i));
> - writel_relaxed(config->cntr_val[i],
> - drvdata->base + TRCCNTVRn(i));
> + etm4x_relaxed_write32(csa, config->cntrldvr[i], TRCCNTRLDVRn(i));
> + etm4x_relaxed_write32(csa, config->cntr_ctrl[i], TRCCNTCTLRn(i));
> + etm4x_relaxed_write32(csa, config->cntr_val[i], TRCCNTVRn(i));
> }
>
> /*
> @@ -166,52 +170,45 @@ static int etm4_enable_hw(struct etmv4_drvdata *drvdata)
> * such start at 2.
> */
> for (i = 2; i < drvdata->nr_resource * 2; i++)
> - writel_relaxed(config->res_ctrl[i],
> - drvdata->base + TRCRSCTLRn(i));
> + etm4x_relaxed_write32(csa, config->res_ctrl[i], TRCRSCTLRn(i));
>
> for (i = 0; i < drvdata->nr_ss_cmp; i++) {
> /* always clear status bit on restart if using single-shot */
> if (config->ss_ctrl[i] || config->ss_pe_cmp[i])
> config->ss_status[i] &= ~BIT(31);
> - writel_relaxed(config->ss_ctrl[i],
> - drvdata->base + TRCSSCCRn(i));
> - writel_relaxed(config->ss_status[i],
> - drvdata->base + TRCSSCSRn(i));
> - writel_relaxed(config->ss_pe_cmp[i],
> - drvdata->base + TRCSSPCICRn(i));
> + etm4x_relaxed_write32(csa, config->ss_ctrl[i], TRCSSCCRn(i));
> + etm4x_relaxed_write32(csa, config->ss_status[i], TRCSSCSRn(i));
> + etm4x_relaxed_write32(csa, config->ss_pe_cmp[i], TRCSSPCICRn(i));
> }
> for (i = 0; i < drvdata->nr_addr_cmp; i++) {
> - writeq_relaxed(config->addr_val[i],
> - drvdata->base + TRCACVRn(i));
> - writeq_relaxed(config->addr_acc[i],
> - drvdata->base + TRCACATRn(i));
> + etm4x_relaxed_write64(csa, config->addr_val[i], TRCACVRn(i));
> + etm4x_relaxed_write64(csa, config->addr_acc[i], TRCACATRn(i));
> }
> for (i = 0; i < drvdata->numcidc; i++)
> - writeq_relaxed(config->ctxid_pid[i],
> - drvdata->base + TRCCIDCVRn(i));
> - writel_relaxed(config->ctxid_mask0, drvdata->base + TRCCIDCCTLR0);
> - writel_relaxed(config->ctxid_mask1, drvdata->base + TRCCIDCCTLR1);
> + etm4x_relaxed_write64(csa, config->ctxid_pid[i], TRCCIDCVRn(i));
> + etm4x_relaxed_write32(csa, config->ctxid_mask0, TRCCIDCCTLR0);
> + etm4x_relaxed_write32(csa, config->ctxid_mask1, TRCCIDCCTLR1);
>
> for (i = 0; i < drvdata->numvmidc; i++)
> - writeq_relaxed(config->vmid_val[i],
> - drvdata->base + TRCVMIDCVRn(i));
> - writel_relaxed(config->vmid_mask0, drvdata->base + TRCVMIDCCTLR0);
> - writel_relaxed(config->vmid_mask1, drvdata->base + TRCVMIDCCTLR1);
> + etm4x_relaxed_write64(csa, config->vmid_val[i], TRCVMIDCVRn(i));
> + etm4x_relaxed_write32(csa, config->vmid_mask0, TRCVMIDCCTLR0);
> + etm4x_relaxed_write32(csa, config->vmid_mask1, TRCVMIDCCTLR1);
>
> if (!drvdata->skip_power_up) {
> + u32 trcpdcr = etm4x_relaxed_read32(csa, TRCPDCR);
> +
> /*
> * Request to keep the trace unit powered and also
> * emulation of powerdown
> */
> - writel_relaxed(readl_relaxed(drvdata->base + TRCPDCR) |
> - TRCPDCR_PU, drvdata->base + TRCPDCR);
> + etm4x_relaxed_write32(csa, trcpdcr | TRCPDCR_PU, TRCPDCR);
> }
>
> /* Enable the trace unit */
> - writel_relaxed(1, drvdata->base + TRCPRGCTLR);
> + etm4x_relaxed_write32(csa, 1, TRCPRGCTLR);
>
> /* wait for TRCSTATR.IDLE to go back down to '0' */
> - if (coresight_timeout(&csdev->access, TRCSTATR, TRCSTATR_IDLE_BIT, 0))
> + if (coresight_timeout(csa, TRCSTATR, TRCSTATR_IDLE_BIT, 0))
Please avoid doing that. Change it once in 06/14 and don't touch after that.
Moreover it creates an imbalance because the other coresight_timeout() in the
same function still uses csdev->access. There are other instances of changes
like this in the file that need to be addressed.
> dev_err(etm_dev,
> "timeout while waiting for Idle Trace Status\n");
>
> @@ -477,18 +474,19 @@ static void etm4_disable_hw(void *info)
> struct etmv4_config *config = &drvdata->config;
> struct device *etm_dev = &drvdata->csdev->dev;
> struct coresight_device *csdev = drvdata->csdev;
> + struct csdev_access *csa = &csdev->access;
> int i;
>
> - CS_UNLOCK(&csdev->access);
> + CS_UNLOCK(csa);
Same here.
>
> if (!drvdata->skip_power_up) {
> /* power can be removed from the trace unit now */
> - control = readl_relaxed(drvdata->base + TRCPDCR);
> + control = etm4x_relaxed_read32(csa, TRCPDCR);
> control &= ~TRCPDCR_PU;
> - writel_relaxed(control, drvdata->base + TRCPDCR);
> + etm4x_relaxed_write32(csa, control, TRCPDCR);
> }
>
> - control = readl_relaxed(drvdata->base + TRCPRGCTLR);
> + control = etm4x_relaxed_read32(csa, TRCPRGCTLR);
>
> /* EN, bit[0] Trace unit enable bit */
> control &= ~0x1;
> @@ -500,7 +498,7 @@ static void etm4_disable_hw(void *info)
> */
> dsb(sy);
> isb();
> - writel_relaxed(control, drvdata->base + TRCPRGCTLR);
> + etm4x_relaxed_write32(csa, control, TRCPRGCTLR);
>
> /* wait for TRCSTATR.PMSTABLE to go to '1' */
> if (coresight_timeout(&csdev->access, TRCSTATR,
> @@ -511,13 +509,13 @@ static void etm4_disable_hw(void *info)
> /* read the status of the single shot comparators */
> for (i = 0; i < drvdata->nr_ss_cmp; i++) {
> config->ss_status[i] =
> - readl_relaxed(drvdata->base + TRCSSCSRn(i));
> + etm4x_relaxed_read32(csa, TRCSSCSRn(i));
> }
>
> /* read back the current counter values */
> for (i = 0; i < drvdata->nr_cntr; i++) {
> config->cntr_val[i] =
> - readl_relaxed(drvdata->base + TRCCNTVRn(i));
> + etm4x_relaxed_read32(csa, TRCCNTVRn(i));
> }
>
> coresight_disclaim_device_unlocked(csdev);
> @@ -546,7 +544,7 @@ static int etm4_disable_perf(struct coresight_device *csdev,
> * scheduled again. Configuration of the start/stop logic happens in
> * function etm4_set_event_filters().
> */
> - control = readl_relaxed(drvdata->base + TRCVICTLR);
> + control = etm4x_relaxed_read32(&csdev->access, TRCVICTLR);
> /* TRCVICTLR::SSSTATUS, bit[9] */
> filters->ssstatus = (control & BIT(9));
>
> @@ -641,12 +639,12 @@ static void etm4_init_arch_data(void *info)
> return;
>
> /* Make sure all registers are accessible */
> - etm4_os_unlock(drvdata);
> + etm4_os_unlock_csa(drvdata, csa);
>
> CS_UNLOCK(csa);
>
> /* find all capabilities of the tracing unit */
> - etmidr0 = readl_relaxed(drvdata->base + TRCIDR0);
> + etmidr0 = etm4x_relaxed_read32(csa, TRCIDR0);
>
> /* INSTP0, bits[2:1] P0 tracing support field */
> if (BMVAL(etmidr0, 1, 1) && BMVAL(etmidr0, 2, 2))
> @@ -686,7 +684,7 @@ static void etm4_init_arch_data(void *info)
> drvdata->ts_size = BMVAL(etmidr0, 24, 28);
>
> /* base architecture of trace unit */
> - etmidr1 = readl_relaxed(drvdata->base + TRCIDR1);
> + etmidr1 = etm4x_relaxed_read32(csa, TRCIDR1);
> /*
> * TRCARCHMIN, bits[7:4] architecture the minor version number
> * TRCARCHMAJ, bits[11:8] architecture major versin number
> @@ -695,7 +693,7 @@ static void etm4_init_arch_data(void *info)
> drvdata->config.arch = drvdata->arch;
>
> /* maximum size of resources */
> - etmidr2 = readl_relaxed(drvdata->base + TRCIDR2);
> + etmidr2 = etm4x_relaxed_read32(csa, TRCIDR2);
> /* CIDSIZE, bits[9:5] Indicates the Context ID size */
> drvdata->ctxid_size = BMVAL(etmidr2, 5, 9);
> /* VMIDSIZE, bits[14:10] Indicates the VMID size */
> @@ -703,7 +701,7 @@ static void etm4_init_arch_data(void *info)
> /* CCSIZE, bits[28:25] size of the cycle counter in bits minus 12 */
> drvdata->ccsize = BMVAL(etmidr2, 25, 28);
>
> - etmidr3 = readl_relaxed(drvdata->base + TRCIDR3);
> + etmidr3 = etm4x_relaxed_read32(csa, TRCIDR3);
> /* CCITMIN, bits[11:0] minimum threshold value that can be programmed */
> drvdata->ccitmin = BMVAL(etmidr3, 0, 11);
> /* EXLEVEL_S, bits[19:16] Secure state instruction tracing */
> @@ -748,7 +746,7 @@ static void etm4_init_arch_data(void *info)
> drvdata->nooverflow = false;
>
> /* number of resources trace unit supports */
> - etmidr4 = readl_relaxed(drvdata->base + TRCIDR4);
> + etmidr4 = etm4x_relaxed_read32(csa, TRCIDR4);
> /* NUMACPAIRS, bits[0:3] number of addr comparator pairs for tracing */
> drvdata->nr_addr_cmp = BMVAL(etmidr4, 0, 3);
> /* NUMPC, bits[15:12] number of PE comparator inputs for tracing */
> @@ -768,14 +766,14 @@ static void etm4_init_arch_data(void *info)
> drvdata->nr_ss_cmp = BMVAL(etmidr4, 20, 23);
> for (i = 0; i < drvdata->nr_ss_cmp; i++) {
> drvdata->config.ss_status[i] =
> - readl_relaxed(drvdata->base + TRCSSCSRn(i));
> + etm4x_relaxed_read32(csa, TRCSSCSRn(i));
> }
> /* NUMCIDC, bits[27:24] number of Context ID comparators for tracing */
> drvdata->numcidc = BMVAL(etmidr4, 24, 27);
> /* NUMVMIDC, bits[31:28] number of VMID comparators for tracing */
> drvdata->numvmidc = BMVAL(etmidr4, 28, 31);
>
> - etmidr5 = readl_relaxed(drvdata->base + TRCIDR5);
> + etmidr5 = etm4x_relaxed_read32(csa, TRCIDR5);
> /* NUMEXTIN, bits[8:0] number of external inputs implemented */
> drvdata->nr_ext_inp = BMVAL(etmidr5, 0, 8);
> /* TRACEIDSIZE, bits[21:16] indicates the trace ID width */
> @@ -1173,8 +1171,7 @@ static int etm4_cpu_save(struct etmv4_drvdata *drvdata)
> etm4_os_lock(drvdata);
>
> /* wait for TRCSTATR.PMSTABLE to go up */
> - if (coresight_timeout(&csdev->access, TRCSTATR,
> - TRCSTATR_PMSTABLE_BIT, 1)) {
> + if (coresight_timeout(csa, TRCSTATR, TRCSTATR_PMSTABLE_BIT, 1)) {
> dev_err(etm_dev,
> "timeout while waiting for PM Stable Status\n");
> etm4_os_unlock(drvdata);
> @@ -1184,53 +1181,53 @@ static int etm4_cpu_save(struct etmv4_drvdata *drvdata)
>
> state = drvdata->save_state;
>
> - state->trcprgctlr = readl(drvdata->base + TRCPRGCTLR);
> - state->trcprocselr = readl(drvdata->base + TRCPROCSELR);
> - state->trcconfigr = readl(drvdata->base + TRCCONFIGR);
> - state->trcauxctlr = readl(drvdata->base + TRCAUXCTLR);
> - state->trceventctl0r = readl(drvdata->base + TRCEVENTCTL0R);
> - state->trceventctl1r = readl(drvdata->base + TRCEVENTCTL1R);
> - state->trcstallctlr = readl(drvdata->base + TRCSTALLCTLR);
> - state->trctsctlr = readl(drvdata->base + TRCTSCTLR);
> - state->trcsyncpr = readl(drvdata->base + TRCSYNCPR);
> - state->trcccctlr = readl(drvdata->base + TRCCCCTLR);
> - state->trcbbctlr = readl(drvdata->base + TRCBBCTLR);
> - state->trctraceidr = readl(drvdata->base + TRCTRACEIDR);
> - state->trcqctlr = readl(drvdata->base + TRCQCTLR);
> -
> - state->trcvictlr = readl(drvdata->base + TRCVICTLR);
> - state->trcviiectlr = readl(drvdata->base + TRCVIIECTLR);
> - state->trcvissctlr = readl(drvdata->base + TRCVISSCTLR);
> - state->trcvipcssctlr = readl(drvdata->base + TRCVIPCSSCTLR);
> - state->trcvdctlr = readl(drvdata->base + TRCVDCTLR);
> - state->trcvdsacctlr = readl(drvdata->base + TRCVDSACCTLR);
> - state->trcvdarcctlr = readl(drvdata->base + TRCVDARCCTLR);
> + state->trcprgctlr = etm4x_read32(csa, TRCPRGCTLR);
> + state->trcprocselr = etm4x_read32(csa, TRCPROCSELR);
> + state->trcconfigr = etm4x_read32(csa, TRCCONFIGR);
> + state->trcauxctlr = etm4x_read32(csa, TRCAUXCTLR);
> + state->trceventctl0r = etm4x_read32(csa, TRCEVENTCTL0R);
> + state->trceventctl1r = etm4x_read32(csa, TRCEVENTCTL1R);
> + state->trcstallctlr = etm4x_read32(csa, TRCSTALLCTLR);
> + state->trctsctlr = etm4x_read32(csa, TRCTSCTLR);
> + state->trcsyncpr = etm4x_read32(csa, TRCSYNCPR);
> + state->trcccctlr = etm4x_read32(csa, TRCCCCTLR);
> + state->trcbbctlr = etm4x_read32(csa, TRCBBCTLR);
> + state->trctraceidr = etm4x_read32(csa, TRCTRACEIDR);
> + state->trcqctlr = etm4x_read32(csa, TRCQCTLR);
> +
> + state->trcvictlr = etm4x_read32(csa, TRCVICTLR);
> + state->trcviiectlr = etm4x_read32(csa, TRCVIIECTLR);
> + state->trcvissctlr = etm4x_read32(csa, TRCVISSCTLR);
> + state->trcvipcssctlr = etm4x_read32(csa, TRCVIPCSSCTLR);
> + state->trcvdctlr = etm4x_read32(csa, TRCVDCTLR);
> + state->trcvdsacctlr = etm4x_read32(csa, TRCVDSACCTLR);
> + state->trcvdarcctlr = etm4x_read32(csa, TRCVDARCCTLR);
>
> for (i = 0; i < drvdata->nrseqstate; i++)
> - state->trcseqevr[i] = readl(drvdata->base + TRCSEQEVRn(i));
> + state->trcseqevr[i] = etm4x_read32(csa, TRCSEQEVRn(i));
>
> - state->trcseqrstevr = readl(drvdata->base + TRCSEQRSTEVR);
> - state->trcseqstr = readl(drvdata->base + TRCSEQSTR);
> - state->trcextinselr = readl(drvdata->base + TRCEXTINSELR);
> + state->trcseqrstevr = etm4x_read32(csa, TRCSEQRSTEVR);
> + state->trcseqstr = etm4x_read32(csa, TRCSEQSTR);
> + state->trcextinselr = etm4x_read32(csa, TRCEXTINSELR);
>
> for (i = 0; i < drvdata->nr_cntr; i++) {
> - state->trccntrldvr[i] = readl(drvdata->base + TRCCNTRLDVRn(i));
> - state->trccntctlr[i] = readl(drvdata->base + TRCCNTCTLRn(i));
> - state->trccntvr[i] = readl(drvdata->base + TRCCNTVRn(i));
> + state->trccntrldvr[i] = etm4x_read32(csa, TRCCNTRLDVRn(i));
> + state->trccntctlr[i] = etm4x_read32(csa, TRCCNTCTLRn(i));
> + state->trccntvr[i] = etm4x_read32(csa, TRCCNTVRn(i));
> }
>
> for (i = 0; i < drvdata->nr_resource * 2; i++)
> - state->trcrsctlr[i] = readl(drvdata->base + TRCRSCTLRn(i));
> + state->trcrsctlr[i] = etm4x_read32(csa, TRCRSCTLRn(i));
>
> for (i = 0; i < drvdata->nr_ss_cmp; i++) {
> - state->trcssccr[i] = readl(drvdata->base + TRCSSCCRn(i));
> - state->trcsscsr[i] = readl(drvdata->base + TRCSSCSRn(i));
> - state->trcsspcicr[i] = readl(drvdata->base + TRCSSPCICRn(i));
> + state->trcssccr[i] = etm4x_read32(csa, TRCSSCCRn(i));
> + state->trcsscsr[i] = etm4x_read32(csa, TRCSSCSRn(i));
> + state->trcsspcicr[i] = etm4x_read32(csa, TRCSSPCICRn(i));
> }
>
> for (i = 0; i < drvdata->nr_addr_cmp * 2; i++) {
> - state->trcacvr[i] = readq(drvdata->base + TRCACVRn(i));
> - state->trcacatr[i] = readq(drvdata->base + TRCACATRn(i));
> + state->trcacvr[i] = etm4x_read64(csa, TRCACVRn(i));
> + state->trcacatr[i] = etm4x_read64(csa, TRCACATRn(i));
> }
>
> /*
> @@ -1241,23 +1238,23 @@ static int etm4_cpu_save(struct etmv4_drvdata *drvdata)
> */
>
> for (i = 0; i < drvdata->numcidc; i++)
> - state->trccidcvr[i] = readq(drvdata->base + TRCCIDCVRn(i));
> + state->trccidcvr[i] = etm4x_read64(csa, TRCCIDCVRn(i));
>
> for (i = 0; i < drvdata->numvmidc; i++)
> - state->trcvmidcvr[i] = readq(drvdata->base + TRCVMIDCVRn(i));
> + state->trcvmidcvr[i] = etm4x_read64(csa, TRCVMIDCVRn(i));
>
> - state->trccidcctlr0 = readl(drvdata->base + TRCCIDCCTLR0);
> - state->trccidcctlr1 = readl(drvdata->base + TRCCIDCCTLR1);
> + state->trccidcctlr0 = etm4x_read32(csa, TRCCIDCCTLR0);
> + state->trccidcctlr1 = etm4x_read32(csa, TRCCIDCCTLR1);
>
> - state->trcvmidcctlr0 = readl(drvdata->base + TRCVMIDCCTLR0);
> - state->trcvmidcctlr0 = readl(drvdata->base + TRCVMIDCCTLR1);
> + state->trcvmidcctlr0 = etm4x_read32(csa, TRCVMIDCCTLR0);
> + state->trcvmidcctlr0 = etm4x_read32(csa, TRCVMIDCCTLR1);
>
> - state->trcclaimset = readl(drvdata->base + TRCCLAIMCLR);
> + state->trcclaimset = etm4x_read32(csa, TRCCLAIMCLR);
>
> - state->trcpdcr = readl(drvdata->base + TRCPDCR);
> + state->trcpdcr = etm4x_read32(csa, TRCPDCR);
>
> /* wait for TRCSTATR.IDLE to go up */
> - if (coresight_timeout(&csdev->access, TRCSTATR, TRCSTATR_IDLE_BIT, 1)) {
> + if (coresight_timeout(csa, TRCSTATR, TRCSTATR_IDLE_BIT, 1)) {
> dev_err(etm_dev,
> "timeout while waiting for Idle Trace Status\n");
> etm4_os_unlock(drvdata);
> @@ -1272,8 +1269,7 @@ static int etm4_cpu_save(struct etmv4_drvdata *drvdata)
> * potentially save power on systems that respect the TRCPDCR_PU
> * despite requesting software to save/restore state.
> */
> - writel_relaxed((state->trcpdcr & ~TRCPDCR_PU),
> - drvdata->base + TRCPDCR);
> + etm4x_relaxed_write32(csa, (state->trcpdcr & ~TRCPDCR_PU), TRCPDCR);
>
> out:
> CS_LOCK(csa);
> @@ -1293,84 +1289,72 @@ static void etm4_cpu_restore(struct etmv4_drvdata *drvdata)
> csa = &csdev->access;
> CS_UNLOCK(csa);
>
> - writel_relaxed(state->trcclaimset, drvdata->base + TRCCLAIMSET);
> -
> - writel_relaxed(state->trcprgctlr, drvdata->base + TRCPRGCTLR);
> - writel_relaxed(state->trcprocselr, drvdata->base + TRCPROCSELR);
> - writel_relaxed(state->trcconfigr, drvdata->base + TRCCONFIGR);
> - writel_relaxed(state->trcauxctlr, drvdata->base + TRCAUXCTLR);
> - writel_relaxed(state->trceventctl0r, drvdata->base + TRCEVENTCTL0R);
> - writel_relaxed(state->trceventctl1r, drvdata->base + TRCEVENTCTL1R);
> - writel_relaxed(state->trcstallctlr, drvdata->base + TRCSTALLCTLR);
> - writel_relaxed(state->trctsctlr, drvdata->base + TRCTSCTLR);
> - writel_relaxed(state->trcsyncpr, drvdata->base + TRCSYNCPR);
> - writel_relaxed(state->trcccctlr, drvdata->base + TRCCCCTLR);
> - writel_relaxed(state->trcbbctlr, drvdata->base + TRCBBCTLR);
> - writel_relaxed(state->trctraceidr, drvdata->base + TRCTRACEIDR);
> - writel_relaxed(state->trcqctlr, drvdata->base + TRCQCTLR);
> -
> - writel_relaxed(state->trcvictlr, drvdata->base + TRCVICTLR);
> - writel_relaxed(state->trcviiectlr, drvdata->base + TRCVIIECTLR);
> - writel_relaxed(state->trcvissctlr, drvdata->base + TRCVISSCTLR);
> - writel_relaxed(state->trcvipcssctlr, drvdata->base + TRCVIPCSSCTLR);
> - writel_relaxed(state->trcvdctlr, drvdata->base + TRCVDCTLR);
> - writel_relaxed(state->trcvdsacctlr, drvdata->base + TRCVDSACCTLR);
> - writel_relaxed(state->trcvdarcctlr, drvdata->base + TRCVDARCCTLR);
> + etm4x_relaxed_write32(csa, state->trcclaimset, TRCCLAIMSET);
> +
> + etm4x_relaxed_write32(csa, state->trcprgctlr, TRCPRGCTLR);
> + etm4x_relaxed_write32(csa, state->trcprocselr, TRCPROCSELR);
> + etm4x_relaxed_write32(csa, state->trcconfigr, TRCCONFIGR);
> + etm4x_relaxed_write32(csa, state->trcauxctlr, TRCAUXCTLR);
> + etm4x_relaxed_write32(csa, state->trceventctl0r, TRCEVENTCTL0R);
> + etm4x_relaxed_write32(csa, state->trceventctl1r, TRCEVENTCTL1R);
> + etm4x_relaxed_write32(csa, state->trcstallctlr, TRCSTALLCTLR);
> + etm4x_relaxed_write32(csa, state->trctsctlr, TRCTSCTLR);
> + etm4x_relaxed_write32(csa, state->trcsyncpr, TRCSYNCPR);
> + etm4x_relaxed_write32(csa, state->trcccctlr, TRCCCCTLR);
> + etm4x_relaxed_write32(csa, state->trcbbctlr, TRCBBCTLR);
> + etm4x_relaxed_write32(csa, state->trctraceidr, TRCTRACEIDR);
> + etm4x_relaxed_write32(csa, state->trcqctlr, TRCQCTLR);
> +
> + etm4x_relaxed_write32(csa, state->trcvictlr, TRCVICTLR);
> + etm4x_relaxed_write32(csa, state->trcviiectlr, TRCVIIECTLR);
> + etm4x_relaxed_write32(csa, state->trcvissctlr, TRCVISSCTLR);
> + etm4x_relaxed_write32(csa, state->trcvipcssctlr, TRCVIPCSSCTLR);
> + etm4x_relaxed_write32(csa, state->trcvdctlr, TRCVDCTLR);
> + etm4x_relaxed_write32(csa, state->trcvdsacctlr, TRCVDSACCTLR);
> + etm4x_relaxed_write32(csa, state->trcvdarcctlr, TRCVDARCCTLR);
>
> for (i = 0; i < drvdata->nrseqstate; i++)
> - writel_relaxed(state->trcseqevr[i],
> - drvdata->base + TRCSEQEVRn(i));
> + etm4x_relaxed_write32(csa, state->trcseqevr[i], TRCSEQEVRn(i));
>
> - writel_relaxed(state->trcseqrstevr, drvdata->base + TRCSEQRSTEVR);
> - writel_relaxed(state->trcseqstr, drvdata->base + TRCSEQSTR);
> - writel_relaxed(state->trcextinselr, drvdata->base + TRCEXTINSELR);
> + etm4x_relaxed_write32(csa, state->trcseqrstevr, TRCSEQRSTEVR);
> + etm4x_relaxed_write32(csa, state->trcseqstr, TRCSEQSTR);
> + etm4x_relaxed_write32(csa, state->trcextinselr, TRCEXTINSELR);
>
> for (i = 0; i < drvdata->nr_cntr; i++) {
> - writel_relaxed(state->trccntrldvr[i],
> - drvdata->base + TRCCNTRLDVRn(i));
> - writel_relaxed(state->trccntctlr[i],
> - drvdata->base + TRCCNTCTLRn(i));
> - writel_relaxed(state->trccntvr[i],
> - drvdata->base + TRCCNTVRn(i));
> + etm4x_relaxed_write32(csa, state->trccntrldvr[i], TRCCNTRLDVRn(i));
> + etm4x_relaxed_write32(csa, state->trccntctlr[i], TRCCNTCTLRn(i));
> + etm4x_relaxed_write32(csa, state->trccntvr[i], TRCCNTVRn(i));
> }
>
> for (i = 0; i < drvdata->nr_resource * 2; i++)
> - writel_relaxed(state->trcrsctlr[i],
> - drvdata->base + TRCRSCTLRn(i));
> + etm4x_relaxed_write32(csa, state->trcrsctlr[i], TRCRSCTLRn(i));
>
> for (i = 0; i < drvdata->nr_ss_cmp; i++) {
> - writel_relaxed(state->trcssccr[i],
> - drvdata->base + TRCSSCCRn(i));
> - writel_relaxed(state->trcsscsr[i],
> - drvdata->base + TRCSSCSRn(i));
> - writel_relaxed(state->trcsspcicr[i],
> - drvdata->base + TRCSSPCICRn(i));
> + etm4x_relaxed_write32(csa, state->trcssccr[i], TRCSSCCRn(i));
> + etm4x_relaxed_write32(csa, state->trcsscsr[i], TRCSSCSRn(i));
> + etm4x_relaxed_write32(csa, state->trcsspcicr[i], TRCSSPCICRn(i));
> }
>
> for (i = 0; i < drvdata->nr_addr_cmp * 2; i++) {
> - writeq_relaxed(state->trcacvr[i],
> - drvdata->base + TRCACVRn(i));
> - writeq_relaxed(state->trcacatr[i],
> - drvdata->base + TRCACATRn(i));
> + etm4x_relaxed_write64(csa, state->trcacvr[i], TRCACVRn(i));
> + etm4x_relaxed_write64(csa, state->trcacatr[i], TRCACATRn(i));
> }
>
> for (i = 0; i < drvdata->numcidc; i++)
> - writeq_relaxed(state->trccidcvr[i],
> - drvdata->base + TRCCIDCVRn(i));
> + etm4x_relaxed_write64(csa, state->trccidcvr[i], TRCCIDCVRn(i));
>
> for (i = 0; i < drvdata->numvmidc; i++)
> - writeq_relaxed(state->trcvmidcvr[i],
> - drvdata->base + TRCVMIDCVRn(i));
> + etm4x_relaxed_write64(csa, state->trcvmidcvr[i], TRCVMIDCVRn(i));
>
> - writel_relaxed(state->trccidcctlr0, drvdata->base + TRCCIDCCTLR0);
> - writel_relaxed(state->trccidcctlr1, drvdata->base + TRCCIDCCTLR1);
> + etm4x_relaxed_write32(csa, state->trccidcctlr0, TRCCIDCCTLR0);
> + etm4x_relaxed_write32(csa, state->trccidcctlr1, TRCCIDCCTLR1);
>
> - writel_relaxed(state->trcvmidcctlr0, drvdata->base + TRCVMIDCCTLR0);
> - writel_relaxed(state->trcvmidcctlr0, drvdata->base + TRCVMIDCCTLR1);
> + etm4x_relaxed_write32(csa, state->trcvmidcctlr0, TRCVMIDCCTLR0);
> + etm4x_relaxed_write32(csa, state->trcvmidcctlr0, TRCVMIDCCTLR1);
>
> - writel_relaxed(state->trcclaimset, drvdata->base + TRCCLAIMSET);
> + etm4x_relaxed_write32(csa, state->trcclaimset, TRCCLAIMSET);
>
> - writel_relaxed(state->trcpdcr, drvdata->base + TRCPDCR);
> + etm4x_relaxed_write32(csa, state->trcpdcr, TRCPDCR);
>
> drvdata->state_needs_restore = false;
>
> diff --git a/drivers/hwtracing/coresight/coresight-etm4x.h b/drivers/hwtracing/coresight/coresight-etm4x.h
> index b8283e1d6d88..2b51d03ab6d7 100644
> --- a/drivers/hwtracing/coresight/coresight-etm4x.h
> +++ b/drivers/hwtracing/coresight/coresight-etm4x.h
> @@ -120,6 +120,30 @@
> #define TRCCIDR2 0xFF8
> #define TRCCIDR3 0xFFC
>
> +#define etm4x_relaxed_read32(csa, offset) \
> + readl_relaxed((csa)->base + (offset))
> +
> +#define etm4x_read32(csa, offset) \
> + readl((csa)->base + (offset))
> +
> +#define etm4x_relaxed_write32(csa, val, offset) \
> + writel_relaxed((val), (csa)->base + (offset))
> +
> +#define etm4x_write32(csa, val, offset) \
> + writel((val), (csa)->base + (offset))
> +
> +#define etm4x_relaxed_read64(csa, offset) \
> + readq_relaxed((csa)->base + (offset))
> +
> +#define etm4x_read64(csa, offset) \
> + readq((csa)->base + (offset))
> +
> +#define etm4x_relaxed_write64(csa, val, offset) \
> + writeq_relaxed((val), (csa)->base + (offset))
> +
> +#define etm4x_write64(csa, val, offset) \
> + writeq((val), (csa)->base + (offset))
> +
Since I haven't gone through the rest of the patches I'll assume you want to
enhance the above to pick an access type at some point in the future.
> /* ETMv4 resources */
> #define ETM_MAX_NR_PE 8
> #define ETMv4_MAX_CNTR 4
> --
> 2.24.1
>
On 07/30/2020 06:31 PM, Mathieu Poirier wrote:
> On Wed, Jul 22, 2020 at 06:20:30PM +0100, Suzuki K Poulose wrote:
>> etm4_init_arch_data is called early during the device probe,
>> even before the coresight_device is registered. Since we are
>> about to replace the direct access via abstraction layer, we
>> need a way to pass in the csdev_access for the given device.
>> Towards this free up the argument, which is already available
>> via etmdrvdata[smp_processor_id()].
>>
>> Cc: Mathieu Poirier <[email protected]>
>> Cc: Mike Leach <[email protected]>
>> Signed-off-by: Suzuki K Poulose <[email protected]>
>> ---
>> drivers/hwtracing/coresight/coresight-etm4x.c | 15 +++++++++++----
>> 1 file changed, 11 insertions(+), 4 deletions(-)
>>
>> diff --git a/drivers/hwtracing/coresight/coresight-etm4x.c b/drivers/hwtracing/coresight/coresight-etm4x.c
>> index 7bb74c659c4f..67deb4a4e618 100644
>> --- a/drivers/hwtracing/coresight/coresight-etm4x.c
>> +++ b/drivers/hwtracing/coresight/coresight-etm4x.c
>> @@ -614,7 +614,8 @@ static const struct coresight_ops etm4_cs_ops = {
>> .source_ops = &etm4_source_ops,
>> };
>>
>> -static void etm4_init_arch_data(void *info)
>> +
>> +static void etm4_init_arch_data(void *__unused)
>> {
>> u32 etmidr0;
>> u32 etmidr1;
>> @@ -622,8 +623,14 @@ static void etm4_init_arch_data(void *info)
>> u32 etmidr3;
>> u32 etmidr4;
>> u32 etmidr5;
>> - struct etmv4_drvdata *drvdata = info;
>> - int i;
>> + struct etmv4_drvdata *drvdata;
>> + int i, cpu;
>> +
>> + cpu = raw_smp_processor_id();
>
> Can you provide details on the motivation to use the raw_ version over the regular
> one? As far as I can see in linux/smp.h there is no difference between them
> unless DEBUB_PREEMPT is enabled. Even then the debug version won't complain
> since the task is CPU affined.
>
Right, it is partly my misunderstanding. debug_smp_processor_id() is to
detect cases where smp_processor_id() is called in pre-emptible
contexts. This is not the case here. So it is fine to use the
smp_processor_id(). I will switch to that in the next version.
Thanks
Suzuki
On 07/30/2020 09:20 PM, Mathieu Poirier wrote:
> On Wed, Jul 22, 2020 at 06:20:34PM +0100, Suzuki K Poulose wrote:
>> Convert all register accesses from etm4x driver to use a wrapper
>> to allow switching the access at runtime with little overhead.
>>
>> co-developed by sed tool ;-), mostly equivalent to :
>>
>> s/readl\(_relaxed\)\?(drvdata->base + \(.*\))/etm4x_\1_read32(csdev, \2)
>> s/writel\(_relaxed\)\?(\(.*\), drvdata->base + \(.*\))/etm4x_\1_write32(csdev, \2, \3)
>>
>> We don't want to replace them with the csdev_access_* to
>> avoid a function call for every register access for system
>> register access.
>>
>> Cc: Mathieu Poirier <[email protected]>
>> Cc: Mike Leach <[email protected]>
>> Signed-off-by: Suzuki K Poulose <[email protected]>
>> ---
>> .../coresight/coresight-etm4x-sysfs.c | 9 +-
>> drivers/hwtracing/coresight/coresight-etm4x.c | 334 +++++++++---------
>> drivers/hwtracing/coresight/coresight-etm4x.h | 24 ++
>> 3 files changed, 189 insertions(+), 178 deletions(-)
>>
Agreed to all the comments.
>> diff --git a/drivers/hwtracing/coresight/coresight-etm4x.h b/drivers/hwtracing/coresight/coresight-etm4x.h
>> index b8283e1d6d88..2b51d03ab6d7 100644
>> --- a/drivers/hwtracing/coresight/coresight-etm4x.h
>> +++ b/drivers/hwtracing/coresight/coresight-etm4x.h
>> @@ -120,6 +120,30 @@
>> #define TRCCIDR2 0xFF8
>> #define TRCCIDR3 0xFFC
>>
>> +#define etm4x_relaxed_read32(csa, offset) \
>> + readl_relaxed((csa)->base + (offset))
>> +
>> +#define etm4x_read32(csa, offset) \
>> + readl((csa)->base + (offset))
>> +
>> +#define etm4x_relaxed_write32(csa, val, offset) \
>> + writel_relaxed((val), (csa)->base + (offset))
>> +
>> +#define etm4x_write32(csa, val, offset) \
>> + writel((val), (csa)->base + (offset))
>> +
>> +#define etm4x_relaxed_read64(csa, offset) \
>> + readq_relaxed((csa)->base + (offset))
>> +
>> +#define etm4x_read64(csa, offset) \
>> + readq((csa)->base + (offset))
>> +
>> +#define etm4x_relaxed_write64(csa, val, offset) \
>> + writeq_relaxed((val), (csa)->base + (offset))
>> +
>> +#define etm4x_write64(csa, val, offset) \
>> + writeq((val), (csa)->base + (offset))
>> +
>
> Since I haven't gone through the rest of the patches I'll assume you want to
> enhance the above to pick an access type at some point in the future.
>
Yes, they are plumbed in with the introduction of system instruction
support. We don't want to the overhead of a function call for
each register access. Also, we would like to avoid jumping
through the large switch..cases for a compile time constant
offset. Hence this macro.
Cheers
Suzuki