summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--drivers/video/tegra/host/debug.c3
-rw-r--r--drivers/video/tegra/host/debug.h1
-rw-r--r--drivers/video/tegra/host/dev.c45
-rw-r--r--include/trace/events/nvhost.h109
4 files changed, 132 insertions, 26 deletions
diff --git a/drivers/video/tegra/host/debug.c b/drivers/video/tegra/host/debug.c
index 4659a97ac110..aa4b41d96574 100644
--- a/drivers/video/tegra/host/debug.c
+++ b/drivers/video/tegra/host/debug.c
@@ -26,6 +26,7 @@
#include "debug.h"
pid_t nvhost_debug_null_kickoff_pid;
+unsigned int nvhost_debug_trace_cmdbuf;
pid_t nvhost_debug_force_timeout_pid;
u32 nvhost_debug_force_timeout_val;
@@ -130,6 +131,8 @@ void nvhost_debug_init(struct nvhost_master *master)
debugfs_create_u32("null_kickoff_pid", S_IRUGO|S_IWUSR, de,
&nvhost_debug_null_kickoff_pid);
+ debugfs_create_u32("trace_cmdbuf", S_IRUGO|S_IWUSR, de,
+ &nvhost_debug_trace_cmdbuf);
if (master->op.debug.debug_init)
master->op.debug.debug_init(de);
diff --git a/drivers/video/tegra/host/debug.h b/drivers/video/tegra/host/debug.h
index 0e9e51e5f955..9dd3a1995478 100644
--- a/drivers/video/tegra/host/debug.h
+++ b/drivers/video/tegra/host/debug.h
@@ -46,5 +46,6 @@ void nvhost_debug_output(struct output *o, const char* fmt, ...);
extern pid_t nvhost_debug_force_timeout_pid;
extern u32 nvhost_debug_force_timeout_val;
extern u32 nvhost_debug_force_timeout_channel;
+extern unsigned int nvhost_debug_trace_cmdbuf;
#endif /*__NVHOST_DEBUG_H */
diff --git a/drivers/video/tegra/host/dev.c b/drivers/video/tegra/host/dev.c
index b552d5c52606..1767e53ca884 100644
--- a/drivers/video/tegra/host/dev.c
+++ b/drivers/video/tegra/host/dev.c
@@ -47,6 +47,7 @@
#define DRIVER_NAME "tegra_grhost"
#define IFACE_NAME "nvhost"
+#define TRACE_MAX_LENGTH 128U
static int nvhost_major = NVHOST_MAJOR;
static int nvhost_minor;
@@ -74,6 +75,40 @@ struct nvhost_ctrl_userctx {
u32 *mod_locks;
};
+/*
+ * Write cmdbuf to ftrace output. Checks if cmdbuf contents should be output
+ * and mmaps the cmdbuf contents if required.
+ */
+static void trace_write_cmdbuf(const char *name, u32 mem_id,
+ u32 words, u32 offset)
+{
+ struct nvmap_handle_ref handle;
+ void *mem = NULL;
+
+ if (nvhost_debug_trace_cmdbuf) {
+ handle.handle = nvmap_id_to_handle(mem_id);
+ mem = nvmap_mmap(&handle);
+ if (IS_ERR_OR_NULL(mem))
+ mem = NULL;
+ };
+
+ trace_nvhost_channel_write_cmdbuf(name, mem_id, words, offset);
+ if (mem) {
+ u32 i;
+ /*
+ * Write in batches of 128 as there seems to be a limit of how
+ * much you can output to ftrace at once.
+ */
+ for (i = 0; i < words; i += TRACE_MAX_LENGTH) {
+ trace_nvhost_channel_write_cmdbuf_data(name, mem_id,
+ min(words - i, TRACE_MAX_LENGTH),
+ offset + i * sizeof(u32),
+ mem);
+ }
+ nvmap_munmap(&handle, mem);
+ }
+}
+
static int nvhost_channelrelease(struct inode *inode, struct file *filp)
{
struct nvhost_channel_userctx *priv = filp->private_data;
@@ -218,7 +253,8 @@ static ssize_t nvhost_channelwrite(struct file *filp, const char __user *buf,
if (err)
break;
trace_nvhost_channel_write_submit(priv->ch->desc->name,
- count, priv->hdr.num_cmdbufs, priv->hdr.num_relocs);
+ count, priv->hdr.num_cmdbufs, priv->hdr.num_relocs,
+ priv->hdr.syncpt_id, priv->hdr.syncpt_incrs);
} else if (priv->hdr.num_cmdbufs) {
struct nvhost_cmdbuf cmdbuf;
consumed = sizeof(cmdbuf);
@@ -228,7 +264,7 @@ static ssize_t nvhost_channelwrite(struct file *filp, const char __user *buf,
err = -EFAULT;
break;
}
- trace_nvhost_channel_write_cmdbuf(priv->ch->desc->name,
+ trace_write_cmdbuf(priv->ch->desc->name,
cmdbuf.mem, cmdbuf.words, cmdbuf.offset);
add_gather(priv,
cmdbuf.mem, cmdbuf.words, cmdbuf.offset);
@@ -407,7 +443,8 @@ static long nvhost_channelctl(struct file *filp,
trace_nvhost_ioctl_channel_submit(priv->ch->desc->name,
priv->hdr.submit_version,
priv->hdr.num_cmdbufs, priv->hdr.num_relocs,
- priv->hdr.num_waitchks);
+ priv->hdr.num_waitchks,
+ priv->hdr.syncpt_id, priv->hdr.syncpt_incrs);
break;
}
case NVHOST_IOCTL_CHANNEL_GET_SYNCPOINTS:
@@ -616,6 +653,8 @@ static int nvhost_ioctl_ctrl_module_regrdwr(
void *values = args->values;
u32 vals[64];
+ trace_nvhost_ioctl_ctrl_module_regrdwr(args->id,
+ args->num_offsets, args->write);
if (!(args->id < ctx->dev->nb_modules) ||
(num_offsets == 0))
return -EINVAL;
diff --git a/include/trace/events/nvhost.h b/include/trace/events/nvhost.h
index 2a1845950ed5..a0184440a09c 100644
--- a/include/trace/events/nvhost.h
+++ b/include/trace/events/nvhost.h
@@ -53,15 +53,18 @@ DEFINE_EVENT(nvhost, nvhost_ioctl_channel_flush,
);
TRACE_EVENT(nvhost_channel_write_submit,
- TP_PROTO(const char *name, ssize_t count, u32 cmdbufs, u32 relocs),
+ TP_PROTO(const char *name, ssize_t count, u32 cmdbufs, u32 relocs,
+ u32 syncpt_id, u32 syncpt_incrs),
- TP_ARGS(name, count, cmdbufs, relocs),
+ TP_ARGS(name, count, cmdbufs, relocs, syncpt_id, syncpt_incrs),
TP_STRUCT__entry(
__field(const char *, name)
__field(ssize_t, count)
__field(u32, cmdbufs)
__field(u32, relocs)
+ __field(u32, syncpt_id)
+ __field(u32, syncpt_incrs)
),
TP_fast_assign(
@@ -69,18 +72,21 @@ TRACE_EVENT(nvhost_channel_write_submit,
__entry->count = count;
__entry->cmdbufs = cmdbufs;
__entry->relocs = relocs;
+ __entry->syncpt_id = syncpt_id;
+ __entry->syncpt_incrs = syncpt_incrs;
),
- TP_printk("name=%s, count=%lu, cmdbufs=%lu, relocs=%ld",
- __entry->name, (unsigned long)__entry->count,
- (unsigned long)__entry->cmdbufs, (unsigned long)__entry->relocs)
+ TP_printk("name=%s, count=%d, cmdbufs=%u, relocs=%u, syncpt_id=%u, syncpt_incrs=%u",
+ __entry->name, __entry->count, __entry->cmdbufs, __entry->relocs,
+ __entry->syncpt_id, __entry->syncpt_incrs)
);
TRACE_EVENT(nvhost_ioctl_channel_submit,
TP_PROTO(const char *name, u32 version, u32 cmdbufs, u32 relocs,
- u32 waitchks),
+ u32 waitchks, u32 syncpt_id, u32 syncpt_incrs),
- TP_ARGS(name, version, cmdbufs, relocs, waitchks),
+ TP_ARGS(name, version, cmdbufs, relocs, waitchks,
+ syncpt_id, syncpt_incrs),
TP_STRUCT__entry(
__field(const char *, name)
@@ -88,6 +94,8 @@ TRACE_EVENT(nvhost_ioctl_channel_submit,
__field(u32, cmdbufs)
__field(u32, relocs)
__field(u32, waitchks)
+ __field(u32, syncpt_id)
+ __field(u32, syncpt_incrs)
),
TP_fast_assign(
@@ -96,16 +104,18 @@ TRACE_EVENT(nvhost_ioctl_channel_submit,
__entry->cmdbufs = cmdbufs;
__entry->relocs = relocs;
__entry->waitchks = waitchks;
+ __entry->syncpt_id = syncpt_id;
+ __entry->syncpt_incrs = syncpt_incrs;
),
- TP_printk("name=%s, version=%lu, cmdbufs=%lu, relocs=%ld, waitchks=%ld",
- __entry->name, (unsigned long)__entry->version,
- (unsigned long)__entry->cmdbufs, (unsigned long)__entry->relocs,
- (unsigned long)__entry->waitchks)
+ TP_printk("name=%s, version=%u, cmdbufs=%u, relocs=%u, waitchks=%u, syncpt_id=%u, syncpt_incrs=%u",
+ __entry->name, __entry->version, __entry->cmdbufs, __entry->relocs,
+ __entry->waitchks, __entry->syncpt_id, __entry->syncpt_incrs)
);
TRACE_EVENT(nvhost_channel_write_cmdbuf,
- TP_PROTO(const char *name, u32 mem_id, u32 words, u32 offset),
+ TP_PROTO(const char *name, u32 mem_id,
+ u32 words, u32 offset),
TP_ARGS(name, mem_id, words, offset),
@@ -123,9 +133,43 @@ TRACE_EVENT(nvhost_channel_write_cmdbuf,
__entry->offset = offset;
),
- TP_printk("name=%s, mem_id=%08lx, words=%lu, offset=%ld",
- __entry->name, (unsigned long)__entry->mem_id,
- (unsigned long)__entry->words, (unsigned long)__entry->offset)
+ TP_printk("name=%s, mem_id=%08x, words=%u, offset=%d",
+ __entry->name, __entry->mem_id,
+ __entry->words, __entry->offset)
+);
+
+TRACE_EVENT(nvhost_channel_write_cmdbuf_data,
+ TP_PROTO(const char *name, u32 mem_id,
+ u32 words, u32 offset, void *cmdbuf),
+
+ TP_ARGS(name, mem_id, words, offset, cmdbuf),
+
+ TP_STRUCT__entry(
+ __field(const char *, name)
+ __field(u32, mem_id)
+ __field(u32, words)
+ __field(u32, offset)
+ __field(bool, cmdbuf)
+ __dynamic_array(u32, cmdbuf, words)
+ ),
+
+ TP_fast_assign(
+ if (cmdbuf) {
+ memcpy(__get_dynamic_array(cmdbuf), cmdbuf+offset,
+ words * sizeof(u32));
+ }
+ __entry->cmdbuf = cmdbuf;
+ __entry->name = name;
+ __entry->mem_id = mem_id;
+ __entry->words = words;
+ __entry->offset = offset;
+ ),
+
+ TP_printk("name=%s, mem_id=%08x, words=%u, offset=%d, contents=[%s]",
+ __entry->name, __entry->mem_id,
+ __entry->words, __entry->offset,
+ __print_hex(__get_dynamic_array(cmdbuf),
+ __entry->cmdbuf ? __entry->words * 4 : 0))
);
TRACE_EVENT(nvhost_channel_write_relocs,
@@ -143,8 +187,8 @@ TRACE_EVENT(nvhost_channel_write_relocs,
__entry->relocs = relocs;
),
- TP_printk("name=%s, relocs=%lu",
- __entry->name, (unsigned long)__entry->relocs)
+ TP_printk("name=%s, relocs=%u",
+ __entry->name, __entry->relocs)
);
TRACE_EVENT(nvhost_channel_write_waitchks,
@@ -164,9 +208,8 @@ TRACE_EVENT(nvhost_channel_write_waitchks,
__entry->waitmask = waitmask;
),
- TP_printk("name=%s, waitchks=%lu, waitmask=%08lx",
- __entry->name, (unsigned long)__entry->waitchks,
- (unsigned long)__entry->waitmask)
+ TP_printk("name=%s, waitchks=%u, waitmask=%08x",
+ __entry->name, __entry->waitchks, __entry->waitmask)
);
TRACE_EVENT(nvhost_channel_context_switch,
@@ -186,9 +229,8 @@ TRACE_EVENT(nvhost_channel_context_switch,
__entry->new_ctx = new_ctx;
),
- TP_printk("name=%s, old=%08lx, new=%08lx",
- __entry->name, (long unsigned int)__entry->old_ctx,
- (long unsigned int)__entry->new_ctx)
+ TP_printk("name=%s, old=%p, new=%p",
+ __entry->name, __entry->old_ctx, __entry->new_ctx)
);
TRACE_EVENT(nvhost_ctrlopen,
@@ -287,6 +329,27 @@ TRACE_EVENT(nvhost_ioctl_ctrl_syncpt_wait,
__entry->id, __entry->threshold, __entry->timeout)
);
+TRACE_EVENT(nvhost_ioctl_ctrl_module_regrdwr,
+ TP_PROTO(u32 id, u32 num_offsets, bool write),
+
+ TP_ARGS(id, num_offsets, write),
+
+ TP_STRUCT__entry(
+ __field(u32, id)
+ __field(u32, num_offsets)
+ __field(bool, write)
+ ),
+
+ TP_fast_assign(
+ __entry->id = id;
+ __entry->num_offsets = num_offsets;
+ __entry->write = write;
+ ),
+
+ TP_printk("id=%u, num_offsets=%u, write=%d",
+ __entry->id, __entry->num_offsets, __entry->write)
+);
+
TRACE_EVENT(nvhost_channel_submitted,
TP_PROTO(const char *name, u32 syncpt_base, u32 syncpt_max),