Commit b56eb9cd authored by Pawel Moll's avatar Pawel Moll Committed by Sasha Levin

bus: arm-ccn: Fix PMU handling of MN

[ Upstream commit 4e486cba ]

The "Miscellaneous Node" fell through cracks of node initialisation,
as its ID is shared with HN-I.

This patch treats MN as a special case (which it is), adding separate
validation check for it and pre-defining the node ID in relevant events
descriptions. That way one can simply run:

	# perf stat -a -e ccn/mn_ecbarrier/ <workload>

Additionally, direction in the MN pseudo-events XP watchpoint
definitions is corrected to be "TX" (1) as they are defined from the
crosspoint point of view (thus barriers are transmitted from XP to MN).

Cc: stable@vger.kernel.org # 3.17+
Signed-off-by: default avatarPawel Moll <pawel.moll@arm.com>
Signed-off-by: default avatarSasha Levin <alexander.levin@verizon.com>
parent 7298a8bf
...@@ -183,6 +183,7 @@ struct arm_ccn { ...@@ -183,6 +183,7 @@ struct arm_ccn {
struct arm_ccn_component *xp; struct arm_ccn_component *xp;
struct arm_ccn_dt dt; struct arm_ccn_dt dt;
int mn_id;
}; };
...@@ -322,6 +323,7 @@ struct arm_ccn_pmu_event { ...@@ -322,6 +323,7 @@ struct arm_ccn_pmu_event {
static ssize_t arm_ccn_pmu_event_show(struct device *dev, static ssize_t arm_ccn_pmu_event_show(struct device *dev,
struct device_attribute *attr, char *buf) struct device_attribute *attr, char *buf)
{ {
struct arm_ccn *ccn = pmu_to_arm_ccn(dev_get_drvdata(dev));
struct arm_ccn_pmu_event *event = container_of(attr, struct arm_ccn_pmu_event *event = container_of(attr,
struct arm_ccn_pmu_event, attr); struct arm_ccn_pmu_event, attr);
ssize_t res; ssize_t res;
...@@ -348,6 +350,9 @@ static ssize_t arm_ccn_pmu_event_show(struct device *dev, ...@@ -348,6 +350,9 @@ static ssize_t arm_ccn_pmu_event_show(struct device *dev,
res += snprintf(buf + res, PAGE_SIZE - res, res += snprintf(buf + res, PAGE_SIZE - res,
",cmp_l=?,cmp_h=?,mask=?"); ",cmp_l=?,cmp_h=?,mask=?");
break; break;
case CCN_TYPE_MN:
res += snprintf(buf + res, PAGE_SIZE - res, ",node=%d", ccn->mn_id);
break;
default: default:
res += snprintf(buf + res, PAGE_SIZE - res, ",node=?"); res += snprintf(buf + res, PAGE_SIZE - res, ",node=?");
break; break;
...@@ -377,9 +382,9 @@ static umode_t arm_ccn_pmu_events_is_visible(struct kobject *kobj, ...@@ -377,9 +382,9 @@ static umode_t arm_ccn_pmu_events_is_visible(struct kobject *kobj,
} }
static struct arm_ccn_pmu_event arm_ccn_pmu_events[] = { static struct arm_ccn_pmu_event arm_ccn_pmu_events[] = {
CCN_EVENT_MN(eobarrier, "dir=0,vc=0,cmp_h=0x1c00", CCN_IDX_MASK_OPCODE), CCN_EVENT_MN(eobarrier, "dir=1,vc=0,cmp_h=0x1c00", CCN_IDX_MASK_OPCODE),
CCN_EVENT_MN(ecbarrier, "dir=0,vc=0,cmp_h=0x1e00", CCN_IDX_MASK_OPCODE), CCN_EVENT_MN(ecbarrier, "dir=1,vc=0,cmp_h=0x1e00", CCN_IDX_MASK_OPCODE),
CCN_EVENT_MN(dvmop, "dir=0,vc=0,cmp_h=0x2800", CCN_IDX_MASK_OPCODE), CCN_EVENT_MN(dvmop, "dir=1,vc=0,cmp_h=0x2800", CCN_IDX_MASK_OPCODE),
CCN_EVENT_HNI(txdatflits, "dir=1,vc=3", CCN_IDX_MASK_ANY), CCN_EVENT_HNI(txdatflits, "dir=1,vc=3", CCN_IDX_MASK_ANY),
CCN_EVENT_HNI(rxdatflits, "dir=0,vc=3", CCN_IDX_MASK_ANY), CCN_EVENT_HNI(rxdatflits, "dir=0,vc=3", CCN_IDX_MASK_ANY),
CCN_EVENT_HNI(txreqflits, "dir=1,vc=0", CCN_IDX_MASK_ANY), CCN_EVENT_HNI(txreqflits, "dir=1,vc=0", CCN_IDX_MASK_ANY),
...@@ -666,6 +671,12 @@ static int arm_ccn_pmu_event_init(struct perf_event *event) ...@@ -666,6 +671,12 @@ static int arm_ccn_pmu_event_init(struct perf_event *event)
/* Validate node/xp vs topology */ /* Validate node/xp vs topology */
switch (type) { switch (type) {
case CCN_TYPE_MN:
if (node_xp != ccn->mn_id) {
dev_warn(ccn->dev, "Invalid MN ID %d!\n", node_xp);
return -EINVAL;
}
break;
case CCN_TYPE_XP: case CCN_TYPE_XP:
if (node_xp >= ccn->num_xps) { if (node_xp >= ccn->num_xps) {
dev_warn(ccn->dev, "Invalid XP ID %d!\n", node_xp); dev_warn(ccn->dev, "Invalid XP ID %d!\n", node_xp);
...@@ -1231,6 +1242,8 @@ static int arm_ccn_init_nodes(struct arm_ccn *ccn, int region, ...@@ -1231,6 +1242,8 @@ static int arm_ccn_init_nodes(struct arm_ccn *ccn, int region,
switch (type) { switch (type) {
case CCN_TYPE_MN: case CCN_TYPE_MN:
ccn->mn_id = id;
return 0;
case CCN_TYPE_DT: case CCN_TYPE_DT:
return 0; return 0;
case CCN_TYPE_XP: case CCN_TYPE_XP:
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment