Commit 1b6b0e08 authored by Mike Leach's avatar Mike Leach Committed by Greg Kroah-Hartman
Browse files

coresight: etm4x: Fix issues with start-stop logic.



Fixes the following issues when using the ETMv4 start-stop logic.

1) Setting a start or a stop address should not automatically set the
start-stop status to 'on'. The value set by the user in 'mode' must
be respected or start instances could be missed.
2) Missing API for controlling TRCVIPCSSCTLR - start stop control by
PE comparators.
3) Default ETM configuration sets a trace all range, and correctly sets
the start-stop status bit. This was not being correctly reflected in
the 'mode' parameter.

Signed-off-by: default avatarMike Leach <mike.leach@linaro.org>
Signed-off-by: default avatarMathieu Poirier <mathieu.poirier@linaro.org>
Link: https://lore.kernel.org/r/20191104181251.26732-8-mathieu.poirier@linaro.org


Signed-off-by: default avatarGreg Kroah-Hartman <gregkh@linuxfoundation.org>
parent 75198a7d
Loading
Loading
Loading
Loading
+35 −4
Original line number Diff line number Diff line
@@ -217,6 +217,7 @@ static ssize_t reset_store(struct device *dev,

	/* No start-stop filtering for ViewInst */
	config->vissctlr = 0x0;
	config->vipcssctlr = 0x0;

	/* Disable seq events */
	for (i = 0; i < drvdata->nrseqstate-1; i++)
@@ -1059,8 +1060,6 @@ static ssize_t addr_start_store(struct device *dev,
	config->addr_val[idx] = (u64)val;
	config->addr_type[idx] = ETM_ADDR_TYPE_START;
	config->vissctlr |= BIT(idx);
	/* SSSTATUS, bit[9] - turn on start/stop logic */
	config->vinst_ctrl |= BIT(9);
	spin_unlock(&drvdata->spinlock);
	return size;
}
@@ -1116,8 +1115,6 @@ static ssize_t addr_stop_store(struct device *dev,
	config->addr_val[idx] = (u64)val;
	config->addr_type[idx] = ETM_ADDR_TYPE_STOP;
	config->vissctlr |= BIT(idx + 16);
	/* SSSTATUS, bit[9] - turn on start/stop logic */
	config->vinst_ctrl |= BIT(9);
	spin_unlock(&drvdata->spinlock);
	return size;
}
@@ -1274,6 +1271,39 @@ static ssize_t addr_exlevel_s_ns_store(struct device *dev,
}
static DEVICE_ATTR_RW(addr_exlevel_s_ns);

static ssize_t vinst_pe_cmp_start_stop_show(struct device *dev,
					    struct device_attribute *attr,
					    char *buf)
{
	unsigned long val;
	struct etmv4_drvdata *drvdata = dev_get_drvdata(dev->parent);
	struct etmv4_config *config = &drvdata->config;

	if (!drvdata->nr_pe_cmp)
		return -EINVAL;
	val = config->vipcssctlr;
	return scnprintf(buf, PAGE_SIZE, "%#lx\n", val);
}
static ssize_t vinst_pe_cmp_start_stop_store(struct device *dev,
					     struct device_attribute *attr,
					     const char *buf, size_t size)
{
	unsigned long val;
	struct etmv4_drvdata *drvdata = dev_get_drvdata(dev->parent);
	struct etmv4_config *config = &drvdata->config;

	if (kstrtoul(buf, 16, &val))
		return -EINVAL;
	if (!drvdata->nr_pe_cmp)
		return -EINVAL;

	spin_lock(&drvdata->spinlock);
	config->vipcssctlr = val;
	spin_unlock(&drvdata->spinlock);
	return size;
}
static DEVICE_ATTR_RW(vinst_pe_cmp_start_stop);

static ssize_t seq_idx_show(struct device *dev,
			    struct device_attribute *attr,
			    char *buf)
@@ -2080,6 +2110,7 @@ static struct attribute *coresight_etmv4_attrs[] = {
	&dev_attr_addr_ctxtype.attr,
	&dev_attr_addr_context.attr,
	&dev_attr_addr_exlevel_s_ns.attr,
	&dev_attr_vinst_pe_cmp_start_stop.attr,
	&dev_attr_seq_idx.attr,
	&dev_attr_seq_state.attr,
	&dev_attr_seq_event.attr,
+1 −0
Original line number Diff line number Diff line
@@ -887,6 +887,7 @@ static void etm4_set_default_filter(struct etmv4_config *config)
	 * in the started state
	 */
	config->vinst_ctrl |= BIT(9);
	config->mode |= ETM_MODE_VIEWINST_STARTSTOP;

	/* No start-stop filtering for ViewInst */
	config->vissctlr = 0x0;