firmware: qcom_scm: Add trace points to scm driver

Adding traces to find the arguments passed to secure world
and the values returned.

Change-Id: I6a90f968a05873f0ecbd4a0cc8c85d704e1d64cf
Signed-off-by: Elliot Berman <eberman@codeaurora.org>
Signed-off-by: Siddharth Gupta <sidgup@codeaurora.org>
This commit is contained in:
Elliot Berman 2019-11-07 13:54:38 -08:00 • committed by Siddharth Gupta
commit 873f25f55f
2 changed files with 49 additions and 37 deletions

View file

@ -19,6 +19,9 @@
#include "qcom_scm.h"
#define CREATE_TRACE_POINTS
#include <trace/events/scm.h>
#define MAX_QCOM_SCM_ARGS 10
#define MAX_QCOM_SCM_RETS 3
@ -169,10 +172,15 @@ static void __qcom_scm_call_do_quirk(const struct arm_smccc_args *smc,
struct arm_smccc_res *res)
{
unsigned long a0 = smc->a[0];
ktime_t time;
const bool trace = trace_scm_call_enabled();
struct arm_smccc_quirk quirk = { .id = ARM_SMCCC_QUIRK_QCOM_A6 };
quirk.state.a6 = 0;
if (trace)
time = ktime_get();
do {
arm_smccc_smc_quirk(a0, smc->a[1], smc->a[2], smc->a[3],
smc->a[4], smc->a[5], quirk.state.a6,
@ -182,6 +190,9 @@ static void __qcom_scm_call_do_quirk(const struct arm_smccc_args *smc,
a0 = res->a0;
} while (res->a0 == QCOM_SCM_INTERRUPTED);
if (trace)
trace_scm_call(smc->a, res, ktime_us_delta(ktime_get(), time));
}
static int qcom_scm_call_smccc(struct device *dev,
@ -261,9 +272,7 @@ static int qcom_scm_call_smccc(struct device *dev,
do {
mutex_lock(&qcom_scm_lock);
__qcom_scm_call_do_quirk(&smc, &res);
mutex_unlock(&qcom_scm_lock);
if (res.a0 == QCOM_SCM_V2_EBUSY) {
@ -329,10 +338,19 @@ static inline void *legacy_get_response_buffer(
static void __qcom_scm_call_do(const struct arm_smccc_args *smc,
struct arm_smccc_res *res)
{
ktime_t time;
const bool trace = trace_scm_call_enabled();
if (trace)
time = ktime_get();
do {
arm_smccc_smc(smc->a[0], smc->a[1], smc->a[2], smc->a[3],
smc->a[4], smc->a[5], smc->a[6], smc->a[7], res);
} while (res->a0 == QCOM_SCM_INTERRUPTED);
if (trace)
trace_scm_call(smc->a, res, ktime_us_delta(ktime_get(), time));
}
/**
@ -438,6 +456,8 @@ static int qcom_scm_call_atomic_legacy(struct device *dev,
struct arm_smccc_args smc = {{0}};
struct arm_smccc_res res;
size_t i, arglen = desc->arginfo & 0xf;
const bool trace = trace_scm_call_enabled();
ktime_t time;
BUG_ON(arglen > LEGACY_ATOMIC_N_REG_ARGS);
@ -447,9 +467,14 @@ static int qcom_scm_call_atomic_legacy(struct device *dev,
for (i = 0; i < arglen; i++)
smc.a[i + LEGACY_ATOMIC_FIRST_REG_IDX] = desc->args[i];
if (trace)
time = ktime_get();
arm_smccc_smc(smc.a[0], smc.a[1], smc.a[2], smc.a[3],
smc.a[4], smc.a[5], smc.a[6], smc.a[7], &res);
if (trace)
trace_scm_call(smc.a, &res, ktime_us_delta(ktime_get(), time));
desc->res[0] = res.a1;
desc->res[1] = res.a2;
desc->res[2] = res.a3;

View file

@ -1,6 +1,6 @@
/* SPDX-License-Identifier: GPL-2.0-only */
/*
* Copyright (c) 2016, 2018, The Linux Foundation. All rights reserved.
* Copyright (c) 2016, 2018-2019 The Linux Foundation. All rights reserved.
*/
#undef TRACE_SYSTEM
@ -10,50 +10,37 @@
#define _TRACE_SCM_H
#include <linux/types.h>
#include <linux/tracepoint.h>
#include <soc/qcom/scm.h>
#include <linux/arm-smccc.h>
TRACE_EVENT(scm_call_start,
TRACE_EVENT(scm_call,
TP_PROTO(u64 x0, struct scm_desc *p),
TP_PROTO(const unsigned long *a, const struct arm_smccc_res *r,
const s64 delta),
TP_ARGS(x0, p),
TP_ARGS(a, r, delta),
TP_STRUCT__entry(
__field(u64, x0)
__field(u32, arginfo)
__array(u64, args, MAX_SCM_ARGS)
__field(u64, x5)
__array(u64, args, 8)
__array(unsigned long, ret, 4)
__field(s64, delta)
),
TP_fast_assign(
__entry->x0 = x0;
__entry->arginfo = p->arginfo;
memcpy(__entry->args, p->args, sizeof(__entry->args));
__entry->x5 = p->x5;
memcpy(__entry->args, a, sizeof(__entry->args));
__entry->ret[0] = r->a0;
__entry->ret[1] = r->a1;
__entry->ret[2] = r->a2;
__entry->ret[3] = r->a3;
__entry->delta = delta;
),
TP_printk("func id=%#llx (args: %#x, %#llx, %#llx, %#llx, %#llx)",
__entry->x0, __entry->arginfo, __entry->args[0],
__entry->args[1], __entry->args[2], __entry->x5)
);
TRACE_EVENT(scm_call_end,
TP_PROTO(struct scm_desc *p),
TP_ARGS(p),
TP_STRUCT__entry(
__array(u64, ret, MAX_SCM_RETS)
),
TP_fast_assign(
memcpy(__entry->ret, p->ret, sizeof(__entry->ret));
),
TP_printk("ret: %#llx, %#llx, %#llx",
__entry->ret[0], __entry->ret[1], __entry->ret[2])
TP_printk("%3ld [%#lx %#lx %#lx %#lx %#lx %#lx %#lx %#lx] (%#lx %#lx %#lx %#lx)",
__entry->delta,
__entry->args[0], __entry->args[1], __entry->args[2],
__entry->args[3], __entry->args[4], __entry->args[5],
__entry->args[6], __entry->args[7],
__entry->ret[0], __entry->ret[1],
__entry->ret[2], __entry->ret[3])
);
#endif /* _TRACE_SCM_H */